Files
CosmicLaca-ComfyUI_Primere_…/front_end/frontend_helper.js
T

127 lines
4.3 KiB
JavaScript

const TOAST_DURATION_MS = 6000;
const BTN_HEIGHT = 32;
const BTN_COLOR = "#771a1a";
const BTN_COLOR_ACTIVE = "#932424";
const BTN_RADIUS = 6;
const BTN_FONT = "bold 15px sans-serif";
export function applyPrimereButtonStyle(widget) {
widget.computeSize = () => [0, BTN_HEIGHT];
widget.draw = function (ctx, node, widget_width, y) {
ctx.save();
const margin = 15;
ctx.fillStyle = this.clicked ? BTN_COLOR_ACTIVE : BTN_COLOR;
if (this.clicked) {
this.clicked = false;
node.setDirtyCanvas?.(true);
}
ctx.beginPath();
ctx.roundRect(margin, y, widget_width - margin * 2, BTN_HEIGHT, BTN_RADIUS);
ctx.fill();
ctx.fillStyle = "#dad570";
ctx.font = BTN_FONT;
ctx.textAlign = "center";
ctx.textBaseline = "middle";
ctx.fillText(this.name, widget_width * 0.5, y + BTN_HEIGHT * 0.5);
ctx.restore();
};
}
export function showToast(status, message) {
let container = document.getElementById("primere-toast-container");
if (!container) {
container = document.createElement("div");
container.id = "primere-toast-container";
Object.assign(container.style, {
position: "fixed",
top: "50%",
left: "50%",
transform: "translate(-50%, -50%)",
zIndex: "99999",
display: "flex",
flexDirection: "column",
gap: "8px",
pointerEvents: "none",
});
document.body.appendChild(container);
}
const isSuccess = status === "success";
const accentColor = isSuccess ? "#4caf50" : "#f44336";
const icon = isSuccess ? "✔" : "✖";
const toast = document.createElement("div");
Object.assign(toast.style, {
position: "relative",
overflow: "hidden",
background: "#1e1e1e",
border: `1px solid ${accentColor}`,
borderLeft: `4px solid ${accentColor}`,
borderRadius: "6px",
padding: "10px 14px 10px 12px",
minWidth: "280px",
maxWidth: "440px",
display: "flex",
alignItems: "flex-start",
gap: "10px",
pointerEvents: "all",
boxShadow: "0 4px 16px rgba(0,0,0,0.6)",
opacity: "0",
transform: "translateY(-12px)",
transition: "opacity 0.25s ease, transform 0.25s ease",
fontFamily: "sans-serif",
fontSize: "15px",
color: "#e0e0e0",
cursor: "default",
});
const iconEl = document.createElement("span");
iconEl.textContent = icon;
Object.assign(iconEl.style, { color: accentColor, fontSize: "15px", flexShrink: "0", lineHeight: "1.5" });
const textEl = document.createElement("span");
textEl.textContent = message;
Object.assign(textEl.style, { flex: "1", lineHeight: "1.5", wordBreak: "normal", overflowWrap: "break-word" });
const closeBtn = document.createElement("button");
closeBtn.textContent = "✕";
Object.assign(closeBtn.style, {
background: "none", border: "none", color: "#888", cursor: "pointer",
fontSize: "13px", padding: "0 0 0 6px", flexShrink: "0", lineHeight: "1.5",
});
closeBtn.addEventListener("mouseover", () => { closeBtn.style.color = "#ccc"; });
closeBtn.addEventListener("mouseout", () => { closeBtn.style.color = "#888"; });
const progress = document.createElement("div");
Object.assign(progress.style, {
position: "absolute", bottom: "0", left: "0",
height: "3px", width: "100%",
background: accentColor,
transformOrigin: "left",
transform: "scaleX(1)",
transition: `transform ${TOAST_DURATION_MS / 1000}s linear`,
});
toast.appendChild(iconEl);
toast.appendChild(textEl);
toast.appendChild(closeBtn);
toast.appendChild(progress);
container.appendChild(toast);
requestAnimationFrame(() => requestAnimationFrame(() => {
toast.style.opacity = "1";
toast.style.transform = "translateY(0)";
progress.style.transform = "scaleX(0)";
}));
function dismiss() {
clearTimeout(timer);
toast.style.opacity = "0";
toast.style.transform = "translateY(-12px)";
setTimeout(() => toast.remove(), 280);
}
const timer = setTimeout(dismiss, TOAST_DURATION_MS);
closeBtn.addEventListener("click", dismiss);
}