instruckt 0.4.13 → 0.4.16
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +23 -3
- package/dist/instruckt.cjs.js +1196 -94
- package/dist/instruckt.cjs.js.map +1 -1
- package/dist/instruckt.d.mts +28 -8
- package/dist/instruckt.d.ts +28 -8
- package/dist/instruckt.esm.js +1196 -94
- package/dist/instruckt.esm.js.map +1 -1
- package/dist/instruckt.iife.js +99 -42
- package/dist/instruckt.iife.js.map +1 -1
- package/package.json +4 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/index.ts","../src/api.ts","../src/ui/styles.ts","../src/ui/toolbar.ts","../src/ui/highlight.ts","../src/ui/popup.ts","../src/ui/markers.ts","../src/selector.ts","../src/adapters/livewire.ts","../src/adapters/vue.ts","../src/adapters/svelte.ts","../src/adapters/react.ts","../src/instruckt.ts"],"sourcesContent":["import { Instruckt } from './instruckt'\nimport type { InstrucktConfig, Annotation, AnnotationIntent, AnnotationSeverity, AnnotationStatus, FrameworkContext } from './types'\nimport type { AnnotationPayload } from './api'\n\nexport { Instruckt }\nexport type { InstrucktConfig, Annotation, AnnotationPayload, AnnotationIntent, AnnotationSeverity, AnnotationStatus, FrameworkContext }\n\n/**\n * Initialize instruckt.\n *\n * @example\n * instruckt.init({ endpoint: '/instruckt' })\n *\n * @example CDN\n * <script src=\"instruckt.iife.js\"></script>\n * <script>Instruckt.init({ endpoint: '/instruckt' })</script>\n */\nexport function init(config: InstrucktConfig): Instruckt {\n return new Instruckt(config)\n}\n","import type { Annotation } from './types'\n\n/** Read Laravel's XSRF-TOKEN cookie for CSRF protection */\nfunction getCsrfToken(): string {\n const match = document.cookie.match(/(?:^|;\\s*)XSRF-TOKEN=([^;]+)/)\n return match ? decodeURIComponent(match[1]) : ''\n}\n\nfunction headers(): Record<string, string> {\n const h: Record<string, string> = {\n 'Content-Type': 'application/json',\n Accept: 'application/json',\n 'X-Requested-With': 'XMLHttpRequest',\n }\n const csrf = getCsrfToken()\n if (csrf) h['X-XSRF-TOKEN'] = csrf\n return h\n}\n\n/** Convert snake_case API response to camelCase for JS types */\nexport function toCamelCase(obj: Record<string, unknown>): Record<string, unknown> {\n const out: Record<string, unknown> = {}\n for (const [k, v] of Object.entries(obj)) {\n const camel = k.replace(/_([a-z])/g, (_, c) => c.toUpperCase())\n out[camel] = Array.isArray(v)\n ? v.map(item => (item && typeof item === 'object' && !Array.isArray(item)) ? toCamelCase(item as Record<string, unknown>) : item)\n : (v && typeof v === 'object' && !Array.isArray(v)) ? toCamelCase(v as Record<string, unknown>) : v\n }\n return out\n}\n\n/** Convert camelCase JS payload to snake_case for Laravel API */\nfunction toSnake(obj: Record<string, unknown>): Record<string, unknown> {\n const out: Record<string, unknown> = {}\n for (const [k, v] of Object.entries(obj)) {\n const snake = k.replace(/[A-Z]/g, c => `_${c.toLowerCase()}`)\n out[snake] = (v && typeof v === 'object' && !Array.isArray(v)) ? toSnake(v as Record<string, unknown>) : v\n }\n return out\n}\n\nexport type AnnotationPayload = Omit<\n Annotation,\n 'id' | 'status' | 'thread' | 'createdAt'\n>\n\nexport class InstrucktApi {\n constructor(private readonly endpoint: string) {}\n\n async getAnnotations(): Promise<Annotation[]> {\n const res = await fetch(`${this.endpoint}/annotations`, {\n headers: headers(),\n })\n if (!res.ok) throw new Error(`instruckt: failed to load annotations (${res.status})`)\n const raw: Record<string, unknown>[] = await res.json()\n return raw.map(r => toCamelCase(r) as unknown as Annotation)\n }\n\n async addAnnotation(data: AnnotationPayload): Promise<Annotation> {\n const res = await fetch(`${this.endpoint}/annotations`, {\n method: 'POST',\n headers: headers(),\n body: JSON.stringify(toSnake(data as unknown as Record<string, unknown>)),\n })\n if (!res.ok) throw new Error(`instruckt: failed to add annotation (${res.status})`)\n return toCamelCase(await res.json()) as unknown as Annotation\n }\n\n async updateAnnotation(\n annotationId: string,\n data: Partial<Pick<Annotation, 'status' | 'comment'>>,\n ): Promise<Annotation> {\n const res = await fetch(`${this.endpoint}/annotations/${annotationId}`, {\n method: 'PATCH',\n headers: headers(),\n body: JSON.stringify(toSnake(data as unknown as Record<string, unknown>)),\n })\n if (!res.ok) throw new Error(`instruckt: failed to update annotation (${res.status})`)\n return toCamelCase(await res.json()) as unknown as Annotation\n }\n\n async addReply(annotationId: string, content: string, role: 'human' | 'agent' = 'human'): Promise<Annotation> {\n const res = await fetch(`${this.endpoint}/annotations/${annotationId}/reply`, {\n method: 'POST',\n headers: headers(),\n body: JSON.stringify({ role, content }),\n })\n if (!res.ok) throw new Error(`instruckt: failed to add reply (${res.status})`)\n return toCamelCase(await res.json()) as unknown as Annotation\n }\n}\n","/** Global styles injected into document.head — ONLY what must affect the host page */\nexport const GLOBAL_CSS = /* css */ `\nbody.ik-annotating,\nbody.ik-annotating * { cursor: crosshair !important; }\n`\n\n/** Toolbar shadow DOM styles — fully isolated */\nexport const TOOLBAR_CSS = /* css */ `\n:host {\n all: initial;\n display: block;\n position: fixed;\n z-index: 2147483646;\n}\n\n* { box-sizing: border-box; }\n\n:host-context([data-instruckt-theme=\"dark\"]),\n@media (prefers-color-scheme: dark) {\n :host {\n --ik-bg: #1c1c1e; --ik-bg2: #2c2c2e; --ik-border: #38383a;\n --ik-text: #f4f4f5; --ik-muted: #a1a1aa;\n --ik-shadow: 0 8px 32px rgba(0,0,0,.4), 0 0 0 1px rgba(255,255,255,.06);\n }\n}\n\n:host {\n --ik-accent: #6366f1;\n --ik-accent-h: #4f46e5;\n --ik-bg: #ffffff;\n --ik-bg2: #f4f4f5;\n --ik-border: #e4e4e7;\n --ik-text: #18181b;\n --ik-muted: #a1a1aa;\n --ik-shadow: 0 8px 32px rgba(0,0,0,.08), 0 0 0 1px rgba(0,0,0,.04);\n}\n\n.toolbar {\n display: flex;\n flex-direction: column;\n align-items: center;\n gap: 2px;\n background: var(--ik-bg);\n border-radius: 12px;\n padding: 6px;\n box-shadow: var(--ik-shadow);\n user-select: none;\n touch-action: none;\n cursor: grab;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;\n}\n.toolbar:active { cursor: grabbing; }\n\n.btn {\n display: flex;\n align-items: center;\n justify-content: center;\n width: 34px;\n height: 34px;\n border-radius: 8px;\n border: none;\n background: transparent;\n color: var(--ik-muted);\n cursor: pointer;\n padding: 0;\n position: relative;\n transition: background .15s ease, color .15s ease;\n}\n.btn svg { display: block; }\n.btn:hover { background: var(--ik-bg2); color: var(--ik-text); }\n.btn.active { background: var(--ik-accent); color: #fff; }\n.btn.active:hover { background: var(--ik-accent-h); }\n\n.divider { width: 18px; height: 1px; background: var(--ik-border); margin: 3px 0; }\n\n.badge {\n position: absolute;\n top: -3px; right: -3px;\n min-width: 16px; height: 16px;\n background: #ef4444;\n color: #fff;\n border-radius: 8px;\n font-size: 10px; font-weight: 600;\n display: flex; align-items: center; justify-content: center;\n padding: 0 4px;\n line-height: 1;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;\n}\n\n.minimize-btn { color: var(--ik-muted); opacity: .6; }\n.minimize-btn:hover { opacity: 1; }\n\n.danger-btn { color: var(--ik-muted); opacity: .6; }\n.danger-btn:hover { opacity: 1; color: #ef4444; }\n\n.clear-wrap {\n position: relative;\n display: flex;\n align-items: center;\n}\n.clear-all-btn {\n display: none;\n position: absolute;\n right: 100%;\n top: 0;\n background: var(--ik-bg);\n box-shadow: var(--ik-shadow);\n border-radius: 8px;\n}\n/* Instant tooltip */\n.clear-all-btn::before {\n content: attr(data-tooltip);\n position: absolute;\n right: calc(100% + 6px);\n top: 50%;\n transform: translateY(-50%);\n white-space: nowrap;\n font-size: 11px;\n padding: 4px 8px;\n border-radius: 6px;\n background: var(--ik-text);\n color: var(--ik-bg);\n pointer-events: none;\n opacity: 0;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;\n}\n.clear-all-btn:hover::before { opacity: 1; }\n/* Invisible bridge so hover doesn't break crossing the gap */\n.clear-all-btn::after {\n content: '';\n position: absolute;\n top: 0;\n left: 100%;\n width: 6px;\n height: 100%;\n}\n.clear-wrap:hover .clear-all-btn { display: flex; align-items: center; justify-content: center; }\n\n.fab {\n display: flex;\n align-items: center;\n justify-content: center;\n width: 32px;\n height: 32px;\n border-radius: 50%;\n border: none;\n background: var(--ik-bg);\n color: var(--ik-muted);\n box-shadow: var(--ik-shadow);\n cursor: pointer;\n padding: 0;\n transition: color .15s ease, transform .15s ease;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;\n}\n.fab:hover { color: var(--ik-accent); transform: scale(1.1); }\n.fab { position: relative; }\n\n.fab-badge {\n position: absolute;\n top: -4px; right: -4px;\n min-width: 16px; height: 16px;\n background: #6366f1;\n color: #fff;\n border-radius: 8px;\n font-size: 9px; font-weight: 700;\n display: flex; align-items: center; justify-content: center;\n padding: 0 3px;\n line-height: 1;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;\n}\n`\n\n/** Popup shadow DOM styles — fully isolated */\nexport const POPUP_CSS = /* css */ `\n:host {\n all: initial;\n display: block;\n position: fixed;\n z-index: 2147483647;\n}\n\n* { box-sizing: border-box; }\n\n:host {\n --ik-accent: #6366f1;\n --ik-accent-h: #4f46e5;\n --ik-bg: #ffffff;\n --ik-bg2: #f8f8f8;\n --ik-border: #e4e4e7;\n --ik-text: #18181b;\n --ik-muted: #71717a;\n --ik-shadow: 0 4px 24px rgba(0,0,0,.12);\n --ik-radius: 10px;\n --ik-hl: rgba(99,102,241,.15);\n}\n\n@media (prefers-color-scheme: dark) {\n :host {\n --ik-bg: #1c1c1e; --ik-bg2: #2c2c2e; --ik-border: #3a3a3c;\n --ik-text: #f4f4f5; --ik-muted: #a1a1aa;\n --ik-shadow: 0 4px 24px rgba(0,0,0,.5);\n --ik-hl: rgba(99,102,241,.2);\n }\n}\n\n.popup {\n width: 340px;\n background: var(--ik-bg);\n border: 1px solid var(--ik-border);\n border-radius: var(--ik-radius);\n box-shadow: var(--ik-shadow);\n padding: 14px;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;\n font-size: 13px;\n color: var(--ik-text);\n animation: pop-in .12s ease;\n}\n@keyframes pop-in {\n from { opacity:0; transform: scale(.95) translateY(4px); }\n to { opacity:1; transform: scale(1) translateY(0); }\n}\n\n.header { display:flex; align-items:center; justify-content:space-between; margin-bottom:10px; }\n.element-tag {\n font-size:11px; font-family:ui-monospace,monospace; color:var(--ik-muted);\n background:var(--ik-bg2); border-radius:4px; padding:2px 6px;\n max-width:220px; overflow:hidden; text-overflow:ellipsis; white-space:nowrap;\n}\n.close-btn {\n background:none; border:none; color:var(--ik-muted);\n cursor:pointer; font-size:18px; line-height:1; padding:0;\n}\n\n.fw-badge {\n display:inline-flex; align-items:center; gap:4px;\n font-size:10px; font-weight:700; text-transform:uppercase; letter-spacing:.05em;\n color:var(--ik-accent); background:var(--ik-hl); border-radius:4px;\n padding:2px 6px; margin-bottom:8px;\n}\n.selected-text {\n font-size:12px; color:var(--ik-muted); background:var(--ik-bg2);\n border-left:3px solid var(--ik-accent); padding:4px 8px;\n border-radius:0 4px 4px 0; margin-bottom:10px;\n overflow:hidden; text-overflow:ellipsis; white-space:nowrap;\n}\n\n.label {\n font-size:10px; font-weight:700; text-transform:uppercase;\n letter-spacing:.05em; color:var(--ik-muted); margin-bottom:4px;\n}\n.row { display:flex; gap:6px; margin-bottom:10px; }\n.chips { display:flex; gap:4px; flex-wrap:wrap; }\n\n.chip {\n font-size:11px; padding:3px 8px; border-radius:12px;\n border:1px solid var(--ik-border); background:transparent;\n color:var(--ik-muted); cursor:pointer; transition:all .1s;\n}\n.chip:hover { border-color:var(--ik-accent); color:var(--ik-accent); }\n.chip.sel { background:var(--ik-accent); border-color:var(--ik-accent); color:#fff; }\n.chip.blocking.sel { background:#ef4444; border-color:#ef4444; }\n.chip.important.sel { background:#f97316; border-color:#f97316; }\n.chip.suggestion.sel{ background:#22c55e; border-color:#22c55e; }\n\ntextarea {\n width:100%; min-height:80px; resize:vertical;\n border:1px solid var(--ik-border); border-radius:6px;\n background:var(--ik-bg2); color:var(--ik-text);\n font-family:inherit; font-size:13px; padding:8px 10px;\n outline:none; transition:border-color .15s; margin-bottom:10px;\n}\ntextarea:focus { border-color:var(--ik-accent); }\ntextarea::placeholder { color:var(--ik-muted); }\n\n.actions { display:flex; justify-content:flex-end; gap:6px; }\n\n.btn-secondary {\n padding:6px 14px; border-radius:6px; border:1px solid var(--ik-border);\n background:transparent; color:var(--ik-muted); font-size:12px; cursor:pointer; transition:all .1s;\n}\n.btn-secondary:hover { border-color:var(--ik-muted); color:var(--ik-text); }\n\n.btn-primary {\n padding:6px 14px; border-radius:6px; border:none;\n background:var(--ik-accent); color:#fff;\n font-size:12px; font-weight:700; cursor:pointer; transition:background .1s;\n}\n.btn-primary:hover { background:var(--ik-accent-h); }\n.btn-primary:disabled { opacity:.5; cursor:not-allowed; }\n\n.btn-danger {\n padding:6px 14px; border-radius:6px; border:1px solid #ef4444;\n background:transparent; color:#ef4444;\n font-size:12px; cursor:pointer; transition:all .1s;\n}\n.btn-danger:hover { background:#ef4444; color:#fff; }\n\n/* Thread view */\n.thread { margin-top:10px; border-top:1px solid var(--ik-border); padding-top:10px; }\n.msg { margin-bottom:8px; }\n.msg-role {\n font-size:10px; font-weight:700; text-transform:uppercase;\n letter-spacing:.05em; margin-bottom:2px;\n}\n.msg-role.human { color:var(--ik-accent); }\n.msg-role.agent { color:#22c55e; }\n.msg-content { font-size:12px; line-height:1.5; }\n\n.status-badge {\n display:inline-flex; align-items:center; gap:4px;\n font-size:10px; font-weight:700; text-transform:uppercase; letter-spacing:.05em;\n border-radius:4px; padding:2px 6px;\n}\n.status-badge.pending { background:rgba(99,102,241,.15); color:var(--ik-accent); }\n.status-badge.acknowledged { background:rgba(249,115,22,.15); color:#f97316; }\n.status-badge.resolved { background:rgba(34,197,94,.15); color:#22c55e; }\n.status-badge.dismissed { background:var(--ik-bg2); color:var(--ik-muted); }\n`\n\n/** Marker pin styles injected into document.head — pins overlay the page */\nexport const MARKER_CSS = /* css */ `\n.ik-marker {\n position: absolute;\n z-index: 2147483645;\n width: 24px; height: 24px;\n border-radius: 50%;\n background: #6366f1;\n color: #fff;\n font-size: 11px; font-weight: 700;\n display: flex; align-items: center; justify-content: center;\n cursor: pointer;\n box-shadow: 0 2px 8px rgba(99,102,241,.4);\n transition: transform .15s ease;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;\n pointer-events: all;\n user-select: none;\n}\n.ik-marker:hover { transform: scale(1.15); }\n.ik-marker.resolved { background: #22c55e; box-shadow: 0 2px 8px rgba(34,197,94,.4); }\n.ik-marker.dismissed { background: #71717a; box-shadow: 0 2px 8px rgba(0,0,0,.2); }\n.ik-marker.acknowledged { background: #f97316; box-shadow: 0 2px 8px rgba(249,115,22,.4); }\n`\n\n/** Inject styles into document.head (idempotent) */\nexport function injectGlobalStyles(): void {\n if (document.getElementById('instruckt-global')) return\n const style = document.createElement('style')\n style.id = 'instruckt-global'\n style.textContent = GLOBAL_CSS + MARKER_CSS\n document.head.appendChild(style)\n}\n","import { TOOLBAR_CSS } from './styles'\n\nexport type ToolbarMode = 'idle' | 'annotating' | 'frozen'\n\ninterface ToolbarCallbacks {\n onToggleAnnotate: (active: boolean) => void\n onFreezeAnimations: (frozen: boolean) => void\n onCopy: () => void\n onClearPage?: () => void\n onClearAll?: () => void\n onMinimize?: (minimized: boolean) => void\n}\n\n// ── Inline SVG icons (24x24, 2px stroke) ─────────────────────\n\nconst ICONS = {\n annotate: `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M12 20h9\"/><path d=\"M16.5 3.5a2.121 2.121 0 0 1 3 3L7 19l-4 1 1-4 12.5-12.5z\"/></svg>`,\n freeze: `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><rect x=\"6\" y=\"4\" width=\"4\" height=\"16\" rx=\"1\"/><rect x=\"14\" y=\"4\" width=\"4\" height=\"16\" rx=\"1\"/></svg>`,\n copy: `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><rect x=\"9\" y=\"9\" width=\"13\" height=\"13\" rx=\"2\"/><path d=\"M5 15H4a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h9a2 2 0 0 1 2 2v1\"/></svg>`,\n check: `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><polyline points=\"20 6 9 17 4 12\"/></svg>`,\n clear: `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><polyline points=\"3 6 5 6 21 6\"/><path d=\"M19 6v14a2 2 0 0 1-2 2H7a2 2 0 0 1-2-2V6m3 0V4a2 2 0 0 1 2-2h4a2 2 0 0 1 2 2v2\"/></svg>`,\n minimize: `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><polyline points=\"7 13 12 18 17 13\"/><line x1=\"12\" y1=\"6\" x2=\"12\" y2=\"18\"/></svg>`,\n logo: `<svg width=\"16\" height=\"16\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M12 20h9\"/><path d=\"M16.5 3.5a2.121 2.121 0 0 1 3 3L7 19l-4 1 1-4 12.5-12.5z\"/></svg>`,\n} as const\n\nexport class Toolbar {\n private host!: HTMLElement\n private shadow!: ShadowRoot\n private toolbarEl!: HTMLDivElement\n private fab!: HTMLButtonElement\n private fabBadge: HTMLSpanElement | null = null\n private annotateBtn!: HTMLButtonElement\n private freezeBtn!: HTMLButtonElement\n private copyBtn!: HTMLButtonElement\n private annotateActive = false\n private freezeActive = false\n private minimized = false\n private totalCount = 0\n private dragging = false\n private dragOffset = { x: 0, y: 0 }\n\n constructor(\n private readonly position: string,\n private readonly callbacks: ToolbarCallbacks,\n ) {\n this.build()\n this.setupDrag()\n }\n\n private build(): void {\n this.host = document.createElement('div')\n this.host.setAttribute('data-instruckt', 'toolbar')\n this.shadow = this.host.attachShadow({ mode: 'open' })\n\n const style = document.createElement('style')\n style.textContent = TOOLBAR_CSS\n this.shadow.appendChild(style)\n\n // Full toolbar\n this.toolbarEl = document.createElement('div')\n this.toolbarEl.className = 'toolbar'\n\n this.annotateBtn = this.makeBtn(ICONS.annotate, 'Annotate elements (A)', () => {\n const next = !this.annotateActive\n this.setAnnotateActive(next)\n this.callbacks.onToggleAnnotate(next)\n })\n\n this.freezeBtn = this.makeBtn(ICONS.freeze, 'Freeze page (F)', () => {\n const next = !this.freezeActive\n this.setFreezeActive(next)\n this.callbacks.onFreezeAnimations(next)\n })\n\n this.copyBtn = this.makeBtn(ICONS.copy, 'Copy annotations as markdown', () => {\n this.callbacks.onCopy()\n this.copyBtn.innerHTML = ICONS.check\n setTimeout(() => { this.copyBtn.innerHTML = ICONS.copy }, 1200)\n })\n\n const clearWrap = document.createElement('div')\n clearWrap.className = 'clear-wrap'\n\n const clearBtn = this.makeBtn(ICONS.clear, 'Clear this page (X)', () => {\n this.callbacks.onClearPage?.()\n })\n clearBtn.classList.add('danger-btn')\n\n const clearAllBtn = this.makeBtn(\n `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M12 2C6.5 2 2 6.5 2 12s4.5 10 10 10 10-4.5 10-10S17.5 2 12 2\"/><line x1=\"4.93\" y1=\"4.93\" x2=\"19.07\" y2=\"19.07\"/></svg>`,\n 'Delete all instructions.',\n () => this.callbacks.onClearAll?.(),\n )\n clearAllBtn.classList.add('danger-btn', 'clear-all-btn')\n clearAllBtn.removeAttribute('title')\n clearAllBtn.setAttribute('data-tooltip', 'Delete all instructions.')\n\n clearWrap.appendChild(clearBtn)\n clearWrap.appendChild(clearAllBtn)\n\n const minimizeBtn = this.makeBtn(ICONS.minimize, 'Minimize toolbar', () => {\n this.setMinimized(true)\n })\n minimizeBtn.classList.add('minimize-btn')\n\n const mkDiv = () => { const d = document.createElement('div'); d.className = 'divider'; return d }\n\n this.toolbarEl.append(\n this.annotateBtn, mkDiv(), this.freezeBtn, mkDiv(),\n this.copyBtn, clearWrap, mkDiv(), minimizeBtn,\n )\n this.shadow.appendChild(this.toolbarEl)\n\n // Floating action button (minimized state)\n this.fab = document.createElement('button')\n this.fab.className = 'fab'\n this.fab.title = 'Open instruckt toolbar'\n this.fab.setAttribute('aria-label', 'Open instruckt toolbar')\n this.fab.innerHTML = ICONS.logo\n this.fab.style.display = 'none'\n this.fab.addEventListener('click', (e) => {\n e.stopPropagation()\n this.setMinimized(false)\n })\n this.shadow.appendChild(this.fab)\n\n // Prevent toolbar clicks from reaching page handlers (e.g. Alpine @click.outside)\n // Shadow DOM stopPropagation only works within the shadow tree — clicks still\n // re-dispatch from the host element into the regular DOM.\n this.host.addEventListener('click', (e) => e.stopPropagation())\n this.host.addEventListener('mousedown', (e) => e.stopPropagation())\n this.host.addEventListener('pointerdown', (e) => e.stopPropagation())\n\n this.applyPosition()\n const root = document.getElementById('instruckt-root') ?? document.body\n root.appendChild(this.host)\n }\n\n private makeBtn(iconHtml: string, title: string, onClick: () => void): HTMLButtonElement {\n const btn = document.createElement('button')\n btn.className = 'btn'\n btn.title = title\n btn.setAttribute('aria-label', title)\n btn.innerHTML = iconHtml\n btn.addEventListener('click', (e) => {\n e.stopPropagation()\n onClick()\n })\n return btn\n }\n\n private applyPosition(): void {\n const m = '16px'\n Object.assign(this.host.style, {\n position: 'fixed',\n zIndex: '2147483646',\n bottom: this.position.includes('bottom') ? m : 'auto',\n top: this.position.includes('top') ? m : 'auto',\n right: this.position.includes('right') ? m : 'auto',\n left: this.position.includes('left') ? m : 'auto',\n })\n }\n\n private setupDrag(): void {\n this.shadow.addEventListener('mousedown', (evt) => {\n const e = evt as MouseEvent\n if ((e.target as Element).closest('.btn') || (e.target as Element).closest('.fab')) return\n this.dragging = true\n const rect = this.host.getBoundingClientRect()\n this.dragOffset = { x: e.clientX - rect.left, y: e.clientY - rect.top }\n e.preventDefault()\n })\n\n document.addEventListener('mousemove', (e) => {\n if (!this.dragging) return\n Object.assign(this.host.style, {\n left: `${e.clientX - this.dragOffset.x}px`,\n top: `${e.clientY - this.dragOffset.y}px`,\n right: 'auto',\n bottom: 'auto',\n })\n })\n\n document.addEventListener('mouseup', () => { this.dragging = false })\n }\n\n private setMinimized(min: boolean): void {\n this.minimized = min\n this.toolbarEl.style.display = min ? 'none' : ''\n this.fab.style.display = min ? '' : 'none'\n this.updateFabBadge()\n this.callbacks.onMinimize?.(min)\n }\n\n private updateFabBadge(): void {\n if (this.totalCount > 0 && this.minimized) {\n if (!this.fabBadge) {\n this.fabBadge = document.createElement('span')\n this.fabBadge.className = 'fab-badge'\n this.fab.appendChild(this.fabBadge)\n }\n this.fabBadge.textContent = this.totalCount > 99 ? '99+' : String(this.totalCount)\n } else {\n this.fabBadge?.remove()\n this.fabBadge = null\n }\n }\n\n isMinimized(): boolean {\n return this.minimized\n }\n\n /** Programmatically minimize without firing callback */\n minimize(): void {\n this.minimized = true\n this.toolbarEl.style.display = 'none'\n this.fab.style.display = ''\n this.updateFabBadge()\n }\n\n setAnnotateActive(active: boolean): void {\n this.annotateActive = active\n this.annotateBtn.classList.toggle('active', active)\n document.body.classList.toggle('ik-annotating', active)\n }\n\n setFreezeActive(active: boolean): void {\n this.freezeActive = active\n this.freezeBtn.classList.toggle('active', active)\n }\n\n // Keep for compatibility — resolves visual mode from instruckt.ts\n setMode(mode: ToolbarMode): void {\n this.setAnnotateActive(mode === 'annotating')\n }\n\n setAnnotationCount(count: number): void {\n let badge = this.annotateBtn.querySelector('.badge')\n if (count > 0) {\n if (!badge) {\n badge = document.createElement('span')\n badge.className = 'badge'\n this.annotateBtn.appendChild(badge)\n }\n badge.textContent = count > 99 ? '99+' : String(count)\n } else {\n badge?.remove()\n }\n }\n\n setTotalCount(count: number): void {\n this.totalCount = count\n this.updateFabBadge()\n }\n\n destroy(): void {\n this.host.remove()\n document.body.classList.remove('ik-annotating')\n }\n}\n","/** Hover highlight overlay — uses all inline styles, no CSS class needed */\nexport class ElementHighlight {\n private el: HTMLElement\n\n constructor() {\n this.el = document.createElement('div')\n // All styling inline to avoid any host-page CSS interference\n Object.assign(this.el.style, {\n position: 'fixed',\n pointerEvents: 'none', // MUST be none — prevents swallowing clicks\n zIndex: '2147483644',\n border: '2px solid rgba(99,102,241,0.7)',\n background: 'rgba(99,102,241,0.1)',\n borderRadius: '3px',\n transition: 'all 0.06s ease',\n display: 'none',\n })\n this.el.setAttribute('data-instruckt', 'highlight')\n const root = document.getElementById('instruckt-root') ?? document.body\n root.appendChild(this.el)\n }\n\n show(el: Element): void {\n const rect = el.getBoundingClientRect()\n if (rect.width === 0 && rect.height === 0) {\n this.hide()\n return\n }\n Object.assign(this.el.style, {\n display: 'block',\n left: `${rect.left}px`,\n top: `${rect.top}px`,\n width: `${rect.width}px`,\n height: `${rect.height}px`,\n })\n }\n\n hide(): void {\n this.el.style.display = 'none'\n }\n\n destroy(): void {\n this.el.remove()\n }\n}\n","import type { Annotation, PendingAnnotation } from '../types'\nimport { POPUP_CSS } from './styles'\n\ninterface PopupResult {\n comment: string\n}\n\ninterface PopupCallbacks {\n onSubmit: (result: PopupResult) => void\n onCancel: () => void\n}\n\ninterface EditCallbacks {\n onSave: (annotation: Annotation, newComment: string) => void\n onDelete: (annotation: Annotation) => void\n}\n\nfunction esc(s: string): string {\n return String(s ?? '').replace(/&/g, '&').replace(/</g, '<').replace(/>/g, '>').replace(/\"/g, '"')\n}\n\n/** Annotation popup — rendered in its own shadow DOM for CSS isolation */\nexport class AnnotationPopup {\n private host: HTMLElement | null = null\n private shadow: ShadowRoot | null = null\n\n // ── New annotation popup ──────────────────────────────────────\n\n showNew(pending: PendingAnnotation, callbacks: PopupCallbacks): void {\n this.destroy()\n this.host = document.createElement('div')\n this.host.setAttribute('data-instruckt', 'popup')\n this.stopHostPropagation(this.host)\n this.shadow = this.host.attachShadow({ mode: 'open' })\n\n const style = document.createElement('style')\n style.textContent = POPUP_CSS\n this.shadow.appendChild(style)\n\n const popup = document.createElement('div')\n popup.className = 'popup'\n\n const fwBadge = pending.framework\n ? `<div class=\"fw-badge\">${esc(pending.framework.component)}</div>`\n : ''\n const selText = pending.selectedText\n ? `<div class=\"selected-text\">\"${esc(pending.selectedText.slice(0, 80))}\"</div>`\n : ''\n\n popup.innerHTML = `\n <div class=\"header\">\n <span class=\"element-tag\" title=\"${esc(pending.elementPath)}\">${esc(pending.elementLabel)}</span>\n <button class=\"close-btn\" title=\"Cancel (Esc)\">✕</button>\n </div>\n ${fwBadge}${selText}\n <textarea placeholder=\"What needs to change here?\" rows=\"3\"></textarea>\n <div class=\"actions\">\n <button class=\"btn-secondary\" data-action=\"cancel\">Cancel</button>\n <button class=\"btn-primary\" data-action=\"submit\" disabled>Add note</button>\n </div>\n `\n\n const textarea = popup.querySelector('textarea')!\n const submitBtn = popup.querySelector<HTMLButtonElement>('[data-action=\"submit\"]')!\n\n textarea.addEventListener('input', () => {\n submitBtn.disabled = textarea.value.trim().length === 0\n })\n textarea.addEventListener('keydown', (e) => {\n // Stop ALL keyboard events from reaching page forms (React, Inertia, etc.)\n e.stopPropagation()\n if (e.key === 'Enter' && !e.shiftKey) {\n e.preventDefault()\n if (!submitBtn.disabled) submitBtn.click()\n }\n if (e.key === 'Escape') { callbacks.onCancel(); this.destroy() }\n })\n\n popup.querySelector('[data-action=\"cancel\"]')!.addEventListener('click', () => {\n callbacks.onCancel(); this.destroy()\n })\n popup.querySelector('.close-btn')!.addEventListener('click', () => {\n callbacks.onCancel(); this.destroy()\n })\n submitBtn.addEventListener('click', () => {\n const comment = textarea.value.trim()\n if (!comment) return\n callbacks.onSubmit({ comment })\n this.destroy()\n })\n\n this.shadow.appendChild(popup)\n ;(document.getElementById('instruckt-root') ?? document.body).appendChild(this.host)\n\n this.positionHost(pending.x, pending.y)\n this.setupOutsideClick()\n textarea.focus()\n }\n\n // ── Edit existing annotation ──────────────────────────────────\n\n showEdit(annotation: Annotation, callbacks: EditCallbacks): void {\n this.destroy()\n this.host = document.createElement('div')\n this.host.setAttribute('data-instruckt', 'popup')\n this.stopHostPropagation(this.host)\n this.shadow = this.host.attachShadow({ mode: 'open' })\n\n const style = document.createElement('style')\n style.textContent = POPUP_CSS\n this.shadow.appendChild(style)\n\n const popup = document.createElement('div')\n popup.className = 'popup'\n\n const fwBadge = annotation.framework\n ? `<div class=\"fw-badge\">${esc(annotation.framework.component)}</div>`\n : ''\n\n popup.innerHTML = `\n <div class=\"header\">\n <span class=\"element-tag\" title=\"${esc(annotation.elementPath)}\">${esc(annotation.element)}</span>\n <button class=\"close-btn\">✕</button>\n </div>\n ${fwBadge}\n <textarea rows=\"3\">${esc(annotation.comment)}</textarea>\n <div class=\"actions\">\n <button class=\"btn-danger\" data-action=\"delete\">Remove</button>\n <button class=\"btn-primary\" data-action=\"save\">Save</button>\n </div>\n `\n\n popup.querySelector('.close-btn')!.addEventListener('click', () => this.destroy())\n\n const textarea = popup.querySelector('textarea')!\n const saveBtn = popup.querySelector<HTMLButtonElement>('[data-action=\"save\"]')!\n const deleteBtn = popup.querySelector<HTMLButtonElement>('[data-action=\"delete\"]')!\n\n textarea.addEventListener('keydown', (e) => {\n e.stopPropagation()\n if (e.key === 'Enter' && !e.shiftKey) {\n e.preventDefault()\n saveBtn.click()\n }\n if (e.key === 'Escape') this.destroy()\n })\n\n saveBtn.addEventListener('click', () => {\n const newComment = textarea.value.trim()\n if (!newComment) return\n callbacks.onSave(annotation, newComment)\n this.destroy()\n })\n\n deleteBtn.addEventListener('click', () => {\n callbacks.onDelete(annotation)\n this.destroy()\n })\n\n this.shadow.appendChild(popup)\n ;(document.getElementById('instruckt-root') ?? document.body).appendChild(this.host)\n\n // Position near the marker\n const markerX = (annotation.x / 100) * window.innerWidth\n const markerY = annotation.y - window.scrollY\n this.positionHost(markerX, markerY)\n this.setupOutsideClick()\n textarea.focus()\n textarea.setSelectionRange(textarea.value.length, textarea.value.length)\n }\n\n // ── Helpers ───────────────────────────────────────────────────\n\n /** Prevent popup interactions from reaching page handlers (e.g. @click.outside, form submit) */\n private stopHostPropagation(host: HTMLElement): void {\n for (const evt of ['click', 'mousedown', 'pointerdown', 'keydown', 'keyup', 'keypress', 'submit'] as const) {\n host.addEventListener(evt, (e) => e.stopPropagation())\n }\n }\n\n private positionHost(x: number, y: number): void {\n if (!this.host) return\n // Use popover=\"manual\" to render in the top layer (above native popovers)\n this.host.setAttribute('popover', 'manual')\n try { this.host.showPopover() } catch { /* fallback to z-index */ }\n Object.assign(this.host.style, { position: 'fixed', zIndex: '2147483647', left: '-9999px', top: '0' })\n\n requestAnimationFrame(() => {\n if (!this.host) return\n const w = 340 + 20\n const h = this.host.querySelector('.popup')?.getBoundingClientRect().height ?? 300\n const vw = window.innerWidth\n const vh = window.innerHeight\n const left = Math.max(10, Math.min(x + 10, vw - w))\n const top = Math.max(10, Math.min(y + 10, vh - h - 10))\n Object.assign(this.host.style, { left: `${left}px`, top: `${top}px` })\n })\n }\n\n private boundOutside = (e: MouseEvent): void => {\n if (this.host && !this.host.contains(e.target as Node)) {\n this.destroy()\n }\n }\n\n private setupOutsideClick(): void {\n setTimeout(() => document.addEventListener('mousedown', this.boundOutside), 0)\n }\n\n destroy(): void {\n this.host?.remove()\n this.host = null\n this.shadow = null\n document.removeEventListener('mousedown', this.boundOutside)\n }\n}\n","import type { Annotation } from '../types'\n\ntype MarkerClickHandler = (annotation: Annotation) => void\n\ninterface MarkerEl {\n el: HTMLElement\n annotationId: string\n}\n\n/** Manages numbered annotation pins rendered directly on the page */\nexport class AnnotationMarkers {\n private container: HTMLElement\n private markers: Map<string, MarkerEl> = new Map()\n\n constructor(private readonly onClick: MarkerClickHandler) {\n // Fixed-position container over the page, pointer-events passthrough\n this.container = document.createElement('div')\n Object.assign(this.container.style, {\n position: 'fixed',\n inset: '0',\n pointerEvents: 'none',\n zIndex: '2147483645',\n })\n this.container.setAttribute('data-instruckt', 'markers')\n const root = document.getElementById('instruckt-root') ?? document.body\n root.appendChild(this.container)\n }\n\n /** Add or update a marker for an annotation */\n upsert(annotation: Annotation, index: number): void {\n const existing = this.markers.get(annotation.id)\n\n if (existing) {\n this.updateStyle(existing.el, annotation)\n return\n }\n\n const el = document.createElement('div')\n el.className = `ik-marker ${this.statusClass(annotation.status)}`\n el.textContent = String(index)\n el.title = annotation.comment.slice(0, 60)\n el.style.pointerEvents = 'all'\n\n // Position: annotation.x is % of viewport width, annotation.y is px from top (scroll-adjusted)\n // Convert back to viewport-relative for fixed positioning\n el.style.left = `${(annotation.x / 100) * window.innerWidth}px`\n el.style.top = `${annotation.y - window.scrollY}px`\n\n el.addEventListener('click', (e) => {\n e.stopPropagation()\n this.onClick(annotation)\n })\n\n this.container.appendChild(el)\n this.markers.set(annotation.id, { el, annotationId: annotation.id })\n }\n\n /** Update an existing marker after its annotation status changed */\n update(annotation: Annotation): void {\n const marker = this.markers.get(annotation.id)\n if (!marker) return\n this.updateStyle(marker.el, annotation)\n }\n\n private updateStyle(el: HTMLElement, annotation: Annotation): void {\n el.className = `ik-marker ${this.statusClass(annotation.status)}`\n el.title = annotation.comment.slice(0, 60)\n }\n\n private statusClass(status: string): string {\n if (status === 'resolved') return 'resolved'\n if (status === 'dismissed') return 'dismissed'\n if (status === 'acknowledged') return 'acknowledged'\n return ''\n }\n\n /** Reposition all markers (e.g. after scroll or resize) */\n reposition(annotations: Annotation[]): void {\n annotations.forEach(annotation => {\n const marker = this.markers.get(annotation.id)\n if (!marker) return\n marker.el.style.left = `${(annotation.x / 100) * window.innerWidth}px`\n marker.el.style.top = `${annotation.y - window.scrollY}px`\n })\n }\n\n remove(annotationId: string): void {\n const marker = this.markers.get(annotationId)\n if (!marker) return\n marker.el.remove()\n this.markers.delete(annotationId)\n }\n\n /** Show or hide all markers */\n setVisible(visible: boolean): void {\n this.container.style.display = visible ? '' : 'none'\n }\n\n /** Remove all markers without destroying the container */\n clear(): void {\n for (const { el } of this.markers.values()) {\n el.remove()\n }\n this.markers.clear()\n }\n\n destroy(): void {\n this.container.remove()\n this.markers.clear()\n }\n}\n","/**\n * CSS selector and element path generation.\n * Produces unique, grep-able selectors for any DOM element.\n */\n\n/** Build a unique CSS selector for an element */\nexport function getElementSelector(el: Element): string {\n if (el.id) {\n return `#${CSS.escape(el.id)}`\n }\n\n const path: string[] = []\n let current: Element | null = el\n\n while (current && current !== document.documentElement) {\n const tag = current.tagName.toLowerCase()\n const parent: Element | null = current.parentElement\n\n if (!parent) {\n path.unshift(tag)\n break\n }\n\n // Try unique class combo\n const classes = Array.from(current.classList)\n .filter(c => !c.match(/^(hover|focus|active|visited|is-|has-)/)) // skip state classes\n .slice(0, 3)\n\n if (classes.length > 0) {\n const classSelector = `${tag}.${classes.map(CSS.escape).join('.')}`\n const matches = parent.querySelectorAll(classSelector)\n if (matches.length === 1) {\n path.unshift(classSelector)\n break\n }\n }\n\n // Fall back to nth-child\n const siblings = Array.from(parent.children).filter((c: Element) => c.tagName === current!.tagName)\n if (siblings.length === 1) {\n path.unshift(tag)\n } else {\n const index = siblings.indexOf(current) + 1\n path.unshift(`${tag}:nth-of-type(${index})`)\n }\n\n current = parent\n }\n\n return path.join(' > ')\n}\n\n/** Short element identifier for markdown output (grep-friendly) */\nexport function getElementName(el: Element): string {\n const tag = el.tagName.toLowerCase()\n\n const wireModel = el.getAttribute('wire:model') || el.getAttribute('wire:click')\n if (wireModel) return `${tag}[wire:${wireModel.split('.')[0]}]`\n\n if (el.id) return `${tag}#${el.id}`\n\n const firstClass = el.classList[0]\n if (firstClass) return `${tag}.${firstClass}`\n\n return tag\n}\n\n/** Human-readable HTML-like label for the popup UI */\nexport function getElementLabel(el: Element): string {\n const tag = el.tagName.toLowerCase()\n const text = (el.textContent || '').trim().replace(/\\s+/g, ' ').slice(0, 40)\n\n // Build a short opening tag with key attributes\n const attrs: string[] = []\n if (el.id) attrs.push(`id=\"${el.id}\"`)\n const role = el.getAttribute('role')\n if (role) attrs.push(`role=\"${role}\"`)\n const wireAttr = el.getAttribute('wire:model') || el.getAttribute('wire:click')\n if (wireAttr) attrs.push(`wire:${el.hasAttribute('wire:model') ? 'model' : 'click'}=\"${wireAttr}\"`)\n\n const attrStr = attrs.length ? ' ' + attrs.join(' ') : ''\n const openTag = `<${tag}${attrStr}>`\n\n if (text) return `${openTag} ${text}`\n return openTag\n}\n\n/** Get nearby readable text for context */\nexport function getNearbyText(el: Element): string {\n const text = (el.textContent || '').trim().replace(/\\s+/g, ' ')\n return text.slice(0, 120)\n}\n\n/** CSS classes as a space-separated string, filtering noise */\nexport function getCssClasses(el: Element): string {\n return Array.from(el.classList)\n .filter(c => !c.match(/^(instruckt-)/)) // exclude our own classes\n .join(' ')\n}\n\n/** Get bounding box relative to the page */\nexport function getPageBoundingBox(el: Element): { x: number; y: number; width: number; height: number } {\n const rect = el.getBoundingClientRect()\n return {\n x: rect.left + window.scrollX,\n y: rect.top + window.scrollY,\n width: rect.width,\n height: rect.height,\n }\n}\n","import type { FrameworkContext } from '../types'\n\ndeclare global {\n interface Window {\n Livewire?: { find(id: string): unknown }\n }\n}\n\nexport function isAvailable(): boolean {\n return typeof window.Livewire !== 'undefined'\n}\n\n/** Walk up the DOM from el to find the nearest wire:id ancestor */\nexport function detect(el: Element): Element | null {\n let node: Element | null = el\n while (node && node !== document.documentElement) {\n if (node.getAttribute('wire:id')) return node\n node = node.parentElement\n }\n return null\n}\n\n/** Get Livewire component context for an element */\nexport function getContext(el: Element): FrameworkContext | null {\n if (!isAvailable()) return null\n\n const wireEl = detect(el)\n if (!wireEl) return null\n\n const wireId = wireEl.getAttribute('wire:id')!\n\n // In Livewire v3, the component name lives in the wire:snapshot attribute\n let componentName = 'Unknown'\n const snapshotAttr = wireEl.getAttribute('wire:snapshot')\n if (snapshotAttr) {\n try {\n const snapshot = JSON.parse(snapshotAttr)\n componentName = snapshot?.memo?.name ?? 'Unknown'\n } catch {\n // malformed snapshot\n }\n }\n\n return {\n framework: 'livewire',\n component: componentName,\n wire_id: wireId,\n }\n}\n","import type { FrameworkContext } from '../types'\n\ninterface VueInstance {\n $options?: { name?: string; __name?: string }\n type?: { name?: string; __name?: string }\n uid?: number\n props?: Record<string, unknown>\n setupState?: Record<string, unknown>\n}\n\ninterface VueElement extends Element {\n __vue__?: VueInstance\n __vueParentComponent?: VueInstance\n _vei?: unknown\n}\n\nexport function isAvailable(): boolean {\n // Vue 3: mounts with data-v-app attribute; Vue 2: exposes global Vue constructor\n return !!(document.querySelector('[data-v-app]') || (window as unknown as Record<string, unknown>)['Vue'])\n}\n\n/** Walk up the DOM to find the nearest Vue component */\nexport function detect(el: Element): VueInstance | null {\n let node: VueElement | null = el as VueElement\n while (node && node !== document.documentElement) {\n const instance = node.__vueParentComponent ?? node.__vue__\n if (instance) return instance\n node = node.parentElement as VueElement | null\n }\n return null\n}\n\n/** Get Vue component context for an element */\nexport function getContext(el: Element): FrameworkContext | null {\n const instance = detect(el)\n if (!instance) return null\n\n // Support Vue 2 ($options.name) and Vue 3 (type.name or type.__name)\n const name =\n instance.$options?.name ??\n instance.$options?.__name ??\n instance.type?.name ??\n instance.type?.__name ??\n 'Anonymous'\n\n const data: Record<string, unknown> = {}\n\n // Vue 3 props\n if (instance.props) {\n Object.assign(data, instance.props)\n }\n\n // Vue 3 setup state (public reactive refs)\n if (instance.setupState) {\n for (const [key, value] of Object.entries(instance.setupState)) {\n if (!key.startsWith('_') && typeof value !== 'function') {\n try {\n data[key] = JSON.parse(JSON.stringify(value))\n } catch {\n data[key] = String(value)\n }\n }\n }\n }\n\n return {\n framework: 'vue',\n component: name,\n component_uid: instance.uid !== undefined ? String(instance.uid) : undefined,\n data,\n }\n}\n","import type { FrameworkContext } from '../types'\n\ninterface SvelteMeta {\n loc?: { file?: string }\n ctx?: unknown[]\n}\n\ninterface SvelteElement extends Element {\n __svelte_meta?: SvelteMeta\n __svelte?: unknown\n}\n\n/** Walk up DOM to find nearest Svelte component element */\nexport function detect(el: Element): SvelteMeta | null {\n let node: SvelteElement | null = el as SvelteElement\n while (node && node !== document.documentElement) {\n if (node.__svelte_meta) return node.__svelte_meta\n node = node.parentElement as SvelteElement | null\n }\n return null\n}\n\n/** Get Svelte component context for an element */\nexport function getContext(el: Element): FrameworkContext | null {\n const meta = detect(el)\n if (!meta) return null\n\n // Extract component name from file path e.g. \"/src/components/Button.svelte\" → \"Button\"\n const filePath = meta.loc?.file ?? ''\n const component = filePath\n ? filePath.split('/').pop()?.replace(/\\.svelte$/, '') ?? 'Unknown'\n : 'Unknown'\n\n return {\n framework: 'svelte',\n component,\n data: filePath ? { file: filePath } : undefined,\n }\n}\n","import type { FrameworkContext } from '../types'\n\ninterface ReactFiber {\n type: unknown\n memoizedProps: Record<string, unknown> | null\n pendingProps: Record<string, unknown> | null\n return: ReactFiber | null\n key: string | null\n}\n\ninterface ReactElement extends Element {\n [key: string]: unknown\n}\n\nfunction getFiberKey(el: Element): string | null {\n for (const key of Object.keys(el)) {\n if (key.startsWith('__reactFiber$') || key.startsWith('__reactInternalInstance$')) {\n return key\n }\n }\n return null\n}\n\nfunction getComponentName(fiber: ReactFiber): string {\n let node: ReactFiber | null = fiber\n while (node) {\n const { type } = node\n if (typeof type === 'function' && (type as { name?: string }).name) {\n const name = (type as { name: string }).name\n // Skip React internals (start with lowercase = intrinsic HTML element function)\n if (name[0] === name[0].toUpperCase() && name.length > 1) return name\n }\n if (typeof type === 'object' && type !== null && (type as { displayName?: string }).displayName) {\n return (type as { displayName: string }).displayName\n }\n node = node.return\n }\n return 'Component'\n}\n\nfunction getProps(fiber: ReactFiber): Record<string, unknown> {\n const props = fiber.memoizedProps ?? fiber.pendingProps ?? {}\n const result: Record<string, unknown> = {}\n for (const [k, v] of Object.entries(props)) {\n if (k === 'children' || typeof v === 'function') continue\n try {\n result[k] = JSON.parse(JSON.stringify(v))\n } catch {\n result[k] = String(v)\n }\n }\n return result\n}\n\nexport function isAvailable(): boolean {\n // React attaches fiber data to DOM nodes with __reactFiber$ prefix\n const root = document.getElementById('root') ?? document.getElementById('app') ?? document.body.firstElementChild\n if (!root) return false\n return getFiberKey(root) !== null\n}\n\nexport function getContext(el: Element): FrameworkContext | null {\n let node: Element | null = el\n while (node && node !== document.documentElement) {\n const key = getFiberKey(node)\n if (key) {\n const fiber = (node as ReactElement)[key] as ReactFiber\n if (fiber) {\n const component = getComponentName(fiber)\n const data = getProps(fiber)\n return { framework: 'react', component, data }\n }\n }\n node = node.parentElement\n }\n return null\n}\n","import type { Annotation, InstrucktConfig, PendingAnnotation } from './types'\nimport { InstrucktApi } from './api'\nimport type { AnnotationPayload } from './api'\nimport { Toolbar } from './ui/toolbar'\nimport { ElementHighlight } from './ui/highlight'\nimport { AnnotationPopup } from './ui/popup'\nimport { AnnotationMarkers } from './ui/markers'\nimport { injectGlobalStyles } from './ui/styles'\nimport { getElementSelector, getElementName, getElementLabel, getNearbyText, getCssClasses, getPageBoundingBox } from './selector'\nimport * as livewireAdapter from './adapters/livewire'\nimport * as vueAdapter from './adapters/vue'\nimport * as svelteAdapter from './adapters/svelte'\nimport * as reactAdapter from './adapters/react'\n\n// Re-export for api.ts consumers\nexport type { AnnotationPayload }\n\n/** Normalize URL to pathname for page-scoping (ignore query/hash) */\nfunction pageKey(): string {\n return window.location.pathname\n}\n\nexport class Instruckt {\n private config: Required<Pick<InstrucktConfig, 'endpoint' | 'theme' | 'position'>> & InstrucktConfig\n private api: InstrucktApi\n private toolbar: Toolbar | null = null\n private highlight: ElementHighlight | null = null\n private popup: AnnotationPopup | null = null\n private markers: AnnotationMarkers | null = null\n private annotations: Annotation[] = []\n private isAnnotating = false\n private isFrozen = false\n private frozenStyleEl: HTMLStyleElement | null = null\n private frozenPopovers: { el: HTMLElement; original: string }[] = []\n private rafId: number | null = null\n private pendingMouseTarget: Element | null = null\n private highlightLocked = false\n private pollTimer: ReturnType<typeof setInterval> | null = null\n private boundKeydown: (e: KeyboardEvent) => void\n private boundReposition = (): void => {\n this.markers?.reposition(this.annotations)\n }\n\n constructor(config: InstrucktConfig) {\n this.config = {\n adapters: ['livewire', 'vue', 'svelte', 'react'],\n theme: 'auto',\n position: 'bottom-right',\n ...config,\n }\n this.api = new InstrucktApi(config.endpoint)\n this.boundKeydown = this.onKeydown.bind(this)\n this.init()\n }\n\n private init(): void {\n injectGlobalStyles()\n\n if (this.config.theme !== 'auto') {\n document.documentElement.setAttribute('data-instruckt-theme', this.config.theme)\n }\n\n this.toolbar = new Toolbar(this.config.position, {\n onToggleAnnotate: (active) => {\n this.setAnnotating(active)\n },\n onFreezeAnimations: (frozen) => {\n this.setFrozen(frozen)\n },\n onCopy: () => this.copyToClipboard(true),\n onClearPage: () => this.clearPage(),\n onClearAll: () => this.clearEverything(),\n onMinimize: (min) => this.onMinimize(min),\n })\n\n this.highlight = new ElementHighlight()\n this.popup = new AnnotationPopup()\n this.markers = new AnnotationMarkers((annotation) => this.onMarkerClick(annotation))\n\n document.addEventListener('keydown', this.boundKeydown)\n window.addEventListener('scroll', this.boundReposition, { passive: true })\n window.addEventListener('resize', this.boundReposition, { passive: true })\n\n // Survive SPA navigation across frameworks\n document.addEventListener('livewire:navigated', () => this.reattach())\n document.addEventListener('inertia:navigate', () => this.syncMarkers())\n window.addEventListener('popstate', () => {\n setTimeout(() => this.reattach(), 0)\n })\n\n // Load persisted annotations from the backend\n this.loadAnnotations()\n // Poll for changes (e.g. agent resolved via MCP)\n this.pollTimer = setInterval(() => this.pollForChanges(), 3000)\n\n this.syncMarkers()\n }\n\n private makeToolbarCallbacks() {\n return {\n onToggleAnnotate: (active: boolean) => {\n this.setAnnotating(active)\n },\n onFreezeAnimations: (frozen: boolean) => {\n this.setFrozen(frozen)\n },\n onCopy: () => this.copyToClipboard(true),\n onClearPage: () => this.clearPage(),\n onClearAll: () => this.clearEverything(),\n onMinimize: (min: boolean) => this.onMinimize(min),\n }\n }\n\n private reattach(): void {\n const wasAnnotating = this.isAnnotating\n const wasFrozen = this.isFrozen\n const wasMinimized = this.toolbar?.isMinimized() ?? false\n\n // Detach current listeners before rebuilding\n if (this.isAnnotating) this.detachAnnotateListeners()\n if (this.isFrozen) this.setFrozen(false)\n this.isAnnotating = false\n this.isFrozen = false\n\n // Remove any stale instruckt DOM (Livewire caches and restores old HTML on back nav)\n document.querySelectorAll('[data-instruckt]').forEach(el => el.remove())\n\n // Rebuild everything fresh\n this.toolbar = new Toolbar(this.config.position, this.makeToolbarCallbacks())\n if (wasMinimized) this.toolbar.minimize()\n\n this.markers = new AnnotationMarkers((annotation) => this.onMarkerClick(annotation))\n this.highlight = new ElementHighlight()\n\n if (wasMinimized) this.markers.setVisible(false)\n\n // Re-inject global styles (Livewire may have swapped <head> content)\n const existing = document.getElementById('instruckt-global')\n if (existing) existing.remove()\n injectGlobalStyles()\n\n this.syncMarkers()\n\n // Restore active modes\n if (wasAnnotating && !wasMinimized) this.setAnnotating(true)\n }\n\n // ── Minimize ────────────────────────────────────────────────────\n\n private onMinimize(minimized: boolean): void {\n if (minimized) {\n // Deactivate everything when minimized\n if (this.isAnnotating) this.setAnnotating(false)\n if (this.isFrozen) this.setFrozen(false)\n this.toolbar?.setAnnotateActive(false)\n this.toolbar?.setFreezeActive(false)\n this.markers?.setVisible(false)\n this.popup?.destroy()\n } else {\n // Show markers again when restored\n this.markers?.setVisible(true)\n }\n }\n\n // ── Persistence ─────────────────────────────────────────────────\n\n private static STORAGE_KEY = 'instruckt:annotations'\n\n private async loadAnnotations(): Promise<void> {\n // Always load localStorage first as baseline\n this.loadFromStorage()\n\n try {\n const remote = await this.api.getAnnotations()\n if (remote.length > 0) {\n // Merge: remote is source of truth, but keep any local-only annotations\n const remoteIds = new Set(remote.map(a => a.id))\n const localOnly = this.annotations.filter(a => !remoteIds.has(a.id))\n this.annotations = [...remote, ...localOnly]\n this.saveToStorage()\n }\n } catch {\n // No backend — localStorage already loaded above\n }\n this.syncMarkers()\n }\n\n private saveToStorage(): void {\n try {\n localStorage.setItem(Instruckt.STORAGE_KEY, JSON.stringify(this.annotations))\n } catch { /* storage full or unavailable */ }\n }\n\n private loadFromStorage(): void {\n try {\n const raw = localStorage.getItem(Instruckt.STORAGE_KEY)\n if (raw) this.annotations = JSON.parse(raw)\n } catch { /* corrupt or unavailable */ }\n }\n\n /** Poll API for status changes (e.g. agent resolved via MCP) */\n private async pollForChanges(): Promise<void> {\n try {\n const remote = await this.api.getAnnotations()\n let changed = false\n for (const r of remote) {\n const local = this.annotations.find(a => a.id === r.id)\n if (local && local.status !== r.status) {\n local.status = r.status\n local.resolvedAt = r.resolvedAt\n local.resolvedBy = r.resolvedBy\n changed = true\n }\n }\n if (changed) {\n this.saveToStorage()\n this.syncMarkers()\n }\n } catch { /* no backend or network error — skip */ }\n }\n\n // ── Page-scoped markers ─────────────────────────────────────────\n\n private syncMarkers(): void {\n this.markers?.clear()\n const current = pageKey()\n let idx = 0\n for (const a of this.annotations) {\n if (a.status === 'resolved' || a.status === 'dismissed') continue\n if (this.annotationPageKey(a) === current) {\n idx++\n this.markers?.upsert(a, idx)\n }\n }\n this.toolbar?.setAnnotationCount(this.pageAnnotations().length)\n this.toolbar?.setTotalCount(this.totalActiveCount())\n }\n\n private annotationPageKey(a: Annotation): string {\n try {\n return new URL(a.url).pathname\n } catch {\n return a.url\n }\n }\n\n private pageAnnotations(): Annotation[] {\n const current = pageKey()\n return this.annotations.filter(a =>\n this.annotationPageKey(a) === current &&\n a.status !== 'resolved' && a.status !== 'dismissed'\n )\n }\n\n private totalActiveCount(): number {\n return this.annotations.filter(a => a.status !== 'resolved' && a.status !== 'dismissed').length\n }\n\n // ── Annotate mode ─────────────────────────────────────────────\n\n private setAnnotating(active: boolean): void {\n this.isAnnotating = active\n this.toolbar?.setAnnotateActive(active)\n if (active) {\n this.attachAnnotateListeners()\n } else {\n this.detachAnnotateListeners()\n this.highlight?.hide()\n if (this.rafId !== null) { cancelAnimationFrame(this.rafId); this.rafId = null }\n }\n // When frozen, toggle pointer-events based on annotate state\n this.updateFreezeStyles()\n }\n\n // ── Freeze mode ──────────────────────────────────────────────\n\n private setFrozen(frozen: boolean): void {\n this.isFrozen = frozen\n this.toolbar?.setFreezeActive(frozen)\n if (frozen) {\n this.updateFreezeStyles()\n this.freezePopovers()\n // Use window (not document) so we intercept before Livewire/Alpine handlers\n // on document. Capture on window fires before capture on document.\n for (const evt of this.freezeBlockEvents) {\n window.addEventListener(evt, this.boundFreezeClick, true)\n }\n window.addEventListener('submit', this.boundFreezeSubmit, true)\n // Block events that close dropdowns/popovers (window capture to beat frameworks)\n for (const evt of this.freezePassiveEvents) {\n window.addEventListener(evt, this.boundFreezePassive, true)\n }\n } else {\n this.frozenStyleEl?.remove()\n this.frozenStyleEl = null\n this.unfreezePopovers()\n for (const evt of this.freezeBlockEvents) {\n window.removeEventListener(evt, this.boundFreezeClick, true)\n }\n window.removeEventListener('submit', this.boundFreezeSubmit, true)\n for (const evt of this.freezePassiveEvents) {\n window.removeEventListener(evt, this.boundFreezePassive, true)\n }\n }\n }\n\n /** Pull open popovers out of the top layer so the rest of the page is clickable */\n private freezePopovers(): void {\n this.frozenPopovers = []\n const openSelector = ':popover-open, .\\\\:popover-open'\n document.querySelectorAll('[popover]').forEach((el) => {\n const htmlEl = el as HTMLElement\n const val = htmlEl.getAttribute('popover') ?? ''\n let isOpen = false\n try { isOpen = htmlEl.matches(openSelector) } catch {\n try { isOpen = htmlEl.matches('.\\\\:popover-open') } catch { /* ignore */ }\n }\n if (!isOpen) return\n // Save position before removing popover attribute\n const rect = htmlEl.getBoundingClientRect()\n this.frozenPopovers.push({ el: htmlEl, original: val })\n // Remove popover attribute — pulls element out of top layer\n htmlEl.removeAttribute('popover')\n // Keep it visible with inline styles\n htmlEl.style.setProperty('display', 'block', 'important')\n htmlEl.style.setProperty('position', 'fixed', 'important')\n htmlEl.style.setProperty('z-index', '2147483644', 'important')\n htmlEl.style.setProperty('top', `${rect.top}px`, 'important')\n htmlEl.style.setProperty('left', `${rect.left}px`, 'important')\n htmlEl.style.setProperty('width', `${rect.width}px`, 'important')\n // Add the polyfill class so Flux thinks it's still open\n htmlEl.classList.add(':popover-open')\n })\n }\n\n /** Restore popover attributes */\n private unfreezePopovers(): void {\n for (const { el, original } of this.frozenPopovers) {\n // Remove inline overrides\n for (const prop of ['display', 'position', 'z-index', 'top', 'left', 'width']) {\n el.style.removeProperty(prop)\n }\n el.classList.remove(':popover-open')\n el.setAttribute('popover', original || 'auto')\n }\n this.frozenPopovers = []\n }\n\n private freezeBlockEvents = ['click', 'mousedown', 'pointerdown', 'pointerup', 'mouseup', 'touchstart', 'touchend', 'auxclick'] as const\n private freezePassiveEvents = ['focusin', 'focusout', 'blur', 'pointerleave', 'mouseleave', 'mouseout'] as const\n\n /** Update freeze CSS — pointer-events only blocked when NOT annotating */\n private updateFreezeStyles(): void {\n if (!this.isFrozen) return\n this.frozenStyleEl?.remove()\n this.frozenStyleEl = document.createElement('style')\n this.frozenStyleEl.id = 'instruckt-freeze'\n const pointerBlock = this.isAnnotating ? '' : `\n a[href], a[wire\\\\:navigate], [wire\\\\:click], [wire\\\\:navigate],\n [x-on\\\\:click], [@click], [v-on\\\\:click], [onclick],\n button, input[type=\"submit\"], select, [role=\"button\"], [role=\"link\"],\n [tabindex] {\n pointer-events: none !important;\n cursor: not-allowed !important;\n }\n `\n this.frozenStyleEl.textContent = `\n *, *::before, *::after {\n animation-play-state: paused !important;\n transition: none !important;\n }\n video { filter: none !important; }\n ${pointerBlock}\n `\n document.head.appendChild(this.frozenStyleEl)\n }\n\n /** Block interactions on the page when frozen (except instruckt UI) */\n private boundFreezeClick = (e: Event): void => {\n if (this.isInstruckt(e.target)) return\n // When annotating, only let 'click' through (annotate handler needs it).\n // Always block mousedown/pointerdown/touchstart to prevent framework\n // handlers (Alpine @click.outside, Livewire wire:navigate) from firing.\n if (this.isAnnotating && e.type === 'click') return\n e.preventDefault()\n e.stopPropagation()\n e.stopImmediatePropagation()\n }\n\n private boundFreezeSubmit = (e: Event): void => {\n e.preventDefault()\n e.stopPropagation()\n e.stopImmediatePropagation()\n }\n\n /** Block focus/hover events that JS dropdowns use to auto-close.\n * Block ALL of these — even on instruckt elements — because frameworks\n * like Flux check if focusin target is contained in the popover and\n * close it if it's not (e.g. focus moved to our popup textarea). */\n private boundFreezePassive = (e: Event): void => {\n e.stopPropagation()\n e.stopImmediatePropagation()\n }\n\n // ── Event listeners ───────────────────────────────────────────\n\n private boundMouseMove = (e: MouseEvent): void => {\n if (this.highlightLocked) return\n this.pendingMouseTarget = e.target as Element\n if (this.rafId === null) {\n this.rafId = requestAnimationFrame(() => {\n this.rafId = null\n if (this.highlightLocked) return\n if (this.pendingMouseTarget && !this.isInstruckt(this.pendingMouseTarget)) {\n this.highlight?.show(this.pendingMouseTarget)\n } else {\n this.highlight?.hide()\n }\n })\n }\n }\n\n private boundMouseLeave = (): void => {\n if (this.highlightLocked) return\n this.highlight?.hide()\n }\n\n /** Block mousedown/pointerdown in annotation mode so SPA frameworks can't navigate */\n private boundAnnotateBlock = (e: Event): void => {\n if (this.isInstruckt(e.target)) return\n e.preventDefault()\n e.stopPropagation()\n e.stopImmediatePropagation()\n }\n\n private boundClick = (e: MouseEvent): void => {\n const target = e.target as Element\n if (this.isInstruckt(target)) return\n // Always block clicks in annotation mode — prevents SPA navigation\n // from changing the page before the user can finish their note.\n e.preventDefault()\n e.stopPropagation()\n e.stopImmediatePropagation()\n\n const selectedText = window.getSelection()?.toString().trim() || undefined\n const elementPath = getElementSelector(target)\n const elementName = getElementName(target)\n const elementLabel = getElementLabel(target)\n const cssClasses = getCssClasses(target)\n const nearbyText = getNearbyText(target) || undefined\n const boundingBox = getPageBoundingBox(target)\n const framework = this.detectFramework(target) ?? undefined\n\n const pending: PendingAnnotation = {\n element: target,\n elementPath,\n elementName,\n elementLabel,\n cssClasses,\n boundingBox,\n x: e.clientX,\n y: e.clientY,\n selectedText,\n nearbyText,\n framework,\n }\n\n this.highlight?.show(target)\n this.highlightLocked = true\n\n this.popup?.showNew(pending, {\n onSubmit: (result) => {\n this.highlightLocked = false\n this.highlight?.hide()\n this.submitAnnotation(pending, result.comment)\n },\n onCancel: () => {\n this.highlightLocked = false\n this.highlight?.hide()\n },\n })\n }\n\n private attachAnnotateListeners(): void {\n document.addEventListener('mousemove', this.boundMouseMove)\n document.addEventListener('mouseleave', this.boundMouseLeave)\n // Block mousedown/pointerdown first — SPA frameworks (Livewire wire:navigate,\n // Inertia) intercept these before click fires\n for (const evt of ['mousedown', 'pointerdown'] as const) {\n window.addEventListener(evt, this.boundAnnotateBlock, true)\n }\n // Use window capture to fire before framework handlers on document\n window.addEventListener('click', this.boundClick, true)\n }\n\n private detachAnnotateListeners(): void {\n document.removeEventListener('mousemove', this.boundMouseMove)\n document.removeEventListener('mouseleave', this.boundMouseLeave)\n for (const evt of ['mousedown', 'pointerdown'] as const) {\n window.removeEventListener(evt, this.boundAnnotateBlock, true)\n }\n window.removeEventListener('click', this.boundClick, true)\n }\n\n private isInstruckt(el: EventTarget | null): boolean {\n if (!el || !(el instanceof Element)) return false\n return el.closest('[data-instruckt]') !== null\n }\n\n // ── Framework detection ───────────────────────────────────────\n\n private detectFramework(el: Element) {\n const adapters = this.config.adapters ?? []\n if (adapters.includes('livewire')) {\n const ctx = livewireAdapter.getContext(el)\n if (ctx) return ctx\n }\n if (adapters.includes('vue')) {\n const ctx = vueAdapter.getContext(el)\n if (ctx) return ctx\n }\n if (adapters.includes('svelte')) {\n const ctx = svelteAdapter.getContext(el)\n if (ctx) return ctx\n }\n if (adapters.includes('react')) {\n const ctx = reactAdapter.getContext(el)\n if (ctx) return ctx\n }\n return null\n }\n\n // ── Submit ────────────────────────────────────────────────────\n\n private async submitAnnotation(pending: PendingAnnotation, comment: string): Promise<void> {\n const payload: AnnotationPayload = {\n x: (pending.x / window.innerWidth) * 100,\n y: pending.y + window.scrollY,\n comment,\n element: pending.elementName,\n elementPath: pending.elementPath,\n cssClasses: pending.cssClasses,\n boundingBox: pending.boundingBox,\n selectedText: pending.selectedText,\n nearbyText: pending.nearbyText,\n intent: 'fix',\n severity: 'important',\n framework: pending.framework,\n url: window.location.href,\n }\n\n let annotation: Annotation\n try {\n annotation = await this.api.addAnnotation(payload)\n } catch {\n // No backend — create a local-only annotation\n annotation = {\n ...payload,\n id: crypto.randomUUID(),\n status: 'pending',\n thread: [],\n createdAt: new Date().toISOString(),\n }\n }\n this.annotations.push(annotation)\n this.saveToStorage()\n this.syncMarkers()\n this.config.onAnnotationAdd?.(annotation)\n this.copyAnnotations()\n }\n\n // ── Marker click — edit or delete ─────────────────────────────\n\n private onMarkerClick(annotation: Annotation): void {\n this.popup?.showEdit(annotation, {\n onSave: async (a, newComment) => {\n try {\n const updated = await this.api.updateAnnotation(a.id, { comment: newComment })\n this.onAnnotationUpdated(updated)\n } catch {\n // No backend — update locally\n this.onAnnotationUpdated({ ...a, comment: newComment, updatedAt: new Date().toISOString() })\n }\n },\n onDelete: async (a) => {\n try {\n await this.api.updateAnnotation(a.id, { status: 'dismissed' })\n } catch { /* no backend — just remove locally */ }\n this.removeAnnotation(a.id)\n },\n })\n }\n\n private onAnnotationUpdated(updated: Annotation): void {\n const idx = this.annotations.findIndex(a => a.id === updated.id)\n if (idx >= 0) {\n this.annotations[idx] = updated\n }\n this.saveToStorage()\n this.syncMarkers()\n }\n\n private removeAnnotation(id: string): void {\n this.annotations = this.annotations.filter(a => a.id !== id)\n this.saveToStorage()\n this.syncMarkers()\n }\n\n // ── Clear ───────────────────────────────────────────────────────\n\n private async clearPage(): Promise<void> {\n const page = this.pageAnnotations()\n for (const a of page) {\n try {\n await this.api.updateAnnotation(a.id, { status: 'dismissed' })\n } catch { /* best effort */ }\n }\n this.annotations = this.annotations.filter(a => !page.includes(a))\n this.saveToStorage()\n this.syncMarkers()\n }\n\n private async clearEverything(): Promise<void> {\n const active = this.annotations.filter(a => a.status !== 'resolved' && a.status !== 'dismissed')\n for (const a of active) {\n try {\n await this.api.updateAnnotation(a.id, { status: 'dismissed' })\n } catch { /* best effort */ }\n }\n this.annotations = []\n this.saveToStorage()\n this.syncMarkers()\n }\n\n // ── Keyboard ──────────────────────────────────────────────────\n\n private onKeydown(e: KeyboardEvent): void {\n if (this.toolbar?.isMinimized()) return\n const target = e.target as HTMLElement\n if (['INPUT', 'TEXTAREA', 'SELECT'].includes(target.tagName)) return\n if (target.closest('[contenteditable=\"true\"]')) return\n // Shadow DOM retargets e.target to the host element — check if a popup is open\n if (this.isInstruckt(target)) return\n\n if (e.key === 'a' && !e.metaKey && !e.ctrlKey && !e.altKey) {\n this.setAnnotating(!this.isAnnotating)\n }\n if (e.key === 'f' && !e.metaKey && !e.ctrlKey && !e.altKey) {\n this.setFrozen(!this.isFrozen)\n }\n if (e.key === 'x' && !e.metaKey && !e.ctrlKey && !e.altKey) {\n this.clearPage()\n }\n if (e.key === 'Escape') {\n if (this.isAnnotating) this.setAnnotating(false)\n if (this.isFrozen) this.setFrozen(false)\n }\n }\n\n // ── Copy / export ─────────────────────────────────────────────\n\n /** Auto-copy on annotation submit — only in secure contexts to avoid focus side-effects */\n private copyAnnotations(): void {\n this.copyToClipboard(false)\n }\n\n /** Copy to clipboard. With fallback=true, uses execCommand for non-secure contexts (user-initiated only). */\n private copyToClipboard(fallback: boolean): void {\n const md = this.exportMarkdown()\n if (window.isSecureContext) {\n navigator.clipboard.writeText(md).catch(() => { /* unavailable */ })\n } else if (fallback) {\n try {\n const el = document.createElement('textarea')\n el.value = md\n el.style.cssText = 'position:fixed;left:-9999px'\n document.body.appendChild(el)\n el.select()\n document.execCommand('copy')\n el.remove()\n } catch { /* unavailable */ }\n }\n }\n\n exportMarkdown(): string {\n const pending = this.annotations.filter(a => a.status !== 'resolved' && a.status !== 'dismissed')\n if (pending.length === 0) {\n return `# UI Feedback\\n\\nNo open annotations.`\n }\n\n // Group by page\n const byPage = new Map<string, Annotation[]>()\n for (const a of pending) {\n const key = this.annotationPageKey(a)\n if (!byPage.has(key)) byPage.set(key, [])\n byPage.get(key)!.push(a)\n }\n\n const multiPage = byPage.size > 1\n const lines: string[] = []\n\n if (multiPage) {\n lines.push(`# UI Feedback`)\n lines.push('')\n }\n\n for (const [path, annotations] of byPage) {\n if (multiPage) {\n lines.push(`## ${path}`)\n } else {\n lines.push(`# UI Feedback: ${path}`)\n }\n lines.push('')\n\n const hPrefix = multiPage ? '###' : '##'\n\n annotations.forEach((a, i) => {\n // Feedback-first heading with element context\n const componentSuffix = a.framework?.component ? ` in \\`${a.framework.component}\\`` : ''\n lines.push(`${hPrefix} ${i + 1}. ${a.comment}`)\n lines.push(`- Element: \\`${a.element}\\`${componentSuffix}`)\n\n // File path if available (e.g. Svelte)\n if (a.framework?.data?.file) {\n lines.push(`- File: \\`${a.framework.data.file}\\``)\n }\n\n if (a.cssClasses) {\n lines.push(`- Classes: \\`${a.cssClasses}\\``)\n }\n if (a.selectedText) {\n lines.push(`- Text: \"${a.selectedText}\"`)\n } else if (a.nearbyText) {\n lines.push(`- Text: \"${a.nearbyText.slice(0, 100)}\"`)\n }\n lines.push('')\n })\n }\n\n return lines.join('\\n').trim()\n }\n\n // ── Public API ────────────────────────────────────────────────\n\n getAnnotations(): Annotation[] { return [...this.annotations] }\n\n destroy(): void {\n this.setAnnotating(false)\n this.setFrozen(false)\n document.removeEventListener('keydown', this.boundKeydown)\n window.removeEventListener('scroll', this.boundReposition)\n window.removeEventListener('resize', this.boundReposition)\n this.toolbar?.destroy()\n this.highlight?.destroy()\n this.popup?.destroy()\n this.markers?.destroy()\n if (this.rafId !== null) cancelAnimationFrame(this.rafId)\n if (this.pollTimer !== null) clearInterval(this.pollTimer)\n }\n}\n"],"mappings":"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AAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAsK9B,IAAM;AAAA;AAAA,EAAsB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAA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","names":["_a","detect","getContext","detect","getContext","getContext","_a","e","getContext"]}
|
|
1
|
+
{"version":3,"sources":["../src/index.ts","../src/api.ts","../src/ui/styles.ts","../src/ui/toolbar.ts","../src/ui/highlight.ts","../node_modules/html-to-image/src/util.ts","../node_modules/html-to-image/src/clone-pseudos.ts","../node_modules/html-to-image/src/mimes.ts","../node_modules/html-to-image/src/dataurl.ts","../node_modules/html-to-image/src/clone-node.ts","../node_modules/html-to-image/src/embed-resources.ts","../node_modules/html-to-image/src/embed-images.ts","../node_modules/html-to-image/src/apply-style.ts","../node_modules/html-to-image/src/embed-webfonts.ts","../node_modules/html-to-image/src/index.ts","../src/ui/screenshot.ts","../src/ui/popup.ts","../src/ui/markers.ts","../src/selector.ts","../src/adapters/livewire.ts","../src/adapters/vue.ts","../src/adapters/svelte.ts","../src/adapters/react.ts","../src/instruckt.ts"],"sourcesContent":["import { Instruckt } from './instruckt'\nimport type { InstrucktConfig, Annotation, AnnotationIntent, AnnotationSeverity, AnnotationStatus, FrameworkContext } from './types'\nimport type { AnnotationPayload } from './api'\n\nexport { Instruckt }\nexport type { InstrucktConfig, Annotation, AnnotationPayload, AnnotationIntent, AnnotationSeverity, AnnotationStatus, FrameworkContext }\n\n/**\n * Initialize instruckt.\n *\n * @example\n * instruckt.init({ endpoint: '/instruckt' })\n *\n * @example CDN\n * <script src=\"instruckt.iife.js\"></script>\n * <script>Instruckt.init({ endpoint: '/instruckt' })</script>\n */\nexport function init(config: InstrucktConfig): Instruckt {\n return new Instruckt(config)\n}\n","import type { Annotation } from './types'\n\n/** Read Laravel's XSRF-TOKEN cookie for CSRF protection */\nfunction getCsrfToken(): string {\n const match = document.cookie.match(/(?:^|;\\s*)XSRF-TOKEN=([^;]+)/)\n return match ? decodeURIComponent(match[1]) : ''\n}\n\nfunction headers(): Record<string, string> {\n const h: Record<string, string> = {\n 'Content-Type': 'application/json',\n Accept: 'application/json',\n 'X-Requested-With': 'XMLHttpRequest',\n }\n const csrf = getCsrfToken()\n if (csrf) h['X-XSRF-TOKEN'] = csrf\n return h\n}\n\n/** Convert snake_case API response to camelCase for JS types */\nexport function toCamelCase(obj: Record<string, unknown>): Record<string, unknown> {\n const out: Record<string, unknown> = {}\n for (const [k, v] of Object.entries(obj)) {\n const camel = k.replace(/_([a-z])/g, (_, c) => c.toUpperCase())\n out[camel] = Array.isArray(v)\n ? v.map(item => (item && typeof item === 'object' && !Array.isArray(item)) ? toCamelCase(item as Record<string, unknown>) : item)\n : (v && typeof v === 'object' && !Array.isArray(v)) ? toCamelCase(v as Record<string, unknown>) : v\n }\n return out\n}\n\n/** Convert camelCase JS payload to snake_case for Laravel API */\nfunction toSnake(obj: Record<string, unknown>): Record<string, unknown> {\n const out: Record<string, unknown> = {}\n for (const [k, v] of Object.entries(obj)) {\n const snake = k.replace(/[A-Z]/g, c => `_${c.toLowerCase()}`)\n out[snake] = (v && typeof v === 'object' && !Array.isArray(v)) ? toSnake(v as Record<string, unknown>) : v\n }\n return out\n}\n\nexport type AnnotationPayload = Omit<\n Annotation,\n 'id' | 'status' | 'thread' | 'createdAt'\n>\n\nexport class InstrucktApi {\n constructor(private readonly endpoint: string) {}\n\n async getAnnotations(): Promise<Annotation[]> {\n const res = await fetch(`${this.endpoint}/annotations`, {\n headers: headers(),\n })\n if (!res.ok) throw new Error(`instruckt: failed to load annotations (${res.status})`)\n const raw: Record<string, unknown>[] = await res.json()\n return raw.map(r => toCamelCase(r) as unknown as Annotation)\n }\n\n async addAnnotation(data: AnnotationPayload): Promise<Annotation> {\n const res = await fetch(`${this.endpoint}/annotations`, {\n method: 'POST',\n headers: headers(),\n body: JSON.stringify(toSnake(data as unknown as Record<string, unknown>)),\n })\n if (!res.ok) throw new Error(`instruckt: failed to add annotation (${res.status})`)\n return toCamelCase(await res.json()) as unknown as Annotation\n }\n\n async updateAnnotation(\n annotationId: string,\n data: Partial<Pick<Annotation, 'status' | 'comment'>>,\n ): Promise<Annotation> {\n const res = await fetch(`${this.endpoint}/annotations/${annotationId}`, {\n method: 'PATCH',\n headers: headers(),\n body: JSON.stringify(toSnake(data as unknown as Record<string, unknown>)),\n })\n if (!res.ok) throw new Error(`instruckt: failed to update annotation (${res.status})`)\n return toCamelCase(await res.json()) as unknown as Annotation\n }\n\n}\n","/** Global styles injected into document.head — ONLY what must affect the host page */\nexport const GLOBAL_CSS = /* css */ `\nbody.ik-annotating,\nbody.ik-annotating * { cursor: crosshair !important; }\n`\n\n/** Toolbar shadow DOM styles — fully isolated */\nexport const TOOLBAR_CSS = /* css */ `\n:host {\n all: initial;\n display: block;\n position: fixed;\n z-index: 2147483646;\n}\n\n* { box-sizing: border-box; }\n\n:host-context([data-instruckt-theme=\"dark\"]),\n@media (prefers-color-scheme: dark) {\n :host {\n --ik-bg: #1c1c1e; --ik-bg2: #2c2c2e; --ik-border: #38383a;\n --ik-text: #f4f4f5; --ik-muted: #a1a1aa;\n --ik-shadow: 0 8px 32px rgba(0,0,0,.4), 0 0 0 1px rgba(255,255,255,.06);\n }\n}\n\n:host {\n --ik-accent: #6366f1;\n --ik-accent-h: #4f46e5;\n --ik-bg: #ffffff;\n --ik-bg2: #f4f4f5;\n --ik-border: #e4e4e7;\n --ik-text: #18181b;\n --ik-muted: #a1a1aa;\n --ik-shadow: 0 8px 32px rgba(0,0,0,.08), 0 0 0 1px rgba(0,0,0,.04);\n}\n\n.toolbar {\n display: flex;\n flex-direction: column;\n align-items: center;\n gap: 2px;\n background: var(--ik-bg);\n border-radius: 12px;\n padding: 6px;\n box-shadow: var(--ik-shadow);\n user-select: none;\n touch-action: none;\n cursor: grab;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;\n}\n.toolbar:active { cursor: grabbing; }\n\n.btn {\n display: flex;\n align-items: center;\n justify-content: center;\n width: 34px;\n height: 34px;\n border-radius: 8px;\n border: none;\n background: transparent;\n color: var(--ik-muted);\n cursor: pointer;\n padding: 0;\n position: relative;\n transition: background .15s ease, color .15s ease;\n}\n.btn svg { display: block; }\n.btn:hover { background: var(--ik-bg2); color: var(--ik-text); }\n.btn[data-tooltip]::before {\n content: attr(data-tooltip);\n position: absolute;\n right: calc(100% + 8px);\n top: 50%;\n transform: translateY(-50%);\n white-space: nowrap;\n font-size: 11px;\n padding: 4px 8px;\n border-radius: 6px;\n background: var(--ik-text);\n color: var(--ik-bg);\n pointer-events: none;\n opacity: 0;\n transition: opacity .1s ease;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;\n}\n.btn[data-tooltip]:hover::before { opacity: 1; }\n.btn.active { background: var(--ik-accent); color: #fff; }\n.btn.active:hover { background: var(--ik-accent-h); }\n\n.divider { width: 18px; height: 1px; background: var(--ik-border); margin: 3px 0; }\n\n.badge {\n position: absolute;\n top: -3px; right: -3px;\n min-width: 16px; height: 16px;\n background: #ef4444;\n color: #fff;\n border-radius: 8px;\n font-size: 10px; font-weight: 600;\n display: flex; align-items: center; justify-content: center;\n padding: 0 4px;\n line-height: 1;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;\n}\n\n.minimize-btn { color: var(--ik-muted); opacity: .6; }\n.minimize-btn:hover { opacity: 1; }\n\n.danger-btn { color: var(--ik-muted); opacity: .6; }\n.danger-btn:hover { opacity: 1; color: #ef4444; }\n\n.clear-wrap {\n position: relative;\n display: flex;\n align-items: center;\n}\n.clear-all-btn {\n display: none;\n position: absolute;\n right: 100%;\n top: 0;\n background: var(--ik-bg);\n box-shadow: var(--ik-shadow);\n border-radius: 8px;\n}\n/* clear-all tooltip inherits from .btn[data-tooltip]::before */\n/* Invisible bridge so hover doesn't break crossing the gap */\n.clear-all-btn::after {\n content: '';\n position: absolute;\n top: 0;\n left: 100%;\n width: 6px;\n height: 100%;\n}\n.clear-wrap:hover .clear-all-btn { display: flex; align-items: center; justify-content: center; }\n\n.fab {\n display: flex;\n align-items: center;\n justify-content: center;\n width: 32px;\n height: 32px;\n border-radius: 50%;\n border: none;\n background: var(--ik-bg);\n color: var(--ik-muted);\n box-shadow: var(--ik-shadow);\n cursor: pointer;\n padding: 0;\n transition: color .15s ease, transform .15s ease;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;\n}\n.fab:hover { color: var(--ik-accent); transform: scale(1.1); }\n.fab { position: relative; }\n\n.fab-badge {\n position: absolute;\n top: -4px; right: -4px;\n min-width: 16px; height: 16px;\n background: #6366f1;\n color: #fff;\n border-radius: 8px;\n font-size: 9px; font-weight: 700;\n display: flex; align-items: center; justify-content: center;\n padding: 0 3px;\n line-height: 1;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;\n}\n`\n\n/** Popup shadow DOM styles — fully isolated */\nexport const POPUP_CSS = /* css */ `\n:host {\n all: initial;\n display: block;\n position: fixed;\n z-index: 2147483647;\n}\n\n* { box-sizing: border-box; }\n\n:host {\n --ik-accent: #6366f1;\n --ik-accent-h: #4f46e5;\n --ik-bg: #ffffff;\n --ik-bg2: #f8f8f8;\n --ik-border: #e4e4e7;\n --ik-text: #18181b;\n --ik-muted: #71717a;\n --ik-shadow: 0 4px 24px rgba(0,0,0,.12);\n --ik-radius: 10px;\n --ik-hl: rgba(99,102,241,.15);\n}\n\n@media (prefers-color-scheme: dark) {\n :host {\n --ik-bg: #1c1c1e; --ik-bg2: #2c2c2e; --ik-border: #3a3a3c;\n --ik-text: #f4f4f5; --ik-muted: #a1a1aa;\n --ik-shadow: 0 4px 24px rgba(0,0,0,.5);\n --ik-hl: rgba(99,102,241,.2);\n }\n}\n\n.popup {\n width: 340px;\n background: var(--ik-bg);\n border: 1px solid var(--ik-border);\n border-radius: var(--ik-radius);\n box-shadow: var(--ik-shadow);\n padding: 14px;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;\n font-size: 13px;\n color: var(--ik-text);\n animation: pop-in .12s ease;\n}\n@keyframes pop-in {\n from { opacity:0; transform: scale(.95) translateY(4px); }\n to { opacity:1; transform: scale(1) translateY(0); }\n}\n\n.header { display:flex; align-items:center; justify-content:space-between; margin-bottom:10px; }\n.element-tag {\n font-size:11px; font-family:ui-monospace,monospace; color:var(--ik-muted);\n background:var(--ik-bg2); border-radius:4px; padding:2px 6px;\n max-width:220px; overflow:hidden; text-overflow:ellipsis; white-space:nowrap;\n}\n.close-btn {\n background:none; border:none; color:var(--ik-muted);\n cursor:pointer; font-size:18px; line-height:1; padding:0;\n}\n\n.fw-badge {\n display:inline-flex; align-items:center; gap:4px;\n font-size:10px; font-weight:700; text-transform:uppercase; letter-spacing:.05em;\n color:var(--ik-accent); background:var(--ik-hl); border-radius:4px;\n padding:2px 6px; margin-bottom:8px;\n}\n.selected-text {\n font-size:12px; color:var(--ik-muted); background:var(--ik-bg2);\n border-left:3px solid var(--ik-accent); padding:4px 8px;\n border-radius:0 4px 4px 0; margin-bottom:10px;\n overflow:hidden; text-overflow:ellipsis; white-space:nowrap;\n}\n\n.label {\n font-size:10px; font-weight:700; text-transform:uppercase;\n letter-spacing:.05em; color:var(--ik-muted); margin-bottom:4px;\n}\n.row { display:flex; gap:6px; margin-bottom:10px; }\n.chips { display:flex; gap:4px; flex-wrap:wrap; }\n\n.chip {\n font-size:11px; padding:3px 8px; border-radius:12px;\n border:1px solid var(--ik-border); background:transparent;\n color:var(--ik-muted); cursor:pointer; transition:all .1s;\n}\n.chip:hover { border-color:var(--ik-accent); color:var(--ik-accent); }\n.chip.sel { background:var(--ik-accent); border-color:var(--ik-accent); color:#fff; }\n.chip.blocking.sel { background:#ef4444; border-color:#ef4444; }\n.chip.important.sel { background:#f97316; border-color:#f97316; }\n.chip.suggestion.sel{ background:#22c55e; border-color:#22c55e; }\n\n.screenshot-slot { margin-bottom: 10px; }\n\n.btn-capture {\n display: flex;\n align-items: center;\n gap: 6px;\n width: 100%;\n padding: 8px 10px;\n border: 1px dashed var(--ik-border);\n border-radius: 6px;\n background: var(--ik-bg2);\n color: var(--ik-muted);\n font-size: 12px;\n font-family: inherit;\n cursor: pointer;\n transition: border-color .15s, color .15s;\n}\n.btn-capture:hover {\n border-color: var(--ik-accent);\n color: var(--ik-accent);\n}\n.btn-capture svg { flex-shrink: 0; }\n\n.screenshot-preview {\n position: relative;\n border-radius: 6px;\n overflow: hidden;\n border: 1px solid var(--ik-border);\n margin-bottom: 10px;\n}\n.screenshot-preview img {\n display: block;\n width: 100%;\n max-height: 200px;\n object-fit: contain;\n background: var(--ik-bg2);\n}\n.screenshot-remove {\n position: absolute;\n top: 4px; right: 4px;\n width: 20px; height: 20px;\n border-radius: 50%;\n border: none;\n background: rgba(0,0,0,.6);\n color: #fff;\n font-size: 12px;\n line-height: 1;\n cursor: pointer;\n display: flex;\n align-items: center;\n justify-content: center;\n padding: 0;\n}\n.screenshot-remove:hover { background: #ef4444; }\n\ntextarea {\n width:100%; min-height:80px; resize:vertical;\n border:1px solid var(--ik-border); border-radius:6px;\n background:var(--ik-bg2); color:var(--ik-text);\n font-family:inherit; font-size:13px; padding:8px 10px;\n outline:none; transition:border-color .15s; margin-bottom:10px;\n}\ntextarea:focus { border-color:var(--ik-accent); }\ntextarea::placeholder { color:var(--ik-muted); }\n\n.actions { display:flex; justify-content:flex-end; gap:6px; }\n\n.btn-secondary {\n padding:6px 14px; border-radius:6px; border:1px solid var(--ik-border);\n background:transparent; color:var(--ik-muted); font-size:12px; cursor:pointer; transition:all .1s;\n}\n.btn-secondary:hover { border-color:var(--ik-muted); color:var(--ik-text); }\n\n.btn-primary {\n padding:6px 14px; border-radius:6px; border:none;\n background:var(--ik-accent); color:#fff;\n font-size:12px; font-weight:700; cursor:pointer; transition:background .1s;\n}\n.btn-primary:hover { background:var(--ik-accent-h); }\n.btn-primary:disabled { opacity:.5; cursor:not-allowed; }\n\n.btn-danger {\n padding:6px 14px; border-radius:6px; border:1px solid #ef4444;\n background:transparent; color:#ef4444;\n font-size:12px; cursor:pointer; transition:all .1s;\n}\n.btn-danger:hover { background:#ef4444; color:#fff; }\n\n/* Thread view */\n.thread { margin-top:10px; border-top:1px solid var(--ik-border); padding-top:10px; }\n.msg { margin-bottom:8px; }\n.msg-role {\n font-size:10px; font-weight:700; text-transform:uppercase;\n letter-spacing:.05em; margin-bottom:2px;\n}\n.msg-role.human { color:var(--ik-accent); }\n.msg-role.agent { color:#22c55e; }\n.msg-content { font-size:12px; line-height:1.5; }\n\n.status-badge {\n display:inline-flex; align-items:center; gap:4px;\n font-size:10px; font-weight:700; text-transform:uppercase; letter-spacing:.05em;\n border-radius:4px; padding:2px 6px;\n}\n.status-badge.pending { background:rgba(99,102,241,.15); color:var(--ik-accent); }\n.status-badge.resolved { background:rgba(34,197,94,.15); color:#22c55e; }\n.status-badge.dismissed { background:var(--ik-bg2); color:var(--ik-muted); }\n`\n\n/** Marker pin styles injected into document.head — pins overlay the page */\nexport const MARKER_CSS = /* css */ `\n.ik-marker {\n position: absolute;\n z-index: 2147483645;\n width: 24px; height: 24px;\n border-radius: 50%;\n background: var(--ik-marker-default, #6366f1);\n color: #fff;\n font-size: 11px; font-weight: 700;\n display: flex; align-items: center; justify-content: center;\n cursor: pointer;\n box-shadow: 0 2px 8px color-mix(in srgb, var(--ik-marker-default, #6366f1) 40%, transparent);\n transition: transform .15s ease;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;\n pointer-events: all;\n user-select: none;\n}\n.ik-marker:hover { transform: scale(1.15); }\n.ik-marker.has-screenshot { background: var(--ik-marker-screenshot, #22c55e); box-shadow: 0 2px 8px color-mix(in srgb, var(--ik-marker-screenshot, #22c55e) 40%, transparent); }\n.ik-marker.dismissed { background: var(--ik-marker-dismissed, #71717a); box-shadow: 0 2px 8px rgba(0,0,0,.2); }\n`\n\n/** Inject styles into document.head (idempotent) */\nexport function injectGlobalStyles(colors?: import('../types').MarkerColors): void {\n if (document.getElementById('instruckt-global')) return\n const vars = colors\n ? `:root {${colors.default ? ` --ik-marker-default: ${colors.default};` : ''}${colors.screenshot ? ` --ik-marker-screenshot: ${colors.screenshot};` : ''}${colors.dismissed ? ` --ik-marker-dismissed: ${colors.dismissed};` : ''} }\\n`\n : ''\n const style = document.createElement('style')\n style.id = 'instruckt-global'\n style.textContent = vars + GLOBAL_CSS + MARKER_CSS\n document.head.appendChild(style)\n}\n","import type { KeyBindings } from '../types'\nimport { TOOLBAR_CSS } from './styles'\n\nexport type ToolbarMode = 'idle' | 'annotating' | 'frozen'\n\ninterface ToolbarCallbacks {\n onToggleAnnotate: (active: boolean) => void\n onFreezeAnimations: (frozen: boolean) => void\n onScreenshot: () => void\n onCopy: () => void\n onClearPage?: () => void\n onClearAll?: () => void\n onMinimize?: (minimized: boolean) => void\n}\n\n// ── Inline SVG icons (24x24, 2px stroke) ─────────────────────\n\nconst ICONS = {\n annotate: `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M12 20h9\"/><path d=\"M16.5 3.5a2.121 2.121 0 0 1 3 3L7 19l-4 1 1-4 12.5-12.5z\"/></svg>`,\n freeze: `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><rect x=\"6\" y=\"4\" width=\"4\" height=\"16\" rx=\"1\"/><rect x=\"14\" y=\"4\" width=\"4\" height=\"16\" rx=\"1\"/></svg>`,\n copy: `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><rect x=\"9\" y=\"9\" width=\"13\" height=\"13\" rx=\"2\"/><path d=\"M5 15H4a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h9a2 2 0 0 1 2 2v1\"/></svg>`,\n check: `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><polyline points=\"20 6 9 17 4 12\"/></svg>`,\n clear: `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><polyline points=\"3 6 5 6 21 6\"/><path d=\"M19 6v14a2 2 0 0 1-2 2H7a2 2 0 0 1-2-2V6m3 0V4a2 2 0 0 1 2-2h4a2 2 0 0 1 2 2v2\"/></svg>`,\n minimize: `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><polyline points=\"7 13 12 18 17 13\"/><line x1=\"12\" y1=\"6\" x2=\"12\" y2=\"18\"/></svg>`,\n screenshot: `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M23 19a2 2 0 0 1-2 2H3a2 2 0 0 1-2-2V8a2 2 0 0 1 2-2h4l2-3h6l2 3h4a2 2 0 0 1 2 2z\"/><circle cx=\"12\" cy=\"13\" r=\"4\"/></svg>`,\n logo: `<svg width=\"16\" height=\"16\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M12 20h9\"/><path d=\"M16.5 3.5a2.121 2.121 0 0 1 3 3L7 19l-4 1 1-4 12.5-12.5z\"/></svg>`,\n} as const\n\nexport class Toolbar {\n private host!: HTMLElement\n private shadow!: ShadowRoot\n private toolbarEl!: HTMLDivElement\n private fab!: HTMLButtonElement\n private fabBadge: HTMLSpanElement | null = null\n private annotateBtn!: HTMLButtonElement\n private freezeBtn!: HTMLButtonElement\n private copyBtn!: HTMLButtonElement\n private annotateActive = false\n private freezeActive = false\n private minimized = false\n private totalCount = 0\n private dragging = false\n private dragOffset = { x: 0, y: 0 }\n\n private keys: KeyBindings\n\n constructor(\n private readonly position: string,\n private readonly callbacks: ToolbarCallbacks,\n keys?: KeyBindings,\n ) {\n this.keys = keys ?? {}\n this.build()\n this.setupDrag()\n }\n\n private build(): void {\n this.host = document.createElement('div')\n this.host.setAttribute('data-instruckt', 'toolbar')\n this.shadow = this.host.attachShadow({ mode: 'open' })\n\n const style = document.createElement('style')\n style.textContent = TOOLBAR_CSS\n this.shadow.appendChild(style)\n\n // Full toolbar\n this.toolbarEl = document.createElement('div')\n this.toolbarEl.className = 'toolbar'\n\n const k = this.keys\n this.annotateBtn = this.makeBtn(ICONS.annotate, `Annotate elements (${(k.annotate ?? 'A').toUpperCase()})`, () => {\n const next = !this.annotateActive\n this.setAnnotateActive(next)\n this.callbacks.onToggleAnnotate(next)\n })\n\n this.freezeBtn = this.makeBtn(ICONS.freeze, `Freeze page (${(k.freeze ?? 'F').toUpperCase()})`, () => {\n const next = !this.freezeActive\n this.setFreezeActive(next)\n this.callbacks.onFreezeAnimations(next)\n })\n\n const screenshotBtn = this.makeBtn(ICONS.screenshot, `Screenshot region (${(k.screenshot ?? 'C').toUpperCase()})`, () => {\n this.callbacks.onScreenshot()\n })\n\n this.copyBtn = this.makeBtn(ICONS.copy, 'Copy annotations as markdown', () => {\n this.callbacks.onCopy()\n this.copyBtn.innerHTML = ICONS.check\n setTimeout(() => { this.copyBtn.innerHTML = ICONS.copy }, 1200)\n })\n\n const clearWrap = document.createElement('div')\n clearWrap.className = 'clear-wrap'\n\n const clearBtn = this.makeBtn(ICONS.clear, `Clear this page (${(k.clearPage ?? 'X').toUpperCase()})`, () => {\n this.callbacks.onClearPage?.()\n })\n clearBtn.classList.add('danger-btn')\n\n const clearAllBtn = this.makeBtn(\n `<svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M12 2C6.5 2 2 6.5 2 12s4.5 10 10 10 10-4.5 10-10S17.5 2 12 2\"/><line x1=\"4.93\" y1=\"4.93\" x2=\"19.07\" y2=\"19.07\"/></svg>`,\n 'Delete all instructions.',\n () => this.callbacks.onClearAll?.(),\n )\n clearAllBtn.classList.add('danger-btn', 'clear-all-btn')\n\n clearWrap.appendChild(clearBtn)\n clearWrap.appendChild(clearAllBtn)\n\n const minimizeBtn = this.makeBtn(ICONS.minimize, 'Minimize toolbar', () => {\n this.setMinimized(true)\n })\n minimizeBtn.classList.add('minimize-btn')\n\n const mkDiv = () => { const d = document.createElement('div'); d.className = 'divider'; return d }\n\n this.toolbarEl.append(\n this.annotateBtn, screenshotBtn, mkDiv(), this.freezeBtn, mkDiv(),\n this.copyBtn, clearWrap, mkDiv(), minimizeBtn,\n )\n this.shadow.appendChild(this.toolbarEl)\n\n // Floating action button (minimized state)\n this.fab = document.createElement('button')\n this.fab.className = 'fab'\n this.fab.title = 'Open instruckt toolbar'\n this.fab.setAttribute('aria-label', 'Open instruckt toolbar')\n this.fab.innerHTML = ICONS.logo\n this.fab.style.display = 'none'\n this.fab.addEventListener('click', (e) => {\n e.stopPropagation()\n this.setMinimized(false)\n })\n this.shadow.appendChild(this.fab)\n\n // Prevent toolbar clicks from reaching page handlers (e.g. Alpine @click.outside)\n // Shadow DOM stopPropagation only works within the shadow tree — clicks still\n // re-dispatch from the host element into the regular DOM.\n this.host.addEventListener('click', (e) => e.stopPropagation())\n this.host.addEventListener('mousedown', (e) => e.stopPropagation())\n this.host.addEventListener('pointerdown', (e) => e.stopPropagation())\n\n this.applyPosition()\n const root = document.getElementById('instruckt-root') ?? document.body\n root.appendChild(this.host)\n }\n\n private makeBtn(iconHtml: string, tooltip: string, onClick: () => void): HTMLButtonElement {\n const btn = document.createElement('button')\n btn.className = 'btn'\n btn.setAttribute('data-tooltip', tooltip)\n btn.setAttribute('aria-label', tooltip)\n btn.innerHTML = iconHtml\n btn.addEventListener('click', (e) => {\n e.stopPropagation()\n onClick()\n })\n return btn\n }\n\n private applyPosition(): void {\n const m = '16px'\n Object.assign(this.host.style, {\n position: 'fixed',\n zIndex: '2147483646',\n bottom: this.position.includes('bottom') ? m : 'auto',\n top: this.position.includes('top') ? m : 'auto',\n right: this.position.includes('right') ? m : 'auto',\n left: this.position.includes('left') ? m : 'auto',\n })\n }\n\n private setupDrag(): void {\n this.shadow.addEventListener('mousedown', (evt) => {\n const e = evt as MouseEvent\n if ((e.target as Element).closest('.btn') || (e.target as Element).closest('.fab')) return\n this.dragging = true\n const rect = this.host.getBoundingClientRect()\n this.dragOffset = { x: e.clientX - rect.left, y: e.clientY - rect.top }\n e.preventDefault()\n })\n\n document.addEventListener('mousemove', (e) => {\n if (!this.dragging) return\n Object.assign(this.host.style, {\n left: `${e.clientX - this.dragOffset.x}px`,\n top: `${e.clientY - this.dragOffset.y}px`,\n right: 'auto',\n bottom: 'auto',\n })\n })\n\n document.addEventListener('mouseup', () => { this.dragging = false })\n }\n\n private setMinimized(min: boolean): void {\n this.minimized = min\n this.toolbarEl.style.display = min ? 'none' : ''\n this.fab.style.display = min ? '' : 'none'\n this.updateFabBadge()\n this.callbacks.onMinimize?.(min)\n }\n\n private updateFabBadge(): void {\n if (this.totalCount > 0 && this.minimized) {\n if (!this.fabBadge) {\n this.fabBadge = document.createElement('span')\n this.fabBadge.className = 'fab-badge'\n this.fab.appendChild(this.fabBadge)\n }\n this.fabBadge.textContent = this.totalCount > 99 ? '99+' : String(this.totalCount)\n } else {\n this.fabBadge?.remove()\n this.fabBadge = null\n }\n }\n\n isMinimized(): boolean {\n return this.minimized\n }\n\n /** Programmatically minimize without firing callback */\n minimize(): void {\n this.minimized = true\n this.toolbarEl.style.display = 'none'\n this.fab.style.display = ''\n this.updateFabBadge()\n }\n\n setAnnotateActive(active: boolean): void {\n this.annotateActive = active\n this.annotateBtn.classList.toggle('active', active)\n document.body.classList.toggle('ik-annotating', active)\n }\n\n setFreezeActive(active: boolean): void {\n this.freezeActive = active\n this.freezeBtn.classList.toggle('active', active)\n }\n\n // Keep for compatibility — resolves visual mode from instruckt.ts\n setMode(mode: ToolbarMode): void {\n this.setAnnotateActive(mode === 'annotating')\n }\n\n setAnnotationCount(count: number): void {\n let badge = this.annotateBtn.querySelector('.badge')\n if (count > 0) {\n if (!badge) {\n badge = document.createElement('span')\n badge.className = 'badge'\n this.annotateBtn.appendChild(badge)\n }\n badge.textContent = count > 99 ? '99+' : String(count)\n } else {\n badge?.remove()\n }\n }\n\n setTotalCount(count: number): void {\n this.totalCount = count\n this.updateFabBadge()\n }\n\n destroy(): void {\n this.host.remove()\n document.body.classList.remove('ik-annotating')\n }\n}\n","/** Hover highlight overlay — uses all inline styles, no CSS class needed */\nexport class ElementHighlight {\n private el: HTMLElement\n\n constructor() {\n this.el = document.createElement('div')\n // All styling inline to avoid any host-page CSS interference\n Object.assign(this.el.style, {\n position: 'fixed',\n pointerEvents: 'none', // MUST be none — prevents swallowing clicks\n zIndex: '2147483644',\n border: '2px solid rgba(99,102,241,0.7)',\n background: 'rgba(99,102,241,0.1)',\n borderRadius: '3px',\n transition: 'all 0.06s ease',\n display: 'none',\n })\n this.el.setAttribute('data-instruckt', 'highlight')\n const root = document.getElementById('instruckt-root') ?? document.body\n root.appendChild(this.el)\n }\n\n show(el: Element): void {\n const rect = el.getBoundingClientRect()\n if (rect.width === 0 && rect.height === 0) {\n this.hide()\n return\n }\n Object.assign(this.el.style, {\n display: 'block',\n left: `${rect.left}px`,\n top: `${rect.top}px`,\n width: `${rect.width}px`,\n height: `${rect.height}px`,\n })\n }\n\n hide(): void {\n this.el.style.display = 'none'\n }\n\n destroy(): void {\n this.el.remove()\n }\n}\n","import type { Options } from './types'\n\nexport function resolveUrl(url: string, baseUrl: string | null): string {\n // url is absolute already\n if (url.match(/^[a-z]+:\\/\\//i)) {\n return url\n }\n\n // url is absolute already, without protocol\n if (url.match(/^\\/\\//)) {\n return window.location.protocol + url\n }\n\n // dataURI, mailto:, tel:, etc.\n if (url.match(/^[a-z]+:/i)) {\n return url\n }\n\n const doc = document.implementation.createHTMLDocument()\n const base = doc.createElement('base')\n const a = doc.createElement('a')\n\n doc.head.appendChild(base)\n doc.body.appendChild(a)\n\n if (baseUrl) {\n base.href = baseUrl\n }\n\n a.href = url\n\n return a.href\n}\n\nexport const uuid = (() => {\n // generate uuid for className of pseudo elements.\n // We should not use GUIDs, otherwise pseudo elements sometimes cannot be captured.\n let counter = 0\n\n // ref: http://stackoverflow.com/a/6248722/2519373\n const random = () =>\n // eslint-disable-next-line no-bitwise\n `0000${((Math.random() * 36 ** 4) << 0).toString(36)}`.slice(-4)\n\n return () => {\n counter += 1\n return `u${random()}${counter}`\n }\n})()\n\nexport function delay<T>(ms: number) {\n return (args: T) =>\n new Promise<T>((resolve) => {\n setTimeout(() => resolve(args), ms)\n })\n}\n\nexport function toArray<T>(arrayLike: any): T[] {\n const arr: T[] = []\n\n for (let i = 0, l = arrayLike.length; i < l; i++) {\n arr.push(arrayLike[i])\n }\n\n return arr\n}\n\nlet styleProps: string[] | null = null\nexport function getStyleProperties(options: Options = {}): string[] {\n if (styleProps) {\n return styleProps\n }\n\n if (options.includeStyleProperties) {\n styleProps = options.includeStyleProperties\n return styleProps\n }\n\n styleProps = toArray(window.getComputedStyle(document.documentElement))\n\n return styleProps\n}\n\nfunction px(node: HTMLElement, styleProperty: string) {\n const win = node.ownerDocument.defaultView || window\n const val = win.getComputedStyle(node).getPropertyValue(styleProperty)\n return val ? parseFloat(val.replace('px', '')) : 0\n}\n\nfunction getNodeWidth(node: HTMLElement) {\n const leftBorder = px(node, 'border-left-width')\n const rightBorder = px(node, 'border-right-width')\n return node.clientWidth + leftBorder + rightBorder\n}\n\nfunction getNodeHeight(node: HTMLElement) {\n const topBorder = px(node, 'border-top-width')\n const bottomBorder = px(node, 'border-bottom-width')\n return node.clientHeight + topBorder + bottomBorder\n}\n\nexport function getImageSize(targetNode: HTMLElement, options: Options = {}) {\n const width = options.width || getNodeWidth(targetNode)\n const height = options.height || getNodeHeight(targetNode)\n\n return { width, height }\n}\n\nexport function getPixelRatio() {\n let ratio\n\n let FINAL_PROCESS\n try {\n FINAL_PROCESS = process\n } catch (e) {\n // pass\n }\n\n const val =\n FINAL_PROCESS && FINAL_PROCESS.env\n ? FINAL_PROCESS.env.devicePixelRatio\n : null\n if (val) {\n ratio = parseInt(val, 10)\n if (Number.isNaN(ratio)) {\n ratio = 1\n }\n }\n return ratio || window.devicePixelRatio || 1\n}\n\n// @see https://developer.mozilla.org/en-US/docs/Web/HTML/Element/canvas#maximum_canvas_size\nconst canvasDimensionLimit = 16384\n\nexport function checkCanvasDimensions(canvas: HTMLCanvasElement) {\n if (\n canvas.width > canvasDimensionLimit ||\n canvas.height > canvasDimensionLimit\n ) {\n if (\n canvas.width > canvasDimensionLimit &&\n canvas.height > canvasDimensionLimit\n ) {\n if (canvas.width > canvas.height) {\n canvas.height *= canvasDimensionLimit / canvas.width\n canvas.width = canvasDimensionLimit\n } else {\n canvas.width *= canvasDimensionLimit / canvas.height\n canvas.height = canvasDimensionLimit\n }\n } else if (canvas.width > canvasDimensionLimit) {\n canvas.height *= canvasDimensionLimit / canvas.width\n canvas.width = canvasDimensionLimit\n } else {\n canvas.width *= canvasDimensionLimit / canvas.height\n canvas.height = canvasDimensionLimit\n }\n }\n}\n\nexport function canvasToBlob(\n canvas: HTMLCanvasElement,\n options: Options = {},\n): Promise<Blob | null> {\n if (canvas.toBlob) {\n return new Promise((resolve) => {\n canvas.toBlob(\n resolve,\n options.type ? options.type : 'image/png',\n options.quality ? options.quality : 1,\n )\n })\n }\n\n return new Promise((resolve) => {\n const binaryString = window.atob(\n canvas\n .toDataURL(\n options.type ? options.type : undefined,\n options.quality ? options.quality : undefined,\n )\n .split(',')[1],\n )\n const len = binaryString.length\n const binaryArray = new Uint8Array(len)\n\n for (let i = 0; i < len; i += 1) {\n binaryArray[i] = binaryString.charCodeAt(i)\n }\n\n resolve(\n new Blob([binaryArray], {\n type: options.type ? options.type : 'image/png',\n }),\n )\n })\n}\n\nexport function createImage(url: string): Promise<HTMLImageElement> {\n return new Promise((resolve, reject) => {\n const img = new Image()\n img.onload = () => {\n img.decode().then(() => {\n requestAnimationFrame(() => resolve(img))\n })\n }\n img.onerror = reject\n img.crossOrigin = 'anonymous'\n img.decoding = 'async'\n img.src = url\n })\n}\n\nexport async function svgToDataURL(svg: SVGElement): Promise<string> {\n return Promise.resolve()\n .then(() => new XMLSerializer().serializeToString(svg))\n .then(encodeURIComponent)\n .then((html) => `data:image/svg+xml;charset=utf-8,${html}`)\n}\n\nexport async function nodeToDataURL(\n node: HTMLElement,\n width: number,\n height: number,\n): Promise<string> {\n const xmlns = 'http://www.w3.org/2000/svg'\n const svg = document.createElementNS(xmlns, 'svg')\n const foreignObject = document.createElementNS(xmlns, 'foreignObject')\n\n svg.setAttribute('width', `${width}`)\n svg.setAttribute('height', `${height}`)\n svg.setAttribute('viewBox', `0 0 ${width} ${height}`)\n\n foreignObject.setAttribute('width', '100%')\n foreignObject.setAttribute('height', '100%')\n foreignObject.setAttribute('x', '0')\n foreignObject.setAttribute('y', '0')\n foreignObject.setAttribute('externalResourcesRequired', 'true')\n\n svg.appendChild(foreignObject)\n foreignObject.appendChild(node)\n return svgToDataURL(svg)\n}\n\nexport const isInstanceOfElement = <\n T extends typeof Element | typeof HTMLElement | typeof SVGImageElement,\n>(\n node: Element | HTMLElement | SVGImageElement,\n instance: T,\n): node is T['prototype'] => {\n if (node instanceof instance) return true\n\n const nodePrototype = Object.getPrototypeOf(node)\n\n if (nodePrototype === null) return false\n\n return (\n nodePrototype.constructor.name === instance.name ||\n isInstanceOfElement(nodePrototype, instance)\n )\n}\n","import type { Options } from './types'\nimport { uuid, getStyleProperties } from './util'\n\ntype Pseudo = ':before' | ':after'\n\nfunction formatCSSText(style: CSSStyleDeclaration) {\n const content = style.getPropertyValue('content')\n return `${style.cssText} content: '${content.replace(/'|\"/g, '')}';`\n}\n\nfunction formatCSSProperties(style: CSSStyleDeclaration, options: Options) {\n return getStyleProperties(options)\n .map((name) => {\n const value = style.getPropertyValue(name)\n const priority = style.getPropertyPriority(name)\n\n return `${name}: ${value}${priority ? ' !important' : ''};`\n })\n .join(' ')\n}\n\nfunction getPseudoElementStyle(\n className: string,\n pseudo: Pseudo,\n style: CSSStyleDeclaration,\n options: Options,\n): Text {\n const selector = `.${className}:${pseudo}`\n const cssText = style.cssText\n ? formatCSSText(style)\n : formatCSSProperties(style, options)\n\n return document.createTextNode(`${selector}{${cssText}}`)\n}\n\nfunction clonePseudoElement<T extends HTMLElement>(\n nativeNode: T,\n clonedNode: T,\n pseudo: Pseudo,\n options: Options,\n) {\n const style = window.getComputedStyle(nativeNode, pseudo)\n const content = style.getPropertyValue('content')\n if (content === '' || content === 'none') {\n return\n }\n\n const className = uuid()\n try {\n clonedNode.className = `${clonedNode.className} ${className}`\n } catch (err) {\n return\n }\n\n const styleElement = document.createElement('style')\n styleElement.appendChild(\n getPseudoElementStyle(className, pseudo, style, options),\n )\n clonedNode.appendChild(styleElement)\n}\n\nexport function clonePseudoElements<T extends HTMLElement>(\n nativeNode: T,\n clonedNode: T,\n options: Options,\n) {\n clonePseudoElement(nativeNode, clonedNode, ':before', options)\n clonePseudoElement(nativeNode, clonedNode, ':after', options)\n}\n","const WOFF = 'application/font-woff'\nconst JPEG = 'image/jpeg'\nconst mimes: { [key: string]: string } = {\n woff: WOFF,\n woff2: WOFF,\n ttf: 'application/font-truetype',\n eot: 'application/vnd.ms-fontobject',\n png: 'image/png',\n jpg: JPEG,\n jpeg: JPEG,\n gif: 'image/gif',\n tiff: 'image/tiff',\n svg: 'image/svg+xml',\n webp: 'image/webp',\n}\n\nfunction getExtension(url: string): string {\n const match = /\\.([^./]*?)$/g.exec(url)\n return match ? match[1] : ''\n}\n\nexport function getMimeType(url: string): string {\n const extension = getExtension(url).toLowerCase()\n return mimes[extension] || ''\n}\n","import { Options } from './types'\n\nfunction getContentFromDataUrl(dataURL: string) {\n return dataURL.split(/,/)[1]\n}\n\nexport function isDataUrl(url: string) {\n return url.search(/^(data:)/) !== -1\n}\n\nexport function makeDataUrl(content: string, mimeType: string) {\n return `data:${mimeType};base64,${content}`\n}\n\nexport async function fetchAsDataURL<T>(\n url: string,\n init: RequestInit | undefined,\n process: (data: { result: string; res: Response }) => T,\n): Promise<T> {\n const res = await fetch(url, init)\n if (res.status === 404) {\n throw new Error(`Resource \"${res.url}\" not found`)\n }\n const blob = await res.blob()\n return new Promise<T>((resolve, reject) => {\n const reader = new FileReader()\n reader.onerror = reject\n reader.onloadend = () => {\n try {\n resolve(process({ res, result: reader.result as string }))\n } catch (error) {\n reject(error)\n }\n }\n\n reader.readAsDataURL(blob)\n })\n}\n\nconst cache: { [url: string]: string } = {}\n\nfunction getCacheKey(\n url: string,\n contentType: string | undefined,\n includeQueryParams: boolean | undefined,\n) {\n let key = url.replace(/\\?.*/, '')\n\n if (includeQueryParams) {\n key = url\n }\n\n // font resource\n if (/ttf|otf|eot|woff2?/i.test(key)) {\n key = key.replace(/.*\\//, '')\n }\n\n return contentType ? `[${contentType}]${key}` : key\n}\n\nexport async function resourceToDataURL(\n resourceUrl: string,\n contentType: string | undefined,\n options: Options,\n) {\n const cacheKey = getCacheKey(\n resourceUrl,\n contentType,\n options.includeQueryParams,\n )\n\n if (cache[cacheKey] != null) {\n return cache[cacheKey]\n }\n\n // ref: https://developer.mozilla.org/en/docs/Web/API/XMLHttpRequest/Using_XMLHttpRequest#Bypassing_the_cache\n if (options.cacheBust) {\n // eslint-disable-next-line no-param-reassign\n resourceUrl += (/\\?/.test(resourceUrl) ? '&' : '?') + new Date().getTime()\n }\n\n let dataURL: string\n try {\n const content = await fetchAsDataURL(\n resourceUrl,\n options.fetchRequestInit,\n ({ res, result }) => {\n if (!contentType) {\n // eslint-disable-next-line no-param-reassign\n contentType = res.headers.get('Content-Type') || ''\n }\n return getContentFromDataUrl(result)\n },\n )\n dataURL = makeDataUrl(content, contentType!)\n } catch (error) {\n dataURL = options.imagePlaceholder || ''\n\n let msg = `Failed to fetch resource: ${resourceUrl}`\n if (error) {\n msg = typeof error === 'string' ? error : error.message\n }\n\n if (msg) {\n console.warn(msg)\n }\n }\n\n cache[cacheKey] = dataURL\n return dataURL\n}\n","import type { Options } from './types'\nimport { clonePseudoElements } from './clone-pseudos'\nimport {\n createImage,\n toArray,\n isInstanceOfElement,\n getStyleProperties,\n} from './util'\nimport { getMimeType } from './mimes'\nimport { resourceToDataURL } from './dataurl'\n\nasync function cloneCanvasElement(canvas: HTMLCanvasElement) {\n const dataURL = canvas.toDataURL()\n if (dataURL === 'data:,') {\n return canvas.cloneNode(false) as HTMLCanvasElement\n }\n return createImage(dataURL)\n}\n\nasync function cloneVideoElement(video: HTMLVideoElement, options: Options) {\n if (video.currentSrc) {\n const canvas = document.createElement('canvas')\n const ctx = canvas.getContext('2d')\n canvas.width = video.clientWidth\n canvas.height = video.clientHeight\n ctx?.drawImage(video, 0, 0, canvas.width, canvas.height)\n const dataURL = canvas.toDataURL()\n return createImage(dataURL)\n }\n\n const poster = video.poster\n const contentType = getMimeType(poster)\n const dataURL = await resourceToDataURL(poster, contentType, options)\n return createImage(dataURL)\n}\n\nasync function cloneIFrameElement(iframe: HTMLIFrameElement, options: Options) {\n try {\n if (iframe?.contentDocument?.body) {\n return (await cloneNode(\n iframe.contentDocument.body,\n options,\n true,\n )) as HTMLBodyElement\n }\n } catch {\n // Failed to clone iframe\n }\n\n return iframe.cloneNode(false) as HTMLIFrameElement\n}\n\nasync function cloneSingleNode<T extends HTMLElement>(\n node: T,\n options: Options,\n): Promise<HTMLElement> {\n if (isInstanceOfElement(node, HTMLCanvasElement)) {\n return cloneCanvasElement(node)\n }\n\n if (isInstanceOfElement(node, HTMLVideoElement)) {\n return cloneVideoElement(node, options)\n }\n\n if (isInstanceOfElement(node, HTMLIFrameElement)) {\n return cloneIFrameElement(node, options)\n }\n\n return node.cloneNode(isSVGElement(node)) as T\n}\n\nconst isSlotElement = (node: HTMLElement): node is HTMLSlotElement =>\n node.tagName != null && node.tagName.toUpperCase() === 'SLOT'\n\nconst isSVGElement = (node: HTMLElement): node is HTMLSlotElement =>\n node.tagName != null && node.tagName.toUpperCase() === 'SVG'\n\nasync function cloneChildren<T extends HTMLElement>(\n nativeNode: T,\n clonedNode: T,\n options: Options,\n): Promise<T> {\n if (isSVGElement(clonedNode)) {\n return clonedNode\n }\n\n let children: T[] = []\n\n if (isSlotElement(nativeNode) && nativeNode.assignedNodes) {\n children = toArray<T>(nativeNode.assignedNodes())\n } else if (\n isInstanceOfElement(nativeNode, HTMLIFrameElement) &&\n nativeNode.contentDocument?.body\n ) {\n children = toArray<T>(nativeNode.contentDocument.body.childNodes)\n } else {\n children = toArray<T>((nativeNode.shadowRoot ?? nativeNode).childNodes)\n }\n\n if (\n children.length === 0 ||\n isInstanceOfElement(nativeNode, HTMLVideoElement)\n ) {\n return clonedNode\n }\n\n await children.reduce(\n (deferred, child) =>\n deferred\n .then(() => cloneNode(child, options))\n .then((clonedChild: HTMLElement | null) => {\n if (clonedChild) {\n clonedNode.appendChild(clonedChild)\n }\n }),\n Promise.resolve(),\n )\n\n return clonedNode\n}\n\nfunction cloneCSSStyle<T extends HTMLElement>(\n nativeNode: T,\n clonedNode: T,\n options: Options,\n) {\n const targetStyle = clonedNode.style\n if (!targetStyle) {\n return\n }\n\n const sourceStyle = window.getComputedStyle(nativeNode)\n if (sourceStyle.cssText) {\n targetStyle.cssText = sourceStyle.cssText\n targetStyle.transformOrigin = sourceStyle.transformOrigin\n } else {\n getStyleProperties(options).forEach((name) => {\n let value = sourceStyle.getPropertyValue(name)\n if (name === 'font-size' && value.endsWith('px')) {\n const reducedFont =\n Math.floor(parseFloat(value.substring(0, value.length - 2))) - 0.1\n value = `${reducedFont}px`\n }\n\n if (\n isInstanceOfElement(nativeNode, HTMLIFrameElement) &&\n name === 'display' &&\n value === 'inline'\n ) {\n value = 'block'\n }\n\n if (name === 'd' && clonedNode.getAttribute('d')) {\n value = `path(${clonedNode.getAttribute('d')})`\n }\n\n targetStyle.setProperty(\n name,\n value,\n sourceStyle.getPropertyPriority(name),\n )\n })\n }\n}\n\nfunction cloneInputValue<T extends HTMLElement>(nativeNode: T, clonedNode: T) {\n if (isInstanceOfElement(nativeNode, HTMLTextAreaElement)) {\n clonedNode.innerHTML = nativeNode.value\n }\n\n if (isInstanceOfElement(nativeNode, HTMLInputElement)) {\n clonedNode.setAttribute('value', nativeNode.value)\n }\n}\n\nfunction cloneSelectValue<T extends HTMLElement>(nativeNode: T, clonedNode: T) {\n if (isInstanceOfElement(nativeNode, HTMLSelectElement)) {\n const clonedSelect = clonedNode as any as HTMLSelectElement\n const selectedOption = Array.from(clonedSelect.children).find(\n (child) => nativeNode.value === child.getAttribute('value'),\n )\n\n if (selectedOption) {\n selectedOption.setAttribute('selected', '')\n }\n }\n}\n\nfunction decorate<T extends HTMLElement>(\n nativeNode: T,\n clonedNode: T,\n options: Options,\n): T {\n if (isInstanceOfElement(clonedNode, Element)) {\n cloneCSSStyle(nativeNode, clonedNode, options)\n clonePseudoElements(nativeNode, clonedNode, options)\n cloneInputValue(nativeNode, clonedNode)\n cloneSelectValue(nativeNode, clonedNode)\n }\n\n return clonedNode\n}\n\nasync function ensureSVGSymbols<T extends HTMLElement>(\n clone: T,\n options: Options,\n) {\n const uses = clone.querySelectorAll ? clone.querySelectorAll('use') : []\n if (uses.length === 0) {\n return clone\n }\n\n const processedDefs: { [key: string]: HTMLElement } = {}\n for (let i = 0; i < uses.length; i++) {\n const use = uses[i]\n const id = use.getAttribute('xlink:href')\n if (id) {\n const exist = clone.querySelector(id)\n const definition = document.querySelector(id) as HTMLElement\n if (!exist && definition && !processedDefs[id]) {\n // eslint-disable-next-line no-await-in-loop\n processedDefs[id] = (await cloneNode(definition, options, true))!\n }\n }\n }\n\n const nodes = Object.values(processedDefs)\n if (nodes.length) {\n const ns = 'http://www.w3.org/1999/xhtml'\n const svg = document.createElementNS(ns, 'svg')\n svg.setAttribute('xmlns', ns)\n svg.style.position = 'absolute'\n svg.style.width = '0'\n svg.style.height = '0'\n svg.style.overflow = 'hidden'\n svg.style.display = 'none'\n\n const defs = document.createElementNS(ns, 'defs')\n svg.appendChild(defs)\n\n for (let i = 0; i < nodes.length; i++) {\n defs.appendChild(nodes[i])\n }\n\n clone.appendChild(svg)\n }\n\n return clone\n}\n\nexport async function cloneNode<T extends HTMLElement>(\n node: T,\n options: Options,\n isRoot?: boolean,\n): Promise<T | null> {\n if (!isRoot && options.filter && !options.filter(node)) {\n return null\n }\n\n return Promise.resolve(node)\n .then((clonedNode) => cloneSingleNode(clonedNode, options) as Promise<T>)\n .then((clonedNode) => cloneChildren(node, clonedNode, options))\n .then((clonedNode) => decorate(node, clonedNode, options))\n .then((clonedNode) => ensureSVGSymbols(clonedNode, options))\n}\n","import { Options } from './types'\nimport { resolveUrl } from './util'\nimport { getMimeType } from './mimes'\nimport { isDataUrl, makeDataUrl, resourceToDataURL } from './dataurl'\n\nconst URL_REGEX = /url\\((['\"]?)([^'\"]+?)\\1\\)/g\nconst URL_WITH_FORMAT_REGEX = /url\\([^)]+\\)\\s*format\\(([\"']?)([^\"']+)\\1\\)/g\nconst FONT_SRC_REGEX = /src:\\s*(?:url\\([^)]+\\)\\s*format\\([^)]+\\)[,;]\\s*)+/g\n\nfunction toRegex(url: string): RegExp {\n // eslint-disable-next-line no-useless-escape\n const escaped = url.replace(/([.*+?^${}()|\\[\\]\\/\\\\])/g, '\\\\$1')\n return new RegExp(`(url\\\\(['\"]?)(${escaped})(['\"]?\\\\))`, 'g')\n}\n\nexport function parseURLs(cssText: string): string[] {\n const urls: string[] = []\n\n cssText.replace(URL_REGEX, (raw, quotation, url) => {\n urls.push(url)\n return raw\n })\n\n return urls.filter((url) => !isDataUrl(url))\n}\n\nexport async function embed(\n cssText: string,\n resourceURL: string,\n baseURL: string | null,\n options: Options,\n getContentFromUrl?: (url: string) => Promise<string>,\n): Promise<string> {\n try {\n const resolvedURL = baseURL ? resolveUrl(resourceURL, baseURL) : resourceURL\n const contentType = getMimeType(resourceURL)\n let dataURL: string\n if (getContentFromUrl) {\n const content = await getContentFromUrl(resolvedURL)\n dataURL = makeDataUrl(content, contentType)\n } else {\n dataURL = await resourceToDataURL(resolvedURL, contentType, options)\n }\n return cssText.replace(toRegex(resourceURL), `$1${dataURL}$3`)\n } catch (error) {\n // pass\n }\n return cssText\n}\n\nfunction filterPreferredFontFormat(\n str: string,\n { preferredFontFormat }: Options,\n): string {\n return !preferredFontFormat\n ? str\n : str.replace(FONT_SRC_REGEX, (match: string) => {\n // eslint-disable-next-line no-constant-condition\n while (true) {\n const [src, , format] = URL_WITH_FORMAT_REGEX.exec(match) || []\n if (!format) {\n return ''\n }\n\n if (format === preferredFontFormat) {\n return `src: ${src};`\n }\n }\n })\n}\n\nexport function shouldEmbed(url: string): boolean {\n return url.search(URL_REGEX) !== -1\n}\n\nexport async function embedResources(\n cssText: string,\n baseUrl: string | null,\n options: Options,\n): Promise<string> {\n if (!shouldEmbed(cssText)) {\n return cssText\n }\n\n const filteredCSSText = filterPreferredFontFormat(cssText, options)\n const urls = parseURLs(filteredCSSText)\n return urls.reduce(\n (deferred, url) =>\n deferred.then((css) => embed(css, url, baseUrl, options)),\n Promise.resolve(filteredCSSText),\n )\n}\n","import { Options } from './types'\nimport { embedResources } from './embed-resources'\nimport { toArray, isInstanceOfElement } from './util'\nimport { isDataUrl, resourceToDataURL } from './dataurl'\nimport { getMimeType } from './mimes'\n\nasync function embedProp(\n propName: string,\n node: HTMLElement,\n options: Options,\n) {\n const propValue = node.style?.getPropertyValue(propName)\n if (propValue) {\n const cssString = await embedResources(propValue, null, options)\n node.style.setProperty(\n propName,\n cssString,\n node.style.getPropertyPriority(propName),\n )\n return true\n }\n return false\n}\n\nasync function embedBackground<T extends HTMLElement>(\n clonedNode: T,\n options: Options,\n) {\n ;(await embedProp('background', clonedNode, options)) ||\n (await embedProp('background-image', clonedNode, options))\n ;(await embedProp('mask', clonedNode, options)) ||\n (await embedProp('-webkit-mask', clonedNode, options)) ||\n (await embedProp('mask-image', clonedNode, options)) ||\n (await embedProp('-webkit-mask-image', clonedNode, options))\n}\n\nasync function embedImageNode<T extends HTMLElement | SVGImageElement>(\n clonedNode: T,\n options: Options,\n) {\n const isImageElement = isInstanceOfElement(clonedNode, HTMLImageElement)\n\n if (\n !(isImageElement && !isDataUrl(clonedNode.src)) &&\n !(\n isInstanceOfElement(clonedNode, SVGImageElement) &&\n !isDataUrl(clonedNode.href.baseVal)\n )\n ) {\n return\n }\n\n const url = isImageElement ? clonedNode.src : clonedNode.href.baseVal\n\n const dataURL = await resourceToDataURL(url, getMimeType(url), options)\n await new Promise((resolve, reject) => {\n clonedNode.onload = resolve\n clonedNode.onerror = options.onImageErrorHandler\n ? (...attributes) => {\n try {\n resolve(options.onImageErrorHandler!(...attributes))\n } catch (error) {\n reject(error)\n }\n }\n : reject\n\n const image = clonedNode as HTMLImageElement\n if (image.decode) {\n image.decode = resolve as any\n }\n\n if (image.loading === 'lazy') {\n image.loading = 'eager'\n }\n\n if (isImageElement) {\n clonedNode.srcset = ''\n clonedNode.src = dataURL\n } else {\n clonedNode.href.baseVal = dataURL\n }\n })\n}\n\nasync function embedChildren<T extends HTMLElement>(\n clonedNode: T,\n options: Options,\n) {\n const children = toArray<HTMLElement>(clonedNode.childNodes)\n const deferreds = children.map((child) => embedImages(child, options))\n await Promise.all(deferreds).then(() => clonedNode)\n}\n\nexport async function embedImages<T extends HTMLElement>(\n clonedNode: T,\n options: Options,\n) {\n if (isInstanceOfElement(clonedNode, Element)) {\n await embedBackground(clonedNode, options)\n await embedImageNode(clonedNode, options)\n await embedChildren(clonedNode, options)\n }\n}\n","import type { Options } from './types'\n\nexport function applyStyle<T extends HTMLElement>(\n node: T,\n options: Options,\n): T {\n const { style } = node\n\n if (options.backgroundColor) {\n style.backgroundColor = options.backgroundColor\n }\n\n if (options.width) {\n style.width = `${options.width}px`\n }\n\n if (options.height) {\n style.height = `${options.height}px`\n }\n\n const manual = options.style\n if (manual != null) {\n Object.keys(manual).forEach((key: any) => {\n style[key] = manual[key] as string\n })\n }\n\n return node\n}\n","import type { Options } from './types'\nimport { toArray } from './util'\nimport { fetchAsDataURL } from './dataurl'\nimport { shouldEmbed, embedResources } from './embed-resources'\n\ninterface Metadata {\n url: string\n cssText: string\n}\n\nconst cssFetchCache: { [href: string]: Metadata } = {}\n\nasync function fetchCSS(url: string) {\n let cache = cssFetchCache[url]\n if (cache != null) {\n return cache\n }\n\n const res = await fetch(url)\n const cssText = await res.text()\n cache = { url, cssText }\n\n cssFetchCache[url] = cache\n\n return cache\n}\n\nasync function embedFonts(data: Metadata, options: Options): Promise<string> {\n let cssText = data.cssText\n const regexUrl = /url\\([\"']?([^\"')]+)[\"']?\\)/g\n const fontLocs = cssText.match(/url\\([^)]+\\)/g) || []\n const loadFonts = fontLocs.map(async (loc: string) => {\n let url = loc.replace(regexUrl, '$1')\n if (!url.startsWith('https://')) {\n url = new URL(url, data.url).href\n }\n\n return fetchAsDataURL<[string, string]>(\n url,\n options.fetchRequestInit,\n ({ result }) => {\n cssText = cssText.replace(loc, `url(${result})`)\n return [loc, result]\n },\n )\n })\n\n return Promise.all(loadFonts).then(() => cssText)\n}\n\nfunction parseCSS(source: string) {\n if (source == null) {\n return []\n }\n\n const result: string[] = []\n const commentsRegex = /(\\/\\*[\\s\\S]*?\\*\\/)/gi\n // strip out comments\n let cssText = source.replace(commentsRegex, '')\n\n // eslint-disable-next-line prefer-regex-literals\n const keyframesRegex = new RegExp(\n '((@.*?keyframes [\\\\s\\\\S]*?){([\\\\s\\\\S]*?}\\\\s*?)})',\n 'gi',\n )\n\n // eslint-disable-next-line no-constant-condition\n while (true) {\n const matches = keyframesRegex.exec(cssText)\n if (matches === null) {\n break\n }\n result.push(matches[0])\n }\n cssText = cssText.replace(keyframesRegex, '')\n\n const importRegex = /@import[\\s\\S]*?url\\([^)]*\\)[\\s\\S]*?;/gi\n // to match css & media queries together\n const combinedCSSRegex =\n '((\\\\s*?(?:\\\\/\\\\*[\\\\s\\\\S]*?\\\\*\\\\/)?\\\\s*?@media[\\\\s\\\\S]' +\n '*?){([\\\\s\\\\S]*?)}\\\\s*?})|(([\\\\s\\\\S]*?){([\\\\s\\\\S]*?)})'\n // unified regex\n const unifiedRegex = new RegExp(combinedCSSRegex, 'gi')\n\n // eslint-disable-next-line no-constant-condition\n while (true) {\n let matches = importRegex.exec(cssText)\n if (matches === null) {\n matches = unifiedRegex.exec(cssText)\n if (matches === null) {\n break\n } else {\n importRegex.lastIndex = unifiedRegex.lastIndex\n }\n } else {\n unifiedRegex.lastIndex = importRegex.lastIndex\n }\n result.push(matches[0])\n }\n\n return result\n}\n\nasync function getCSSRules(\n styleSheets: CSSStyleSheet[],\n options: Options,\n): Promise<CSSStyleRule[]> {\n const ret: CSSStyleRule[] = []\n const deferreds: Promise<number | void>[] = []\n\n // First loop inlines imports\n styleSheets.forEach((sheet) => {\n if ('cssRules' in sheet) {\n try {\n toArray<CSSRule>(sheet.cssRules || []).forEach((item, index) => {\n if (item.type === CSSRule.IMPORT_RULE) {\n let importIndex = index + 1\n const url = (item as CSSImportRule).href\n const deferred = fetchCSS(url)\n .then((metadata) => embedFonts(metadata, options))\n .then((cssText) =>\n parseCSS(cssText).forEach((rule) => {\n try {\n sheet.insertRule(\n rule,\n rule.startsWith('@import')\n ? (importIndex += 1)\n : sheet.cssRules.length,\n )\n } catch (error) {\n console.error('Error inserting rule from remote css', {\n rule,\n error,\n })\n }\n }),\n )\n .catch((e) => {\n console.error('Error loading remote css', e.toString())\n })\n\n deferreds.push(deferred)\n }\n })\n } catch (e) {\n const inline =\n styleSheets.find((a) => a.href == null) || document.styleSheets[0]\n if (sheet.href != null) {\n deferreds.push(\n fetchCSS(sheet.href)\n .then((metadata) => embedFonts(metadata, options))\n .then((cssText) =>\n parseCSS(cssText).forEach((rule) => {\n inline.insertRule(rule, inline.cssRules.length)\n }),\n )\n .catch((err: unknown) => {\n console.error('Error loading remote stylesheet', err)\n }),\n )\n }\n console.error('Error inlining remote css file', e)\n }\n }\n })\n\n return Promise.all(deferreds).then(() => {\n // Second loop parses rules\n styleSheets.forEach((sheet) => {\n if ('cssRules' in sheet) {\n try {\n toArray<CSSStyleRule>(sheet.cssRules || []).forEach((item) => {\n ret.push(item)\n })\n } catch (e) {\n console.error(`Error while reading CSS rules from ${sheet.href}`, e)\n }\n }\n })\n\n return ret\n })\n}\n\nfunction getWebFontRules(cssRules: CSSStyleRule[]): CSSStyleRule[] {\n return cssRules\n .filter((rule) => rule.type === CSSRule.FONT_FACE_RULE)\n .filter((rule) => shouldEmbed(rule.style.getPropertyValue('src')))\n}\n\nasync function parseWebFontRules<T extends HTMLElement>(\n node: T,\n options: Options,\n) {\n if (node.ownerDocument == null) {\n throw new Error('Provided element is not within a Document')\n }\n\n const styleSheets = toArray<CSSStyleSheet>(node.ownerDocument.styleSheets)\n const cssRules = await getCSSRules(styleSheets, options)\n\n return getWebFontRules(cssRules)\n}\n\nfunction normalizeFontFamily(font: string) {\n return font.trim().replace(/[\"']/g, '')\n}\n\nfunction getUsedFonts(node: HTMLElement) {\n const fonts = new Set<string>()\n function traverse(node: HTMLElement) {\n const fontFamily =\n node.style.fontFamily || getComputedStyle(node).fontFamily\n fontFamily.split(',').forEach((font) => {\n fonts.add(normalizeFontFamily(font))\n })\n\n Array.from(node.children).forEach((child) => {\n if (child instanceof HTMLElement) {\n traverse(child)\n }\n })\n }\n traverse(node)\n return fonts\n}\n\nexport async function getWebFontCSS<T extends HTMLElement>(\n node: T,\n options: Options,\n): Promise<string> {\n const rules = await parseWebFontRules(node, options)\n const usedFonts = getUsedFonts(node)\n const cssTexts = await Promise.all(\n rules\n .filter((rule) =>\n usedFonts.has(normalizeFontFamily(rule.style.fontFamily)),\n )\n .map((rule) => {\n const baseUrl = rule.parentStyleSheet\n ? rule.parentStyleSheet.href\n : null\n return embedResources(rule.cssText, baseUrl, options)\n }),\n )\n\n return cssTexts.join('\\n')\n}\n\nexport async function embedWebFonts<T extends HTMLElement>(\n clonedNode: T,\n options: Options,\n) {\n const cssText =\n options.fontEmbedCSS != null\n ? options.fontEmbedCSS\n : options.skipFonts\n ? null\n : await getWebFontCSS(clonedNode, options)\n\n if (cssText) {\n const styleNode = document.createElement('style')\n const sytleContent = document.createTextNode(cssText)\n\n styleNode.appendChild(sytleContent)\n\n if (clonedNode.firstChild) {\n clonedNode.insertBefore(styleNode, clonedNode.firstChild)\n } else {\n clonedNode.appendChild(styleNode)\n }\n }\n}\n","import { Options } from './types'\nimport { cloneNode } from './clone-node'\nimport { embedImages } from './embed-images'\nimport { applyStyle } from './apply-style'\nimport { embedWebFonts, getWebFontCSS } from './embed-webfonts'\nimport {\n getImageSize,\n getPixelRatio,\n createImage,\n canvasToBlob,\n nodeToDataURL,\n checkCanvasDimensions,\n} from './util'\n\nexport async function toSvg<T extends HTMLElement>(\n node: T,\n options: Options = {},\n): Promise<string> {\n const { width, height } = getImageSize(node, options)\n const clonedNode = (await cloneNode(node, options, true)) as HTMLElement\n await embedWebFonts(clonedNode, options)\n await embedImages(clonedNode, options)\n applyStyle(clonedNode, options)\n const datauri = await nodeToDataURL(clonedNode, width, height)\n return datauri\n}\n\nexport async function toCanvas<T extends HTMLElement>(\n node: T,\n options: Options = {},\n): Promise<HTMLCanvasElement> {\n const { width, height } = getImageSize(node, options)\n const svg = await toSvg(node, options)\n const img = await createImage(svg)\n\n const canvas = document.createElement('canvas')\n const context = canvas.getContext('2d')!\n const ratio = options.pixelRatio || getPixelRatio()\n const canvasWidth = options.canvasWidth || width\n const canvasHeight = options.canvasHeight || height\n\n canvas.width = canvasWidth * ratio\n canvas.height = canvasHeight * ratio\n\n if (!options.skipAutoScale) {\n checkCanvasDimensions(canvas)\n }\n canvas.style.width = `${canvasWidth}`\n canvas.style.height = `${canvasHeight}`\n\n if (options.backgroundColor) {\n context.fillStyle = options.backgroundColor\n context.fillRect(0, 0, canvas.width, canvas.height)\n }\n\n context.drawImage(img, 0, 0, canvas.width, canvas.height)\n\n return canvas\n}\n\nexport async function toPixelData<T extends HTMLElement>(\n node: T,\n options: Options = {},\n): Promise<Uint8ClampedArray> {\n const { width, height } = getImageSize(node, options)\n const canvas = await toCanvas(node, options)\n const ctx = canvas.getContext('2d')!\n return ctx.getImageData(0, 0, width, height).data\n}\n\nexport async function toPng<T extends HTMLElement>(\n node: T,\n options: Options = {},\n): Promise<string> {\n const canvas = await toCanvas(node, options)\n return canvas.toDataURL()\n}\n\nexport async function toJpeg<T extends HTMLElement>(\n node: T,\n options: Options = {},\n): Promise<string> {\n const canvas = await toCanvas(node, options)\n return canvas.toDataURL('image/jpeg', options.quality || 1)\n}\n\nexport async function toBlob<T extends HTMLElement>(\n node: T,\n options: Options = {},\n): Promise<Blob | null> {\n const canvas = await toCanvas(node, options)\n const blob = await canvasToBlob(canvas)\n return blob\n}\n\nexport async function getFontEmbedCSS<T extends HTMLElement>(\n node: T,\n options: Options = {},\n): Promise<string> {\n return getWebFontCSS(node, options)\n}\n","import { toPng } from 'html-to-image'\n\n/** Capture a DOM element as a base64 PNG data URL */\nexport async function captureElement(el: Element): Promise<string | null> {\n try {\n return await toPng(el as HTMLElement, {\n cacheBust: true,\n pixelRatio: 2,\n skipFonts: true,\n filter: (node: HTMLElement) => {\n // Skip instruckt UI elements from the capture\n if (node.getAttribute?.('data-instruckt')) return false\n // Skip cross-origin link elements (external stylesheets cause SecurityError)\n if (node.tagName === 'LINK' && node.getAttribute('rel') === 'stylesheet') {\n const href = node.getAttribute('href') ?? ''\n if (href.startsWith('http') && !href.startsWith(window.location.origin)) return false\n }\n return true\n },\n })\n } catch {\n return null\n }\n}\n\n/** Capture a rectangular region of the viewport as a base64 PNG data URL */\nexport async function captureRegion(rect: DOMRect): Promise<string | null> {\n try {\n const full = await toPng(document.body, {\n cacheBust: true,\n pixelRatio: 2,\n skipFonts: true,\n filter: (node: HTMLElement) => {\n if (node.getAttribute?.('data-instruckt')) return false\n if (node.tagName === 'LINK' && node.getAttribute('rel') === 'stylesheet') {\n const href = node.getAttribute('href') ?? ''\n if (href.startsWith('http') && !href.startsWith(window.location.origin)) return false\n }\n return true\n },\n })\n\n // Crop the full capture to the selected region\n return await cropImage(full, rect)\n } catch {\n return null\n }\n}\n\n/** Crop a data URL image to a rectangle */\nfunction cropImage(dataUrl: string, rect: DOMRect): Promise<string> {\n return new Promise((resolve, reject) => {\n const img = new Image()\n img.onload = () => {\n const ratio = 2 // matches pixelRatio above\n const canvas = document.createElement('canvas')\n canvas.width = rect.width * ratio\n canvas.height = rect.height * ratio\n const ctx = canvas.getContext('2d')!\n ctx.drawImage(\n img,\n rect.x * ratio, rect.y * ratio,\n rect.width * ratio, rect.height * ratio,\n 0, 0,\n rect.width * ratio, rect.height * ratio,\n )\n resolve(canvas.toDataURL('image/png'))\n }\n img.onerror = reject\n img.src = dataUrl\n })\n}\n\n/** Interactive region selector — returns the selected DOMRect or null if cancelled */\nexport function selectRegion(): Promise<DOMRect | null> {\n return new Promise((resolve) => {\n const overlay = document.createElement('div')\n Object.assign(overlay.style, {\n position: 'fixed',\n inset: '0',\n zIndex: '2147483647',\n cursor: 'crosshair',\n background: 'rgba(0,0,0,0.1)',\n })\n overlay.setAttribute('data-instruckt', 'region-select')\n\n const box = document.createElement('div')\n Object.assign(box.style, {\n position: 'fixed',\n border: '2px dashed #6366f1',\n background: 'rgba(99,102,241,0.08)',\n borderRadius: '4px',\n display: 'none',\n pointerEvents: 'none',\n })\n overlay.appendChild(box)\n\n let startX = 0, startY = 0, dragging = false\n\n const onMouseDown = (e: MouseEvent) => {\n startX = e.clientX\n startY = e.clientY\n dragging = true\n box.style.display = 'block'\n updateBox(e)\n }\n\n const onMouseMove = (e: MouseEvent) => {\n if (!dragging) return\n updateBox(e)\n }\n\n const updateBox = (e: MouseEvent) => {\n const x = Math.min(startX, e.clientX)\n const y = Math.min(startY, e.clientY)\n const w = Math.abs(e.clientX - startX)\n const h = Math.abs(e.clientY - startY)\n Object.assign(box.style, {\n left: `${x}px`,\n top: `${y}px`,\n width: `${w}px`,\n height: `${h}px`,\n })\n }\n\n const onMouseUp = (e: MouseEvent) => {\n if (!dragging) return\n dragging = false\n const x = Math.min(startX, e.clientX)\n const y = Math.min(startY, e.clientY)\n const w = Math.abs(e.clientX - startX)\n const h = Math.abs(e.clientY - startY)\n cleanup()\n if (w < 10 || h < 10) {\n resolve(null)\n } else {\n resolve(new DOMRect(x, y, w, h))\n }\n }\n\n const onKeyDown = (e: KeyboardEvent) => {\n if (e.key === 'Escape') {\n cleanup()\n resolve(null)\n }\n }\n\n const cleanup = () => {\n overlay.remove()\n document.removeEventListener('keydown', onKeyDown, true)\n }\n\n overlay.addEventListener('mousedown', onMouseDown)\n overlay.addEventListener('mousemove', onMouseMove)\n overlay.addEventListener('mouseup', onMouseUp)\n document.addEventListener('keydown', onKeyDown, true)\n document.body.appendChild(overlay)\n })\n}\n","import type { Annotation, PendingAnnotation } from '../types'\nimport { POPUP_CSS } from './styles'\nimport { captureElement } from './screenshot'\n\ninterface PopupResult {\n comment: string\n screenshot?: string\n}\n\ninterface PopupCallbacks {\n onSubmit: (result: PopupResult) => void\n onCancel: () => void\n}\n\ninterface EditCallbacks {\n onSave: (annotation: Annotation, newComment: string) => void\n onDelete: (annotation: Annotation) => void\n}\n\n/** Resolve screenshot URL from annotation data */\nfunction screenshotUrl(screenshot: string | undefined, endpoint?: string): string | null {\n if (!screenshot) return null\n if (screenshot.startsWith('data:')) return screenshot\n // Backend path like \"screenshots/01ABC.png\" — serve via endpoint\n const base = endpoint ?? '/instruckt'\n return `${base}/${screenshot}`\n}\n\nfunction esc(s: string): string {\n return String(s ?? '').replace(/&/g, '&').replace(/</g, '<').replace(/>/g, '>').replace(/\"/g, '"')\n}\n\n/** Annotation popup — rendered in its own shadow DOM for CSS isolation */\nexport class AnnotationPopup {\n private host: HTMLElement | null = null\n private shadow: ShadowRoot | null = null\n\n // ── New annotation popup ──────────────────────────────────────\n\n showNew(pending: PendingAnnotation, callbacks: PopupCallbacks): void {\n this.destroy()\n this.host = document.createElement('div')\n this.host.setAttribute('data-instruckt', 'popup')\n this.stopHostPropagation(this.host)\n this.shadow = this.host.attachShadow({ mode: 'open' })\n\n const style = document.createElement('style')\n style.textContent = POPUP_CSS\n this.shadow.appendChild(style)\n\n const popup = document.createElement('div')\n popup.className = 'popup'\n\n const fwBadge = pending.framework\n ? `<div class=\"fw-badge\">${esc(pending.framework.component)}</div>`\n : ''\n const selText = pending.selectedText\n ? `<div class=\"selected-text\">\"${esc(pending.selectedText.slice(0, 80))}\"</div>`\n : ''\n const hasScreenshot = !!pending.screenshot\n\n popup.innerHTML = `\n <div class=\"header\">\n <span class=\"element-tag\" title=\"${esc(pending.elementPath)}\">${esc(pending.elementLabel)}</span>\n <button class=\"close-btn\" title=\"Cancel (Esc)\">✕</button>\n </div>\n ${fwBadge}${selText}\n <div class=\"screenshot-slot\">${hasScreenshot\n ? `<div class=\"screenshot-preview\"><img src=\"${pending.screenshot}\" alt=\"Screenshot\" /><button class=\"screenshot-remove\" title=\"Remove screenshot\">✕</button></div>`\n : `<button class=\"btn-capture\" data-action=\"capture\"><svg width=\"14\" height=\"14\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M23 19a2 2 0 0 1-2 2H3a2 2 0 0 1-2-2V8a2 2 0 0 1 2-2h4l2-3h6l2 3h4a2 2 0 0 1 2 2z\"/><circle cx=\"12\" cy=\"13\" r=\"4\"/></svg> Capture screenshot</button>`\n }</div>\n <textarea placeholder=\"${hasScreenshot ? 'Add a note (optional)' : 'What needs to change here?'}\" rows=\"3\"></textarea>\n <div class=\"actions\">\n <button class=\"btn-secondary\" data-action=\"cancel\">Cancel</button>\n <button class=\"btn-primary\" data-action=\"submit\" ${hasScreenshot ? '' : 'disabled'}>Add note</button>\n </div>\n `\n\n let currentScreenshot = pending.screenshot ?? null\n const textarea = popup.querySelector('textarea')!\n const submitBtn = popup.querySelector<HTMLButtonElement>('[data-action=\"submit\"]')!\n const screenshotSlot = popup.querySelector('.screenshot-slot')!\n\n const updateSubmitState = () => {\n submitBtn.disabled = !currentScreenshot && textarea.value.trim().length === 0\n }\n\n const attachScreenshotEvents = () => {\n // Capture button\n const captureBtn = screenshotSlot.querySelector('[data-action=\"capture\"]')\n captureBtn?.addEventListener('click', async () => {\n captureBtn.textContent = 'Capturing...'\n const dataUrl = await captureElement(pending.element)\n if (dataUrl) {\n currentScreenshot = dataUrl\n screenshotSlot.innerHTML = `<div class=\"screenshot-preview\"><img src=\"${dataUrl}\" alt=\"Screenshot\" /><button class=\"screenshot-remove\" title=\"Remove screenshot\">✕</button></div>`\n textarea.placeholder = 'Add a note (optional)'\n attachScreenshotEvents()\n updateSubmitState()\n } else {\n captureBtn.textContent = 'Capture failed'\n setTimeout(() => { if (captureBtn.parentElement) captureBtn.innerHTML = `<svg width=\"14\" height=\"14\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M23 19a2 2 0 0 1-2 2H3a2 2 0 0 1-2-2V8a2 2 0 0 1 2-2h4l2-3h6l2 3h4a2 2 0 0 1 2 2z\"/><circle cx=\"12\" cy=\"13\" r=\"4\"/></svg> Capture screenshot` }, 1500)\n }\n })\n\n // Remove button\n const removeBtn = screenshotSlot.querySelector('.screenshot-remove')\n removeBtn?.addEventListener('click', () => {\n currentScreenshot = null\n screenshotSlot.innerHTML = `<button class=\"btn-capture\" data-action=\"capture\"><svg width=\"14\" height=\"14\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M23 19a2 2 0 0 1-2 2H3a2 2 0 0 1-2-2V8a2 2 0 0 1 2-2h4l2-3h6l2 3h4a2 2 0 0 1 2 2z\"/><circle cx=\"12\" cy=\"13\" r=\"4\"/></svg> Capture screenshot</button>`\n textarea.placeholder = 'What needs to change here?'\n attachScreenshotEvents()\n updateSubmitState()\n })\n }\n\n attachScreenshotEvents()\n\n textarea.addEventListener('input', updateSubmitState)\n textarea.addEventListener('keydown', (e) => {\n // Stop ALL keyboard events from reaching page forms (React, Inertia, etc.)\n e.stopPropagation()\n if (e.key === 'Enter' && !e.shiftKey) {\n e.preventDefault()\n if (!submitBtn.disabled) submitBtn.click()\n }\n if (e.key === 'Escape') { callbacks.onCancel(); this.destroy() }\n })\n\n popup.querySelector('[data-action=\"cancel\"]')!.addEventListener('click', () => {\n callbacks.onCancel(); this.destroy()\n })\n popup.querySelector('.close-btn')!.addEventListener('click', () => {\n callbacks.onCancel(); this.destroy()\n })\n submitBtn.addEventListener('click', () => {\n const comment = textarea.value.trim()\n if (!comment && !currentScreenshot) return\n callbacks.onSubmit({ comment: comment || '(screenshot)', screenshot: currentScreenshot ?? undefined })\n this.destroy()\n })\n\n this.shadow.appendChild(popup)\n ;(document.getElementById('instruckt-root') ?? document.body).appendChild(this.host)\n\n this.positionHost(pending.x, pending.y)\n this.setupOutsideClick()\n textarea.focus()\n }\n\n // ── Edit existing annotation ──────────────────────────────────\n\n showEdit(annotation: Annotation, callbacks: EditCallbacks, endpoint?: string): void {\n this.destroy()\n this.host = document.createElement('div')\n this.host.setAttribute('data-instruckt', 'popup')\n this.stopHostPropagation(this.host)\n this.shadow = this.host.attachShadow({ mode: 'open' })\n\n const style = document.createElement('style')\n style.textContent = POPUP_CSS\n this.shadow.appendChild(style)\n\n const popup = document.createElement('div')\n popup.className = 'popup'\n\n const fwBadge = annotation.framework\n ? `<div class=\"fw-badge\">${esc(annotation.framework.component)}</div>`\n : ''\n const ssUrl = screenshotUrl(annotation.screenshot, endpoint)\n const screenshotPreview = ssUrl\n ? `<div class=\"screenshot-preview screenshot-slot\"><img src=\"${ssUrl}\" alt=\"Screenshot\" /><button class=\"screenshot-remove\" title=\"Remove screenshot\">✕</button></div>`\n : ''\n const commentText = annotation.comment === '(screenshot)' ? '' : annotation.comment\n\n popup.innerHTML = `\n <div class=\"header\">\n <span class=\"element-tag\" title=\"${esc(annotation.elementPath)}\">${esc(annotation.element)}</span>\n <button class=\"close-btn\">✕</button>\n </div>\n ${fwBadge}${screenshotPreview}\n <textarea rows=\"3\">${esc(commentText)}</textarea>\n <div class=\"actions\">\n <button class=\"btn-danger\" data-action=\"delete\">Remove</button>\n <button class=\"btn-primary\" data-action=\"save\">Save</button>\n </div>\n `\n\n popup.querySelector('.close-btn')!.addEventListener('click', () => this.destroy())\n\n // Screenshot remove button\n const ssRemoveBtn = popup.querySelector('.screenshot-remove')\n ssRemoveBtn?.addEventListener('click', () => {\n callbacks.onSave(annotation, annotation.comment)\n // Remove screenshot visually\n const slot = popup.querySelector('.screenshot-slot')\n if (slot) slot.remove()\n })\n\n const textarea = popup.querySelector('textarea')!\n const saveBtn = popup.querySelector<HTMLButtonElement>('[data-action=\"save\"]')!\n const deleteBtn = popup.querySelector<HTMLButtonElement>('[data-action=\"delete\"]')!\n\n textarea.addEventListener('keydown', (e) => {\n e.stopPropagation()\n if (e.key === 'Enter' && !e.shiftKey) {\n e.preventDefault()\n saveBtn.click()\n }\n if (e.key === 'Escape') this.destroy()\n })\n\n saveBtn.addEventListener('click', () => {\n const newComment = textarea.value.trim()\n if (!newComment) return\n callbacks.onSave(annotation, newComment)\n this.destroy()\n })\n\n deleteBtn.addEventListener('click', () => {\n callbacks.onDelete(annotation)\n this.destroy()\n })\n\n this.shadow.appendChild(popup)\n ;(document.getElementById('instruckt-root') ?? document.body).appendChild(this.host)\n\n // Position near the marker\n const markerX = (annotation.x / 100) * window.innerWidth\n const markerY = annotation.y - window.scrollY\n this.positionHost(markerX, markerY)\n this.setupOutsideClick()\n textarea.focus()\n textarea.setSelectionRange(textarea.value.length, textarea.value.length)\n }\n\n // ── Helpers ───────────────────────────────────────────────────\n\n /** Prevent popup interactions from reaching page handlers (e.g. @click.outside, form submit) */\n private stopHostPropagation(host: HTMLElement): void {\n for (const evt of ['click', 'mousedown', 'pointerdown', 'keydown', 'keyup', 'keypress', 'submit'] as const) {\n host.addEventListener(evt, (e) => e.stopPropagation())\n }\n }\n\n private positionHost(x: number, y: number): void {\n if (!this.host) return\n // Use popover=\"manual\" to render in the top layer (above native popovers)\n this.host.setAttribute('popover', 'manual')\n try { this.host.showPopover() } catch { /* fallback to z-index */ }\n Object.assign(this.host.style, { position: 'fixed', zIndex: '2147483647', left: '-9999px', top: '0' })\n\n requestAnimationFrame(() => {\n if (!this.host) return\n const w = 340 + 20\n const h = this.host.querySelector('.popup')?.getBoundingClientRect().height ?? 300\n const vw = window.innerWidth\n const vh = window.innerHeight\n const left = Math.max(10, Math.min(x + 10, vw - w))\n const top = Math.max(10, Math.min(y + 10, vh - h - 10))\n Object.assign(this.host.style, { left: `${left}px`, top: `${top}px` })\n })\n }\n\n private boundOutside = (e: MouseEvent): void => {\n if (this.host && !this.host.contains(e.target as Node)) {\n this.destroy()\n }\n }\n\n private setupOutsideClick(): void {\n setTimeout(() => document.addEventListener('mousedown', this.boundOutside), 0)\n }\n\n destroy(): void {\n this.host?.remove()\n this.host = null\n this.shadow = null\n document.removeEventListener('mousedown', this.boundOutside)\n }\n}\n","import type { Annotation } from '../types'\n\ntype MarkerClickHandler = (annotation: Annotation) => void\n\ninterface MarkerEl {\n el: HTMLElement\n annotationId: string\n}\n\n/** Manages numbered annotation pins rendered directly on the page */\nexport class AnnotationMarkers {\n private container: HTMLElement\n private markers: Map<string, MarkerEl> = new Map()\n\n constructor(private readonly onClick: MarkerClickHandler) {\n // Fixed-position container over the page, pointer-events passthrough\n this.container = document.createElement('div')\n Object.assign(this.container.style, {\n position: 'fixed',\n inset: '0',\n pointerEvents: 'none',\n zIndex: '2147483645',\n })\n this.container.setAttribute('data-instruckt', 'markers')\n const root = document.getElementById('instruckt-root') ?? document.body\n root.appendChild(this.container)\n }\n\n /** Add or update a marker for an annotation */\n upsert(annotation: Annotation, index: number): void {\n const existing = this.markers.get(annotation.id)\n\n if (existing) {\n this.updateStyle(existing.el, annotation)\n return\n }\n\n const el = document.createElement('div')\n const ssClass = annotation.screenshot ? ' has-screenshot' : ''\n el.className = `ik-marker ${this.statusClass(annotation.status)}${ssClass}`\n el.textContent = String(index)\n el.title = annotation.comment === '(screenshot)' ? 'Screenshot' : annotation.comment.slice(0, 60)\n el.style.pointerEvents = 'all'\n\n // Position: annotation.x is % of viewport width, annotation.y is px from top (scroll-adjusted)\n // Convert back to viewport-relative for fixed positioning\n el.style.left = `${(annotation.x / 100) * window.innerWidth}px`\n el.style.top = `${annotation.y - window.scrollY}px`\n\n el.addEventListener('click', (e) => {\n e.stopPropagation()\n this.onClick(annotation)\n })\n\n this.container.appendChild(el)\n this.markers.set(annotation.id, { el, annotationId: annotation.id })\n }\n\n /** Update an existing marker after its annotation status changed */\n update(annotation: Annotation): void {\n const marker = this.markers.get(annotation.id)\n if (!marker) return\n this.updateStyle(marker.el, annotation)\n }\n\n private updateStyle(el: HTMLElement, annotation: Annotation): void {\n const ssClass = annotation.screenshot ? ' has-screenshot' : ''\n el.className = `ik-marker ${this.statusClass(annotation.status)}${ssClass}`\n el.title = annotation.comment === '(screenshot)' ? 'Screenshot' : annotation.comment.slice(0, 60)\n }\n\n private statusClass(status: string): string {\n if (status === 'resolved') return 'resolved'\n if (status === 'dismissed') return 'dismissed'\n return ''\n }\n\n /** Reposition all markers (e.g. after scroll or resize) */\n reposition(annotations: Annotation[]): void {\n annotations.forEach(annotation => {\n const marker = this.markers.get(annotation.id)\n if (!marker) return\n marker.el.style.left = `${(annotation.x / 100) * window.innerWidth}px`\n marker.el.style.top = `${annotation.y - window.scrollY}px`\n })\n }\n\n remove(annotationId: string): void {\n const marker = this.markers.get(annotationId)\n if (!marker) return\n marker.el.remove()\n this.markers.delete(annotationId)\n }\n\n /** Show or hide all markers */\n setVisible(visible: boolean): void {\n this.container.style.display = visible ? '' : 'none'\n }\n\n /** Remove all markers without destroying the container */\n clear(): void {\n for (const { el } of this.markers.values()) {\n el.remove()\n }\n this.markers.clear()\n }\n\n destroy(): void {\n this.container.remove()\n this.markers.clear()\n }\n}\n","/**\n * CSS selector and element path generation.\n * Produces unique, grep-able selectors for any DOM element.\n */\n\n/** Build a unique CSS selector for an element */\nexport function getElementSelector(el: Element): string {\n if (el.id) {\n return `#${CSS.escape(el.id)}`\n }\n\n const path: string[] = []\n let current: Element | null = el\n\n while (current && current !== document.documentElement) {\n const tag = current.tagName.toLowerCase()\n const parent: Element | null = current.parentElement\n\n if (!parent) {\n path.unshift(tag)\n break\n }\n\n // Try unique class combo\n const classes = Array.from(current.classList)\n .filter(c => !c.match(/^(hover|focus|active|visited|is-|has-)/)) // skip state classes\n .slice(0, 3)\n\n if (classes.length > 0) {\n const classSelector = `${tag}.${classes.map(CSS.escape).join('.')}`\n const matches = parent.querySelectorAll(classSelector)\n if (matches.length === 1) {\n path.unshift(classSelector)\n break\n }\n }\n\n // Fall back to nth-child\n const siblings = Array.from(parent.children).filter((c: Element) => c.tagName === current!.tagName)\n if (siblings.length === 1) {\n path.unshift(tag)\n } else {\n const index = siblings.indexOf(current) + 1\n path.unshift(`${tag}:nth-of-type(${index})`)\n }\n\n current = parent\n }\n\n return path.join(' > ')\n}\n\n/** Short element identifier for markdown output (grep-friendly) */\nexport function getElementName(el: Element): string {\n const tag = el.tagName.toLowerCase()\n\n const wireModel = el.getAttribute('wire:model') || el.getAttribute('wire:click')\n if (wireModel) return `${tag}[wire:${wireModel.split('.')[0]}]`\n\n if (el.id) return `${tag}#${el.id}`\n\n const firstClass = el.classList[0]\n if (firstClass) return `${tag}.${firstClass}`\n\n return tag\n}\n\n/** Human-readable HTML-like label for the popup UI */\nexport function getElementLabel(el: Element): string {\n const tag = el.tagName.toLowerCase()\n const text = (el.textContent || '').trim().replace(/\\s+/g, ' ').slice(0, 40)\n\n // Build a short opening tag with key attributes\n const attrs: string[] = []\n if (el.id) attrs.push(`id=\"${el.id}\"`)\n const role = el.getAttribute('role')\n if (role) attrs.push(`role=\"${role}\"`)\n const wireAttr = el.getAttribute('wire:model') || el.getAttribute('wire:click')\n if (wireAttr) attrs.push(`wire:${el.hasAttribute('wire:model') ? 'model' : 'click'}=\"${wireAttr}\"`)\n\n const attrStr = attrs.length ? ' ' + attrs.join(' ') : ''\n const openTag = `<${tag}${attrStr}>`\n\n if (text) return `${openTag} ${text}`\n return openTag\n}\n\n/** Get nearby readable text for context */\nexport function getNearbyText(el: Element): string {\n const text = (el.textContent || '').trim().replace(/\\s+/g, ' ')\n return text.slice(0, 120)\n}\n\n/** CSS classes as a space-separated string, filtering noise */\nexport function getCssClasses(el: Element): string {\n return Array.from(el.classList)\n .filter(c => !c.match(/^(instruckt-)/)) // exclude our own classes\n .join(' ')\n}\n\n/** Get bounding box relative to the page */\nexport function getPageBoundingBox(el: Element): { x: number; y: number; width: number; height: number } {\n const rect = el.getBoundingClientRect()\n return {\n x: rect.left + window.scrollX,\n y: rect.top + window.scrollY,\n width: rect.width,\n height: rect.height,\n }\n}\n","import type { FrameworkContext } from '../types'\n\ndeclare global {\n interface Window {\n Livewire?: { find(id: string): unknown }\n }\n}\n\nexport function isAvailable(): boolean {\n return typeof window.Livewire !== 'undefined'\n}\n\n/** Walk up the DOM from el to find the nearest wire:id ancestor */\nexport function detect(el: Element): Element | null {\n let node: Element | null = el\n while (node && node !== document.documentElement) {\n if (node.getAttribute('wire:id')) return node\n node = node.parentElement\n }\n return null\n}\n\n/** Get Livewire component context for an element */\nexport function getContext(el: Element): FrameworkContext | null {\n if (!isAvailable()) return null\n\n const wireEl = detect(el)\n if (!wireEl) return null\n\n const wireId = wireEl.getAttribute('wire:id')!\n\n // In Livewire v3, the component name lives in the wire:snapshot attribute\n let componentName = 'Unknown'\n const snapshotAttr = wireEl.getAttribute('wire:snapshot')\n if (snapshotAttr) {\n try {\n const snapshot = JSON.parse(snapshotAttr)\n componentName = snapshot?.memo?.name ?? 'Unknown'\n } catch {\n // malformed snapshot\n }\n }\n\n return {\n framework: 'livewire',\n component: componentName,\n wire_id: wireId,\n }\n}\n","import type { FrameworkContext } from '../types'\n\ninterface VueInstance {\n $options?: { name?: string; __name?: string }\n type?: { name?: string; __name?: string }\n uid?: number\n props?: Record<string, unknown>\n setupState?: Record<string, unknown>\n}\n\ninterface VueElement extends Element {\n __vue__?: VueInstance\n __vueParentComponent?: VueInstance\n _vei?: unknown\n}\n\nexport function isAvailable(): boolean {\n // Vue 3: mounts with data-v-app attribute; Vue 2: exposes global Vue constructor\n return !!(document.querySelector('[data-v-app]') || (window as unknown as Record<string, unknown>)['Vue'])\n}\n\n/** Walk up the DOM to find the nearest Vue component */\nexport function detect(el: Element): VueInstance | null {\n let node: VueElement | null = el as VueElement\n while (node && node !== document.documentElement) {\n const instance = node.__vueParentComponent ?? node.__vue__\n if (instance) return instance\n node = node.parentElement as VueElement | null\n }\n return null\n}\n\n/** Get Vue component context for an element */\nexport function getContext(el: Element): FrameworkContext | null {\n const instance = detect(el)\n if (!instance) return null\n\n // Support Vue 2 ($options.name) and Vue 3 (type.name or type.__name)\n const name =\n instance.$options?.name ??\n instance.$options?.__name ??\n instance.type?.name ??\n instance.type?.__name ??\n 'Anonymous'\n\n const data: Record<string, unknown> = {}\n\n // Vue 3 props\n if (instance.props) {\n Object.assign(data, instance.props)\n }\n\n // Vue 3 setup state (public reactive refs)\n if (instance.setupState) {\n for (const [key, value] of Object.entries(instance.setupState)) {\n if (!key.startsWith('_') && typeof value !== 'function') {\n try {\n data[key] = JSON.parse(JSON.stringify(value))\n } catch {\n data[key] = String(value)\n }\n }\n }\n }\n\n return {\n framework: 'vue',\n component: name,\n component_uid: instance.uid !== undefined ? String(instance.uid) : undefined,\n data,\n }\n}\n","import type { FrameworkContext } from '../types'\n\ninterface SvelteMeta {\n loc?: { file?: string }\n ctx?: unknown[]\n}\n\ninterface SvelteElement extends Element {\n __svelte_meta?: SvelteMeta\n __svelte?: unknown\n}\n\n/** Walk up DOM to find nearest Svelte component element */\nexport function detect(el: Element): SvelteMeta | null {\n let node: SvelteElement | null = el as SvelteElement\n while (node && node !== document.documentElement) {\n if (node.__svelte_meta) return node.__svelte_meta\n node = node.parentElement as SvelteElement | null\n }\n return null\n}\n\n/** Get Svelte component context for an element */\nexport function getContext(el: Element): FrameworkContext | null {\n const meta = detect(el)\n if (!meta) return null\n\n // Extract component name from file path e.g. \"/src/components/Button.svelte\" → \"Button\"\n const filePath = meta.loc?.file ?? ''\n const component = filePath\n ? filePath.split('/').pop()?.replace(/\\.svelte$/, '') ?? 'Unknown'\n : 'Unknown'\n\n return {\n framework: 'svelte',\n component,\n data: filePath ? { file: filePath } : undefined,\n }\n}\n","import type { FrameworkContext } from '../types'\n\ninterface ReactFiber {\n type: unknown\n memoizedProps: Record<string, unknown> | null\n pendingProps: Record<string, unknown> | null\n return: ReactFiber | null\n key: string | null\n}\n\ninterface ReactElement extends Element {\n [key: string]: unknown\n}\n\nfunction getFiberKey(el: Element): string | null {\n for (const key of Object.keys(el)) {\n if (key.startsWith('__reactFiber$') || key.startsWith('__reactInternalInstance$')) {\n return key\n }\n }\n return null\n}\n\nfunction getComponentName(fiber: ReactFiber): string {\n let node: ReactFiber | null = fiber\n while (node) {\n const { type } = node\n if (typeof type === 'function' && (type as { name?: string }).name) {\n const name = (type as { name: string }).name\n // Skip React internals (start with lowercase = intrinsic HTML element function)\n if (name[0] === name[0].toUpperCase() && name.length > 1) return name\n }\n if (typeof type === 'object' && type !== null && (type as { displayName?: string }).displayName) {\n return (type as { displayName: string }).displayName\n }\n node = node.return\n }\n return 'Component'\n}\n\nfunction getProps(fiber: ReactFiber): Record<string, unknown> {\n const props = fiber.memoizedProps ?? fiber.pendingProps ?? {}\n const result: Record<string, unknown> = {}\n for (const [k, v] of Object.entries(props)) {\n if (k === 'children' || typeof v === 'function') continue\n try {\n result[k] = JSON.parse(JSON.stringify(v))\n } catch {\n result[k] = String(v)\n }\n }\n return result\n}\n\nexport function isAvailable(): boolean {\n // React attaches fiber data to DOM nodes with __reactFiber$ prefix\n const root = document.getElementById('root') ?? document.getElementById('app') ?? document.body.firstElementChild\n if (!root) return false\n return getFiberKey(root) !== null\n}\n\nexport function getContext(el: Element): FrameworkContext | null {\n let node: Element | null = el\n while (node && node !== document.documentElement) {\n const key = getFiberKey(node)\n if (key) {\n const fiber = (node as ReactElement)[key] as ReactFiber\n if (fiber) {\n const component = getComponentName(fiber)\n const data = getProps(fiber)\n return { framework: 'react', component, data }\n }\n }\n node = node.parentElement\n }\n return null\n}\n","import type { Annotation, InstrucktConfig, PendingAnnotation } from './types'\nimport { InstrucktApi } from './api'\nimport type { AnnotationPayload } from './api'\nimport { Toolbar } from './ui/toolbar'\nimport { ElementHighlight } from './ui/highlight'\nimport { AnnotationPopup } from './ui/popup'\nimport { AnnotationMarkers } from './ui/markers'\nimport { injectGlobalStyles } from './ui/styles'\nimport { getElementSelector, getElementName, getElementLabel, getNearbyText, getCssClasses, getPageBoundingBox } from './selector'\nimport { captureElement, captureRegion, selectRegion } from './ui/screenshot'\nimport * as livewireAdapter from './adapters/livewire'\nimport * as vueAdapter from './adapters/vue'\nimport * as svelteAdapter from './adapters/svelte'\nimport * as reactAdapter from './adapters/react'\n\n// Re-export for api.ts consumers\nexport type { AnnotationPayload }\n\n/** Normalize URL to pathname for page-scoping (ignore query/hash) */\nfunction pageKey(): string {\n return window.location.pathname\n}\n\nexport class Instruckt {\n private config: Required<Pick<InstrucktConfig, 'endpoint' | 'theme' | 'position'>> & InstrucktConfig\n private api: InstrucktApi\n private toolbar: Toolbar | null = null\n private highlight: ElementHighlight | null = null\n private popup: AnnotationPopup | null = null\n private markers: AnnotationMarkers | null = null\n private annotations: Annotation[] = []\n private isAnnotating = false\n private isFrozen = false\n private frozenStyleEl: HTMLStyleElement | null = null\n private frozenPopovers: { el: HTMLElement; original: string }[] = []\n private rafId: number | null = null\n private pendingMouseTarget: Element | null = null\n private highlightLocked = false\n private pollTimer: ReturnType<typeof setInterval> | null = null\n private boundKeydown: (e: KeyboardEvent) => void\n private boundReposition = (): void => {\n this.markers?.reposition(this.annotations)\n }\n\n constructor(config: InstrucktConfig) {\n this.config = {\n adapters: ['livewire', 'vue', 'svelte', 'react'],\n theme: 'auto',\n position: 'bottom-right',\n ...config,\n }\n this.api = new InstrucktApi(config.endpoint)\n this.boundKeydown = this.onKeydown.bind(this)\n this.init()\n }\n\n private init(): void {\n injectGlobalStyles(this.config.colors)\n\n if (this.config.theme !== 'auto') {\n document.documentElement.setAttribute('data-instruckt-theme', this.config.theme)\n }\n\n this.toolbar = new Toolbar(this.config.position, {\n onToggleAnnotate: (active) => {\n this.setAnnotating(active)\n },\n onFreezeAnimations: (frozen) => {\n this.setFrozen(frozen)\n },\n onScreenshot: () => this.startRegionCapture(),\n onCopy: () => this.copyToClipboard(true),\n onClearPage: () => this.clearPage(),\n onClearAll: () => this.clearEverything(),\n onMinimize: (min) => this.onMinimize(min),\n }, this.config.keys)\n\n this.highlight = new ElementHighlight()\n this.popup = new AnnotationPopup()\n this.markers = new AnnotationMarkers((annotation) => this.onMarkerClick(annotation))\n\n document.addEventListener('keydown', this.boundKeydown)\n window.addEventListener('scroll', this.boundReposition, { passive: true })\n window.addEventListener('resize', this.boundReposition, { passive: true })\n\n // Survive SPA navigation across frameworks\n document.addEventListener('livewire:navigated', () => this.reattach())\n document.addEventListener('inertia:navigate', () => this.syncMarkers())\n window.addEventListener('popstate', () => {\n setTimeout(() => this.reattach(), 0)\n })\n\n // Load persisted annotations from the backend\n this.loadAnnotations()\n\n this.syncMarkers()\n }\n\n private makeToolbarCallbacks() {\n return {\n onToggleAnnotate: (active: boolean) => {\n this.setAnnotating(active)\n },\n onFreezeAnimations: (frozen: boolean) => {\n this.setFrozen(frozen)\n },\n onScreenshot: () => this.startRegionCapture(),\n onCopy: () => this.copyToClipboard(true),\n onClearPage: () => this.clearPage(),\n onClearAll: () => this.clearEverything(),\n onMinimize: (min: boolean) => this.onMinimize(min),\n }\n }\n\n private reattach(): void {\n const wasAnnotating = this.isAnnotating\n const wasFrozen = this.isFrozen\n const wasMinimized = this.toolbar?.isMinimized() ?? false\n\n // Detach current listeners before rebuilding\n if (this.isAnnotating) this.detachAnnotateListeners()\n if (this.isFrozen) this.setFrozen(false)\n this.isAnnotating = false\n this.isFrozen = false\n\n // Remove any stale instruckt DOM (Livewire caches and restores old HTML on back nav)\n document.querySelectorAll('[data-instruckt]').forEach(el => el.remove())\n\n // Rebuild everything fresh\n this.toolbar = new Toolbar(this.config.position, this.makeToolbarCallbacks())\n if (wasMinimized) this.toolbar.minimize()\n\n this.markers = new AnnotationMarkers((annotation) => this.onMarkerClick(annotation))\n this.highlight = new ElementHighlight()\n\n if (wasMinimized) this.markers.setVisible(false)\n\n // Re-inject global styles (Livewire may have swapped <head> content)\n const existing = document.getElementById('instruckt-global')\n if (existing) existing.remove()\n injectGlobalStyles(this.config.colors)\n\n this.syncMarkers()\n\n // Restore active modes\n if (wasAnnotating && !wasMinimized) this.setAnnotating(true)\n }\n\n // ── Minimize ────────────────────────────────────────────────────\n\n private onMinimize(minimized: boolean): void {\n if (minimized) {\n // Deactivate everything when minimized\n if (this.isAnnotating) this.setAnnotating(false)\n if (this.isFrozen) this.setFrozen(false)\n this.toolbar?.setAnnotateActive(false)\n this.toolbar?.setFreezeActive(false)\n this.markers?.setVisible(false)\n this.popup?.destroy()\n } else {\n // Show markers again when restored\n this.markers?.setVisible(true)\n }\n }\n\n // ── Persistence ─────────────────────────────────────────────────\n\n private static STORAGE_KEY = 'instruckt:annotations'\n\n private async loadAnnotations(): Promise<void> {\n // Always load localStorage first as baseline\n this.loadFromStorage()\n\n try {\n const remote = await this.api.getAnnotations()\n if (remote.length > 0) {\n // Merge: remote is source of truth, but keep any local-only annotations\n const remoteIds = new Set(remote.map(a => a.id))\n const localOnly = this.annotations.filter(a => !remoteIds.has(a.id))\n this.annotations = [...remote, ...localOnly]\n this.saveToStorage()\n }\n } catch {\n // No backend — localStorage already loaded above\n }\n this.syncMarkers()\n }\n\n private saveToStorage(): void {\n try {\n localStorage.setItem(Instruckt.STORAGE_KEY, JSON.stringify(this.annotations))\n } catch { /* storage full or unavailable */ }\n }\n\n private loadFromStorage(): void {\n try {\n const raw = localStorage.getItem(Instruckt.STORAGE_KEY)\n if (raw) this.annotations = JSON.parse(raw)\n } catch { /* corrupt or unavailable */ }\n }\n\n /** Start or stop polling based on whether there are active annotations */\n private updatePolling(): void {\n const hasActive = this.totalActiveCount() > 0\n if (hasActive && !this.pollTimer) {\n this.pollTimer = setInterval(() => this.pollForChanges(), 3000)\n } else if (!hasActive && this.pollTimer) {\n clearInterval(this.pollTimer)\n this.pollTimer = null\n }\n }\n\n /** Poll API for status changes (e.g. agent resolved via MCP) */\n private async pollForChanges(): Promise<void> {\n try {\n const remote = await this.api.getAnnotations()\n let changed = false\n for (const r of remote) {\n const local = this.annotations.find(a => a.id === r.id)\n if (local && local.status !== r.status) {\n local.status = r.status\n local.resolvedAt = r.resolvedAt\n local.resolvedBy = r.resolvedBy\n changed = true\n }\n }\n if (changed) {\n this.saveToStorage()\n this.syncMarkers()\n }\n } catch { /* no backend or network error — skip */ }\n }\n\n // ── Page-scoped markers ─────────────────────────────────────────\n\n private syncMarkers(): void {\n this.markers?.clear()\n const current = pageKey()\n let idx = 0\n for (const a of this.annotations) {\n if (a.status === 'resolved' || a.status === 'dismissed') continue\n if (this.annotationPageKey(a) === current) {\n idx++\n this.markers?.upsert(a, idx)\n }\n }\n this.toolbar?.setAnnotationCount(this.pageAnnotations().length)\n this.toolbar?.setTotalCount(this.totalActiveCount())\n this.updatePolling()\n }\n\n private annotationPageKey(a: Annotation): string {\n try {\n return new URL(a.url).pathname\n } catch {\n return a.url\n }\n }\n\n private pageAnnotations(): Annotation[] {\n const current = pageKey()\n return this.annotations.filter(a =>\n this.annotationPageKey(a) === current &&\n a.status !== 'resolved' && a.status !== 'dismissed'\n )\n }\n\n private totalActiveCount(): number {\n return this.annotations.filter(a => a.status !== 'resolved' && a.status !== 'dismissed').length\n }\n\n // ── Annotate mode ─────────────────────────────────────────────\n\n private setAnnotating(active: boolean): void {\n this.isAnnotating = active\n this.toolbar?.setAnnotateActive(active)\n if (active) {\n this.attachAnnotateListeners()\n } else {\n this.detachAnnotateListeners()\n this.highlight?.hide()\n if (this.rafId !== null) { cancelAnimationFrame(this.rafId); this.rafId = null }\n }\n // When frozen, toggle pointer-events based on annotate state\n this.updateFreezeStyles()\n }\n\n // ── Freeze mode ──────────────────────────────────────────────\n\n private setFrozen(frozen: boolean): void {\n this.isFrozen = frozen\n this.toolbar?.setFreezeActive(frozen)\n if (frozen) {\n this.updateFreezeStyles()\n this.freezePopovers()\n // Use window (not document) so we intercept before Livewire/Alpine handlers\n // on document. Capture on window fires before capture on document.\n for (const evt of this.freezeBlockEvents) {\n window.addEventListener(evt, this.boundFreezeClick, true)\n }\n window.addEventListener('submit', this.boundFreezeSubmit, true)\n // Block events that close dropdowns/popovers (window capture to beat frameworks)\n for (const evt of this.freezePassiveEvents) {\n window.addEventListener(evt, this.boundFreezePassive, true)\n }\n } else {\n this.frozenStyleEl?.remove()\n this.frozenStyleEl = null\n this.unfreezePopovers()\n for (const evt of this.freezeBlockEvents) {\n window.removeEventListener(evt, this.boundFreezeClick, true)\n }\n window.removeEventListener('submit', this.boundFreezeSubmit, true)\n for (const evt of this.freezePassiveEvents) {\n window.removeEventListener(evt, this.boundFreezePassive, true)\n }\n }\n }\n\n /** Pull open popovers out of the top layer so the rest of the page is clickable */\n private freezePopovers(): void {\n this.frozenPopovers = []\n const openSelector = ':popover-open, .\\\\:popover-open'\n document.querySelectorAll('[popover]').forEach((el) => {\n const htmlEl = el as HTMLElement\n const val = htmlEl.getAttribute('popover') ?? ''\n let isOpen = false\n try { isOpen = htmlEl.matches(openSelector) } catch {\n try { isOpen = htmlEl.matches('.\\\\:popover-open') } catch { /* ignore */ }\n }\n if (!isOpen) return\n // Save position before removing popover attribute\n const rect = htmlEl.getBoundingClientRect()\n this.frozenPopovers.push({ el: htmlEl, original: val })\n // Remove popover attribute — pulls element out of top layer\n htmlEl.removeAttribute('popover')\n // Keep it visible with inline styles\n htmlEl.style.setProperty('display', 'block', 'important')\n htmlEl.style.setProperty('position', 'fixed', 'important')\n htmlEl.style.setProperty('z-index', '2147483644', 'important')\n htmlEl.style.setProperty('top', `${rect.top}px`, 'important')\n htmlEl.style.setProperty('left', `${rect.left}px`, 'important')\n htmlEl.style.setProperty('width', `${rect.width}px`, 'important')\n // Add the polyfill class so Flux thinks it's still open\n htmlEl.classList.add(':popover-open')\n })\n }\n\n /** Restore popover attributes */\n private unfreezePopovers(): void {\n for (const { el, original } of this.frozenPopovers) {\n // Remove inline overrides\n for (const prop of ['display', 'position', 'z-index', 'top', 'left', 'width']) {\n el.style.removeProperty(prop)\n }\n el.classList.remove(':popover-open')\n el.setAttribute('popover', original || 'auto')\n }\n this.frozenPopovers = []\n }\n\n private freezeBlockEvents = ['click', 'mousedown', 'pointerdown', 'pointerup', 'mouseup', 'touchstart', 'touchend', 'auxclick'] as const\n private freezePassiveEvents = ['focusin', 'focusout', 'blur', 'pointerleave', 'mouseleave', 'mouseout'] as const\n\n /** Update freeze CSS — pointer-events only blocked when NOT annotating */\n private updateFreezeStyles(): void {\n if (!this.isFrozen) return\n this.frozenStyleEl?.remove()\n this.frozenStyleEl = document.createElement('style')\n this.frozenStyleEl.id = 'instruckt-freeze'\n const pointerBlock = this.isAnnotating ? '' : `\n a[href], a[wire\\\\:navigate], [wire\\\\:click], [wire\\\\:navigate],\n [x-on\\\\:click], [@click], [v-on\\\\:click], [onclick],\n button, input[type=\"submit\"], select, [role=\"button\"], [role=\"link\"],\n [tabindex] {\n pointer-events: none !important;\n cursor: not-allowed !important;\n }\n `\n this.frozenStyleEl.textContent = `\n *, *::before, *::after {\n animation-play-state: paused !important;\n transition: none !important;\n }\n video { filter: none !important; }\n ${pointerBlock}\n `\n document.head.appendChild(this.frozenStyleEl)\n }\n\n /** Block interactions on the page when frozen (except instruckt UI) */\n private boundFreezeClick = (e: Event): void => {\n if (this.isInstruckt(e.target)) return\n // When annotating, only let 'click' through (annotate handler needs it).\n // Always block mousedown/pointerdown/touchstart to prevent framework\n // handlers (Alpine @click.outside, Livewire wire:navigate) from firing.\n if (this.isAnnotating && e.type === 'click') return\n e.preventDefault()\n e.stopPropagation()\n e.stopImmediatePropagation()\n }\n\n private boundFreezeSubmit = (e: Event): void => {\n e.preventDefault()\n e.stopPropagation()\n e.stopImmediatePropagation()\n }\n\n /** Block focus/hover events that JS dropdowns use to auto-close.\n * Block ALL of these — even on instruckt elements — because frameworks\n * like Flux check if focusin target is contained in the popover and\n * close it if it's not (e.g. focus moved to our popup textarea). */\n private boundFreezePassive = (e: Event): void => {\n e.stopPropagation()\n e.stopImmediatePropagation()\n }\n\n // ── Event listeners ───────────────────────────────────────────\n\n private boundMouseMove = (e: MouseEvent): void => {\n if (this.highlightLocked) return\n this.pendingMouseTarget = e.target as Element\n if (this.rafId === null) {\n this.rafId = requestAnimationFrame(() => {\n this.rafId = null\n if (this.highlightLocked) return\n if (this.pendingMouseTarget && !this.isInstruckt(this.pendingMouseTarget)) {\n this.highlight?.show(this.pendingMouseTarget)\n } else {\n this.highlight?.hide()\n }\n })\n }\n }\n\n private boundMouseLeave = (): void => {\n if (this.highlightLocked) return\n this.highlight?.hide()\n }\n\n /** Block mousedown/pointerdown in annotation mode so SPA frameworks can't navigate */\n private boundAnnotateBlock = (e: Event): void => {\n if (this.isInstruckt(e.target)) return\n e.preventDefault()\n e.stopPropagation()\n e.stopImmediatePropagation()\n }\n\n private boundClick = (e: MouseEvent): void => {\n const target = e.target as Element\n if (this.isInstruckt(target)) return\n // Always block clicks in annotation mode — prevents SPA navigation\n // from changing the page before the user can finish their note.\n e.preventDefault()\n e.stopPropagation()\n e.stopImmediatePropagation()\n\n const selectedText = window.getSelection()?.toString().trim() || undefined\n const elementPath = getElementSelector(target)\n const elementName = getElementName(target)\n const elementLabel = getElementLabel(target)\n const cssClasses = getCssClasses(target)\n const nearbyText = getNearbyText(target) || undefined\n const boundingBox = getPageBoundingBox(target)\n const framework = this.detectFramework(target) ?? undefined\n\n this.highlight?.show(target)\n this.highlightLocked = true\n\n const pending: PendingAnnotation = {\n element: target,\n elementPath,\n elementName,\n elementLabel,\n cssClasses,\n boundingBox,\n x: e.clientX,\n y: e.clientY,\n selectedText,\n nearbyText,\n framework,\n }\n\n this.showAnnotationPopup(pending)\n }\n\n private showAnnotationPopup(pending: PendingAnnotation): void {\n this.popup?.showNew(pending, {\n onSubmit: (result) => {\n this.highlightLocked = false\n this.highlight?.hide()\n this.submitAnnotation(pending, result.comment, result.screenshot)\n },\n onCancel: () => {\n this.highlightLocked = false\n this.highlight?.hide()\n },\n })\n }\n\n private attachAnnotateListeners(): void {\n document.addEventListener('mousemove', this.boundMouseMove)\n document.addEventListener('mouseleave', this.boundMouseLeave)\n // Block mousedown/pointerdown first — SPA frameworks (Livewire wire:navigate,\n // Inertia) intercept these before click fires\n for (const evt of ['mousedown', 'pointerdown'] as const) {\n window.addEventListener(evt, this.boundAnnotateBlock, true)\n }\n // Use window capture to fire before framework handlers on document\n window.addEventListener('click', this.boundClick, true)\n }\n\n private detachAnnotateListeners(): void {\n document.removeEventListener('mousemove', this.boundMouseMove)\n document.removeEventListener('mouseleave', this.boundMouseLeave)\n for (const evt of ['mousedown', 'pointerdown'] as const) {\n window.removeEventListener(evt, this.boundAnnotateBlock, true)\n }\n window.removeEventListener('click', this.boundClick, true)\n }\n\n private isInstruckt(el: EventTarget | null): boolean {\n if (!el || !(el instanceof Element)) return false\n return el.closest('[data-instruckt]') !== null\n }\n\n // ── Region screenshot ────────────────────────────────────────\n\n private async startRegionCapture(): Promise<void> {\n // Temporarily exit annotation mode so the crosshair doesn't interfere\n const wasAnnotating = this.isAnnotating\n if (wasAnnotating) this.setAnnotating(false)\n\n const rect = await selectRegion()\n if (!rect) {\n if (wasAnnotating) this.setAnnotating(true)\n return\n }\n\n const screenshot = await captureRegion(rect)\n if (!screenshot) {\n if (wasAnnotating) this.setAnnotating(true)\n return\n }\n\n // Find the element at the center of the selected region\n const centerX = rect.x + rect.width / 2\n const centerY = rect.y + rect.height / 2\n const target = document.elementFromPoint(centerX, centerY) ?? document.body\n\n const pending: PendingAnnotation = {\n element: target,\n elementPath: getElementSelector(target),\n elementName: getElementName(target),\n elementLabel: getElementLabel(target),\n cssClasses: getCssClasses(target),\n boundingBox: getPageBoundingBox(target),\n x: centerX,\n y: centerY,\n nearbyText: getNearbyText(target) || undefined,\n screenshot,\n framework: this.detectFramework(target) ?? undefined,\n }\n\n this.showAnnotationPopup(pending)\n }\n\n // ── Framework detection ───────────────────────────────────────\n\n private detectFramework(el: Element) {\n const adapters = this.config.adapters ?? []\n if (adapters.includes('livewire')) {\n const ctx = livewireAdapter.getContext(el)\n if (ctx) return ctx\n }\n if (adapters.includes('vue')) {\n const ctx = vueAdapter.getContext(el)\n if (ctx) return ctx\n }\n if (adapters.includes('svelte')) {\n const ctx = svelteAdapter.getContext(el)\n if (ctx) return ctx\n }\n if (adapters.includes('react')) {\n const ctx = reactAdapter.getContext(el)\n if (ctx) return ctx\n }\n return null\n }\n\n // ── Submit ────────────────────────────────────────────────────\n\n private async submitAnnotation(pending: PendingAnnotation, comment: string, screenshot?: string): Promise<void> {\n const payload: AnnotationPayload = {\n x: (pending.x / window.innerWidth) * 100,\n y: pending.y + window.scrollY,\n comment,\n element: pending.elementName,\n elementPath: pending.elementPath,\n cssClasses: pending.cssClasses,\n boundingBox: pending.boundingBox,\n selectedText: pending.selectedText,\n nearbyText: pending.nearbyText,\n screenshot,\n intent: 'fix',\n severity: 'important',\n framework: pending.framework,\n url: window.location.href,\n }\n\n let annotation: Annotation\n try {\n annotation = await this.api.addAnnotation(payload)\n } catch {\n // No backend — create a local-only annotation\n annotation = {\n ...payload,\n id: crypto.randomUUID(),\n status: 'pending',\n createdAt: new Date().toISOString(),\n }\n }\n this.annotations.push(annotation)\n this.saveToStorage()\n this.syncMarkers()\n this.config.onAnnotationAdd?.(annotation)\n this.copyAnnotations()\n }\n\n // ── Marker click — edit or delete ─────────────────────────────\n\n private onMarkerClick(annotation: Annotation): void {\n this.popup?.showEdit(annotation, {\n onSave: async (a, newComment) => {\n try {\n const updated = await this.api.updateAnnotation(a.id, { comment: newComment })\n this.onAnnotationUpdated(updated)\n } catch {\n // No backend — update locally\n this.onAnnotationUpdated({ ...a, comment: newComment, updatedAt: new Date().toISOString() })\n }\n },\n onDelete: async (a) => {\n try {\n await this.api.updateAnnotation(a.id, { status: 'dismissed' })\n } catch { /* no backend — just remove locally */ }\n this.removeAnnotation(a.id)\n },\n }, this.config.endpoint)\n }\n\n private onAnnotationUpdated(updated: Annotation): void {\n const idx = this.annotations.findIndex(a => a.id === updated.id)\n if (idx >= 0) {\n this.annotations[idx] = updated\n }\n this.saveToStorage()\n this.syncMarkers()\n }\n\n private removeAnnotation(id: string): void {\n this.annotations = this.annotations.filter(a => a.id !== id)\n this.saveToStorage()\n this.syncMarkers()\n }\n\n // ── Clear ───────────────────────────────────────────────────────\n\n private async clearPage(): Promise<void> {\n const page = this.pageAnnotations()\n for (const a of page) {\n try {\n await this.api.updateAnnotation(a.id, { status: 'dismissed' })\n } catch { /* best effort */ }\n }\n this.annotations = this.annotations.filter(a => !page.includes(a))\n this.saveToStorage()\n this.syncMarkers()\n }\n\n private async clearEverything(): Promise<void> {\n const active = this.annotations.filter(a => a.status !== 'resolved' && a.status !== 'dismissed')\n for (const a of active) {\n try {\n await this.api.updateAnnotation(a.id, { status: 'dismissed' })\n } catch { /* best effort */ }\n }\n this.annotations = []\n this.saveToStorage()\n this.syncMarkers()\n }\n\n // ── Keyboard ──────────────────────────────────────────────────\n\n private onKeydown(e: KeyboardEvent): void {\n if (this.toolbar?.isMinimized()) return\n const target = e.target as HTMLElement\n if (['INPUT', 'TEXTAREA', 'SELECT'].includes(target.tagName)) return\n if (target.closest('[contenteditable=\"true\"]')) return\n // Shadow DOM retargets e.target to the host element — check if a popup is open\n if (this.isInstruckt(target)) return\n\n const keys = this.config.keys ?? {}\n const noMod = !e.metaKey && !e.ctrlKey && !e.altKey\n if (e.key === (keys.annotate ?? 'a') && noMod) {\n this.setAnnotating(!this.isAnnotating)\n }\n if (e.key === (keys.freeze ?? 'f') && noMod) {\n this.setFrozen(!this.isFrozen)\n }\n if (e.key === (keys.screenshot ?? 'c') && noMod) {\n this.startRegionCapture()\n }\n if (e.key === (keys.clearPage ?? 'x') && noMod) {\n this.clearPage()\n }\n if (e.key === 'Escape') {\n if (this.isAnnotating) this.setAnnotating(false)\n if (this.isFrozen) this.setFrozen(false)\n }\n }\n\n // ── Copy / export ─────────────────────────────────────────────\n\n /** Auto-copy on annotation submit — only in secure contexts to avoid focus side-effects */\n private copyAnnotations(): void {\n this.copyToClipboard(false)\n }\n\n /** Copy to clipboard. With fallback=true, uses execCommand for non-secure contexts (user-initiated only). */\n private copyToClipboard(fallback: boolean): void {\n const md = this.exportMarkdown()\n if (window.isSecureContext) {\n navigator.clipboard.writeText(md).catch(() => { /* unavailable */ })\n } else if (fallback) {\n try {\n const el = document.createElement('textarea')\n el.value = md\n el.style.cssText = 'position:fixed;left:-9999px'\n document.body.appendChild(el)\n el.select()\n document.execCommand('copy')\n el.remove()\n } catch { /* unavailable */ }\n }\n }\n\n exportMarkdown(): string {\n const pending = this.annotations.filter(a => a.status !== 'resolved' && a.status !== 'dismissed')\n if (pending.length === 0) {\n return `# UI Feedback\\n\\nNo open annotations.`\n }\n\n // Group by page\n const byPage = new Map<string, Annotation[]>()\n for (const a of pending) {\n const key = this.annotationPageKey(a)\n if (!byPage.has(key)) byPage.set(key, [])\n byPage.get(key)!.push(a)\n }\n\n const multiPage = byPage.size > 1\n const lines: string[] = []\n\n if (multiPage) {\n lines.push(`# UI Feedback`)\n lines.push('')\n }\n\n for (const [path, annotations] of byPage) {\n if (multiPage) {\n lines.push(`## ${path}`)\n } else {\n lines.push(`# UI Feedback: ${path}`)\n }\n lines.push('')\n\n const hPrefix = multiPage ? '###' : '##'\n\n annotations.forEach((a, i) => {\n // Feedback-first heading with element context\n const componentSuffix = a.framework?.component ? ` in \\`${a.framework.component}\\`` : ''\n lines.push(`${hPrefix} ${i + 1}. ${a.comment}`)\n lines.push(`- Element: \\`${a.element}\\`${componentSuffix}`)\n\n // File path if available (e.g. Svelte)\n if (a.framework?.data?.file) {\n lines.push(`- File: \\`${a.framework.data.file}\\``)\n }\n\n if (a.cssClasses) {\n lines.push(`- Classes: \\`${a.cssClasses}\\``)\n }\n if (a.selectedText) {\n lines.push(`- Text: \"${a.selectedText}\"`)\n } else if (a.nearbyText) {\n lines.push(`- Text: \"${a.nearbyText.slice(0, 100)}\"`)\n }\n if (a.screenshot) {\n // If stored as a relative path (from backend), show the full path\n if (!a.screenshot.startsWith('data:')) {\n lines.push(`- Screenshot: \\`storage/app/_instruckt/${a.screenshot}\\``)\n } else {\n lines.push(`- Screenshot: attached`)\n }\n }\n lines.push('')\n })\n }\n\n return lines.join('\\n').trim()\n }\n\n // ── Public API ────────────────────────────────────────────────\n\n getAnnotations(): Annotation[] { return [...this.annotations] }\n\n destroy(): void {\n this.setAnnotating(false)\n this.setFrozen(false)\n document.removeEventListener('keydown', this.boundKeydown)\n window.removeEventListener('scroll', this.boundReposition)\n window.removeEventListener('resize', this.boundReposition)\n this.toolbar?.destroy()\n this.highlight?.destroy()\n this.popup?.destroy()\n this.markers?.destroy()\n if (this.rafId !== null) cancelAnimationFrame(this.rafId)\n if (this.pollTimer !== null) clearInterval(this.pollTimer)\n }\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;;;ACGA,SAAS,eAAuB;AAC9B,QAAM,QAAQ,SAAS,OAAO,MAAM,8BAA8B;AAClE,SAAO,QAAQ,mBAAmB,MAAM,CAAC,CAAC,IAAI;AAChD;AAEA,SAAS,UAAkC;AACzC,QAAM,IAA4B;AAAA,IAChC,gBAAgB;AAAA,IAChB,QAAQ;AAAA,IACR,oBAAoB;AAAA,EACtB;AACA,QAAM,OAAO,aAAa;AAC1B,MAAI,KAAM,GAAE,cAAc,IAAI;AAC9B,SAAO;AACT;AAGO,SAAS,YAAY,KAAuD;AACjF,QAAM,MAA+B,CAAC;AACtC,aAAW,CAAC,GAAG,CAAC,KAAK,OAAO,QAAQ,GAAG,GAAG;AACxC,UAAM,QAAQ,EAAE,QAAQ,aAAa,CAAC,GAAG,MAAM,EAAE,YAAY,CAAC;AAC9D,QAAI,KAAK,IAAI,MAAM,QAAQ,CAAC,IACxB,EAAE,IAAI,UAAS,QAAQ,OAAO,SAAS,YAAY,CAAC,MAAM,QAAQ,IAAI,IAAK,YAAY,IAA+B,IAAI,IAAI,IAC7H,KAAK,OAAO,MAAM,YAAY,CAAC,MAAM,QAAQ,CAAC,IAAK,YAAY,CAA4B,IAAI;AAAA,EACtG;AACA,SAAO;AACT;AAGA,SAAS,QAAQ,KAAuD;AACtE,QAAM,MAA+B,CAAC;AACtC,aAAW,CAAC,GAAG,CAAC,KAAK,OAAO,QAAQ,GAAG,GAAG;AACxC,UAAM,QAAQ,EAAE,QAAQ,UAAU,OAAK,IAAI,EAAE,YAAY,CAAC,EAAE;AAC5D,QAAI,KAAK,IAAK,KAAK,OAAO,MAAM,YAAY,CAAC,MAAM,QAAQ,CAAC,IAAK,QAAQ,CAA4B,IAAI;AAAA,EAC3G;AACA,SAAO;AACT;AAOO,IAAM,eAAN,MAAmB;AAAA,EACxB,YAA6B,UAAkB;AAAlB;AAAA,EAAmB;AAAA,EAEhD,MAAM,iBAAwC;AAC5C,UAAM,MAAM,MAAM,MAAM,GAAG,KAAK,QAAQ,gBAAgB;AAAA,MACtD,SAAS,QAAQ;AAAA,IACnB,CAAC;AACD,QAAI,CAAC,IAAI,GAAI,OAAM,IAAI,MAAM,0CAA0C,IAAI,MAAM,GAAG;AACpF,UAAM,MAAiC,MAAM,IAAI,KAAK;AACtD,WAAO,IAAI,IAAI,OAAK,YAAY,CAAC,CAA0B;AAAA,EAC7D;AAAA,EAEA,MAAM,cAAc,MAA8C;AAChE,UAAM,MAAM,MAAM,MAAM,GAAG,KAAK,QAAQ,gBAAgB;AAAA,MACtD,QAAQ;AAAA,MACR,SAAS,QAAQ;AAAA,MACjB,MAAM,KAAK,UAAU,QAAQ,IAA0C,CAAC;AAAA,IAC1E,CAAC;AACD,QAAI,CAAC,IAAI,GAAI,OAAM,IAAI,MAAM,wCAAwC,IAAI,MAAM,GAAG;AAClF,WAAO,YAAY,MAAM,IAAI,KAAK,CAAC;AAAA,EACrC;AAAA,EAEA,MAAM,iBACJ,cACA,MACqB;AACrB,UAAM,MAAM,MAAM,MAAM,GAAG,KAAK,QAAQ,gBAAgB,YAAY,IAAI;AAAA,MACtE,QAAQ;AAAA,MACR,SAAS,QAAQ;AAAA,MACjB,MAAM,KAAK,UAAU,QAAQ,IAA0C,CAAC;AAAA,IAC1E,CAAC;AACD,QAAI,CAAC,IAAI,GAAI,OAAM,IAAI,MAAM,2CAA2C,IAAI,MAAM,GAAG;AACrF,WAAO,YAAY,MAAM,IAAI,KAAK,CAAC;AAAA,EACrC;AAEF;;;AChFO,IAAM;AAAA;AAAA,EAAuB;AAAA;AAAA;AAAA;AAAA;AAM7B,IAAM;AAAA;AAAA,EAAwB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAuK9B,IAAM;AAAA;AAAA,EAAsB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AA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","names":["_a","_b","init","process","dataURL","cache","node","detect","getContext","detect","getContext","getContext","e","_a","getContext"]}
|