This Confluence user macro adds a celebratory confetti animation when a page is updated.
It automatically detects if the current page version has changed and, if so, displays a short burst of animated confetti along with a random motivational message.
The macro runs silently in the background, cleans up after itself, and resizes to zero once the animation ends — ensuring minimal layout disruption.
Confetti effects are powered by the open-source canvas-confetti library.
#set($pageId = $page.id)
#set($outputType = $renderContext.outputType)
<div id="page-edit-confetti" data-macro="page-edit-confetti" style="display: none; overflow: hidden; padding: 0; margin: 0;"></div>
<style>
@keyframes fadeOut {
0% {
opacity: 1;
transform: scale(1);
}
100% {
opacity: 0;
transform: scale(0.95);
}
}
.fade-out {
animation: fadeOut 500ms ease-out forwards;
}
</style>
<script src="https://cdn.jsdelivr.net/npm/canvas-confetti@1.6.0/dist/confetti.browser.min.js"></script>
<script>
(function () {
const pageId = "$pageId";
const storageKey = "confluence-page-version-" + pageId;
const confettiDuration = 3500;
const fadeDuration = 500;
const confettiBox = document.getElementById("page-edit-confetti");
const outputType = "$outputType";
const messages = [
"🎉 Another page powered up! Your contribution just made the workspace smarter.",
"📝 Update complete! Thanks for keeping the team in the loop!",
"🌟 Way to go! You’ve just made collaboration a little easier for everyone.",
"🚀 Nice update! Great documentation is what drives great teams.",
"💡 Content refreshed! Thanks for keeping knowledge flowing.",
"🏆 Knowledge champion alert! Your update keeps us all moving forward.",
"🔁 Sync complete! This kind of effort is what makes teamwork work.",
"💥 Update magic! You’ve added real value—thanks for keeping things sharp.",
"🌈 Documentation wizardry! A small update, a big impact.",
"🥳 Celebrate that save! Another step toward a more organized, efficient team."
];
if (!confettiBox || typeof AP === "undefined") return;
if (outputType === "preview") {
confettiBox.style.display = "none";
confettiBox.style.height = "0px";
AP.resize("0px", "0px");
setTimeout(() => AP.resize("0px", "0px"), 100);
return
}
confettiBox.style.display = "none";
confettiBox.style.height = "0px";
confettiBox.innerHTML = "";
AP.resize("0px", "0px");
AP.request({
url: "/api/v2/pages/" + pageId + "/versions",
type: "GET",
success: function (responseText) {
try {
const data = JSON.parse(responseText);
const currentVersion = data.results?.[0]?.number;
if (!currentVersion) return;
const storedVersion = parseInt(localStorage.getItem(storageKey), 10);
const isNew = !storedVersion || currentVersion > storedVersion;
if (isNew) {
localStorage.setItem(storageKey, currentVersion.toString());
const message = messages[Math.floor(Math.random() * messages.length)];
confettiBox.innerHTML =
'<div id="confetti-msg" style="' +
'text-align: center;' +
'color: #ff4081;' +
'font-size: 1.8rem;' +
'font-weight: bold;' +
'padding: 2rem 1rem;' +
'font-family: -apple-system, BlinkMacSystemFont, Roboto, Helvetica, Arial, sans-serif;' +
'">' +
message +
'</div>';
confettiBox.style.display = "block";
confettiBox.style.height = "500px";
AP.resize("100%", "500px");
if (window.confetti) {
window.confetti({
particleCount: 200,
spread: 70,
origin: {
y: 0.6
}
});
}
setTimeout(() => {
const msg = document.getElementById("confetti-msg");
if (msg) {
msg.classList.add("fade-out");
}
setTimeout(() => {
confettiBox.innerHTML = "";
confettiBox.style.display = "none";
confettiBox.style.height = "0px";
AP.resize("0px", "0px");
setTimeout(() => AP.resize("0px", "0px"), 100);
}, fadeDuration);
},
confettiDuration);
} else {
confettiBox.innerHTML = "";
confettiBox.style.display = "none";
confettiBox.style.height = "0px";
AP.resize("0px", "0px");
setTimeout(() => AP.resize("0px", "0px"), 100);
}
} catch (e) {
console.error("Failed to parse version response:",
e);
}
},
error: function (err) {
console.error("API request failed:",
err);
}
});
})();
</script>Generate a list of all content created by the current user by default, or by a specified user, across your Confluence site
Retrieve and display all page content properties in an AUI sortable table
Retrieve and display current exchange rates for major currencies against a specified base currency
Create dropdown menus in Confluence Cloud with predefined option sets, multiselect support, and permission-based access controls
Display the creation date of the current Confluence page
Get the latest cryptocurrency exchange rates for major coins
Display a custom list of recently updated content
Perform customized searches based on labels, content types, and other parameters
Show all attachments from the current space in a sortable table view
Convert a specified amount of cryptocurrency to a fiat currency