UNPKG

@usewayn/widget

Version:

Client side widget generator for Wayn PoW CAPTCHA.

105 lines (86 loc) 3.15 kB
(() => { const handleClick = (evt, element, waynWidget, handlers) => { const trigger = () => { handlers.forEach((h) => { element.addEventListener("click", h); h.call(element, evt); }); setTimeout(() => { element.onclick = null; handlers.forEach((h) => element.removeEventListener("click", h)); element.onclick = (e) => handleClick(e, element, waynWidget, handlers); }, 50); }; element.onclick = null; const offset = parseInt(element.getAttribute("data-wayn-floating-offset")) || 8; const position = element.getAttribute("data-wayn-floating-position") || "top"; const rect = element.getBoundingClientRect(); Object.assign(waynWidget.style, { display: "block", position: "absolute", zIndex: "99999" }); const centerX = rect.left + (rect.width - waynWidget.offsetWidth) / 2; const safeX = Math.min(centerX, window.innerWidth - waynWidget.offsetWidth); if (position === "top") { waynWidget.style.top = `${Math.max( window.scrollY, rect.top - waynWidget.offsetHeight - offset + window.scrollY )}px`; } else { waynWidget.style.top = `${Math.min( rect.bottom + offset + window.scrollY, window.innerHeight - waynWidget.offsetHeight + window.scrollY )}px`; } waynWidget.style.left = `${Math.max(safeX, 2)}px`; waynWidget.solve(); waynWidget.addEventListener("solve", ({ detail }) => { element.setAttribute("data-wayn-token", detail.token); element.setAttribute("data-wayn-progress", "done"); setTimeout(() => { trigger(); }, 500); setTimeout(() => { waynWidget.style.display = "none"; }, 700); }); }; const setupElement = (element) => { const waynWidgetSelector = element.getAttribute("data-wayn-floating"); if (!waynWidgetSelector) return; const waynWidget = document.querySelector(waynWidgetSelector); if (!document.contains(waynWidget) && !waynWidget.solve) { throw new Error(`[wayn - floating] "${waynWidgetSelector}" doesn't exist or isn't a Wayn widget`); } waynWidget.style.display = "none"; const handlers = [element.onclick].filter(Boolean); if (typeof getEventListeners === "function") { handlers.push( ...(getEventListeners(element).click || []).map((l) => l.listener) ); } if (handlers.length) { element.onclick = null; handlers.forEach((h) => element.removeEventListener("click", h)); } element.addEventListener("click", (e) => { e.stopImmediatePropagation(); e.preventDefault(); handleClick(e, element, waynWidget, handlers); }); }; const init = (root) => { setupElement(root); root.querySelectorAll("[data-wayn-floating]").forEach(setupElement); }; init(document.body); new MutationObserver((mutations) => mutations.forEach((mutation) => mutation.addedNodes.forEach((node) => { if (node.nodeType === Node.ELEMENT_NODE) init(node); }) ) ).observe(document.body, { childList: true, subtree: true }); })();