mirror of
https://github.com/litruv/lit.ruv.wtf.git
synced 2026-07-24 10:46:03 +10:00
update to node site
This commit is contained in:
71
website/scripts/PrintBubble.js
Normal file
71
website/scripts/PrintBubble.js
Normal file
@@ -0,0 +1,71 @@
|
||||
/**
|
||||
* Manages a Twitch-chat-style stacked speech bubble above a print node element.
|
||||
*
|
||||
* Messages enter at the bottom of the stack, push older messages upward, and
|
||||
* individually fade out after 5 seconds — matching the Twitch chat feel.
|
||||
*/
|
||||
export class PrintBubble {
|
||||
/** @type {HTMLElement} */
|
||||
#stack;
|
||||
|
||||
/** Each active message and its cleanup timer. @type {Array<{ el: HTMLElement, timer: number }>} */
|
||||
#entries = [];
|
||||
|
||||
static #FADE_START_MS = 4500;
|
||||
static #FADE_DURATION_MS = 500;
|
||||
|
||||
/**
|
||||
* @param {HTMLElement} nodeEl - The node element to attach bubbles to.
|
||||
*/
|
||||
constructor(nodeEl) {
|
||||
this.#stack = document.createElement("div");
|
||||
this.#stack.className = "print-bubble-stack";
|
||||
this.#stack.setAttribute("role", "log");
|
||||
this.#stack.setAttribute("aria-live", "polite");
|
||||
nodeEl.appendChild(this.#stack);
|
||||
}
|
||||
|
||||
/**
|
||||
* Pushes a new message onto the bubble stack.
|
||||
*
|
||||
* @param {string} text - The message to display.
|
||||
*/
|
||||
push(text) {
|
||||
const msg = document.createElement("div");
|
||||
msg.className = "print-bubble-msg";
|
||||
msg.textContent = String(text);
|
||||
this.#stack.appendChild(msg);
|
||||
|
||||
const entry = { el: msg, timer: 0 };
|
||||
this.#entries.push(entry);
|
||||
|
||||
entry.timer = window.setTimeout(() => {
|
||||
this.#fadeOut(entry);
|
||||
}, PrintBubble.#FADE_START_MS);
|
||||
}
|
||||
|
||||
/**
|
||||
* Triggers the fade-out animation and removes the message element.
|
||||
*
|
||||
* @param {{ el: HTMLElement, timer: number }} entry
|
||||
*/
|
||||
#fadeOut(entry) {
|
||||
entry.el.classList.add("is-fading");
|
||||
window.setTimeout(() => {
|
||||
entry.el.remove();
|
||||
const idx = this.#entries.indexOf(entry);
|
||||
if (idx !== -1) this.#entries.splice(idx, 1);
|
||||
}, PrintBubble.#FADE_DURATION_MS);
|
||||
}
|
||||
|
||||
/**
|
||||
* Immediately clears all active messages and their timers.
|
||||
*/
|
||||
clear() {
|
||||
for (const entry of this.#entries) {
|
||||
window.clearTimeout(entry.timer);
|
||||
entry.el.remove();
|
||||
}
|
||||
this.#entries = [];
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user