zoooom 1.0.0

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.
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/core/constants.ts","../src/core/transform.ts","../src/core/loader.ts","../src/input/mouse.ts","../src/input/touch.ts","../src/input/wheel.ts","../src/input/keyboard.ts","../src/input/gesture.ts","../src/styles/core.ts","../src/core/Zoooom.ts","../src/joystick/dom.ts","../src/styles/joystick.ts","../src/joystick/joystick.ts"],"names":["Zoooom","injected","ZoooomJoystick"],"mappings":"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","file":"zoooom-full.iife.global.js","sourcesContent":["/** Default pan distance for keyboard arrows (px) */\nexport const PAN_STEP = 50;\n\n/** Zoom multiplier per discrete step (>1 zooms in) */\nexport const ZOOM_FACTOR = 1.5;\n\n/** Minimum zoom scale (allows slight zoom-out) */\nexport const MIN_SCALE = 0.8;\n\n/** Multiplier beyond native resolution for max zoom */\nexport const OVERSCALE_FACTOR = 2;\n\n/** Friction coefficient for momentum — velocity *= this each frame */\nexport const VELOCITY_DAMPING = 0.85;\n\n/** Sensitivity for trackpad continuous zoom */\nexport const TRACKPAD_SENSITIVITY = 0.002;\n\n/** Joystick panning zone radius (px) */\nexport const JOYSTICK_RADIUS = 60;\n\n/** Center deadzone as fraction of radius */\nexport const JOYSTICK_DEADZONE = 0.1;\n\n/** Maximum joystick panning speed (px/frame) */\nexport const MAX_JOYSTICK_SPEED = 10;\n\n/** Dwell timeout before joystick activates (ms) */\nexport const DWELL_TIMEOUT = 100;\n","import { MIN_SCALE, OVERSCALE_FACTOR, VELOCITY_DAMPING } from './constants.js';\nimport type { ZoooomState, ZoooomElements } from '../types.js';\n\n/**\n * Apply the current transform state to the image element.\n * Uses translate(calc(-50% + Xpx), calc(-50% + Ypx)) scale(S) for center-anchored zoom.\n */\nexport function updateTransform(state: ZoooomState, elements: ZoooomElements): void {\n if (!elements.image) return;\n elements.image.style.transform =\n `translate(calc(-50% + ${state.translateX}px), calc(-50% + ${state.translateY}px)) scale(${state.scale})`;\n}\n\n/**\n * Animate momentum after pan release — velocity decays per frame via damping.\n * Skipped when reduced motion is preferred.\n */\nexport function animateMovement(\n state: ZoooomState,\n elements: ZoooomElements,\n onPan?: (x: number, y: number) => void,\n): void {\n if (state.reducedMotion) {\n state.velocityX = 0;\n state.velocityY = 0;\n return;\n }\n\n state.isAnimating = true;\n\n function step() {\n state.translateX += state.velocityX;\n state.translateY += state.velocityY;\n state.velocityX *= VELOCITY_DAMPING;\n state.velocityY *= VELOCITY_DAMPING;\n\n updateTransform(state, elements);\n onPan?.(state.translateX, state.translateY);\n\n if (Math.abs(state.velocityX) > 0.1 || Math.abs(state.velocityY) > 0.1) {\n requestAnimationFrame(step);\n } else {\n state.velocityX = 0;\n state.velocityY = 0;\n state.isAnimating = false;\n }\n }\n\n requestAnimationFrame(step);\n}\n\n/** Center the image in the container (reset translate without changing scale) */\nexport function centerImage(state: ZoooomState, elements: ZoooomElements): void {\n if (!elements.container || !elements.image) return;\n state.translateX = 0;\n state.translateY = 0;\n updateTransform(state, elements);\n}\n\n/** Reset view to scale=1, centered, zero velocity */\nexport function resetView(state: ZoooomState, elements: ZoooomElements): void {\n state.scale = 1;\n state.translateX = 0;\n state.translateY = 0;\n state.velocityX = 0;\n state.velocityY = 0;\n updateTransform(state, elements);\n}\n\n/**\n * Calculate the maximum zoom scale from the image's natural vs displayed dimensions.\n * Allows zooming to full native resolution * overscale factor.\n */\nexport function calculateMaxScale(\n elements: ZoooomElements,\n overscaleFactor: number = OVERSCALE_FACTOR,\n): number {\n if (!elements.image) return 10;\n\n const naturalWidth = elements.image.naturalWidth;\n const naturalHeight = elements.image.naturalHeight;\n const displayWidth = elements.image.clientWidth;\n const displayHeight = elements.image.clientHeight;\n\n if (!naturalWidth || !naturalHeight || !displayWidth || !displayHeight) return 10;\n\n const widthRatio = naturalWidth / displayWidth;\n const heightRatio = naturalHeight / displayHeight;\n const maxScaleFactor = Math.max(widthRatio, heightRatio);\n\n // Higher overscale on mobile for full-res zoom\n const mobileOverscale = window.innerWidth <= 768 ? overscaleFactor * 2 : overscaleFactor;\n return Math.max(maxScaleFactor * mobileOverscale, MIN_SCALE);\n}\n\n/**\n * Zoom toward a specific point (cursor, pinch center, or container center).\n * Maintains the image point under the target coordinate.\n */\nexport function zoomTowardsPoint(\n state: ZoooomState,\n elements: ZoooomElements,\n delta: number,\n pointX?: number,\n pointY?: number,\n onZoom?: (scale: number) => void,\n): void {\n if (!elements.container || !elements.image) return;\n\n const currentScale = state.scale;\n const newScale = Math.max(MIN_SCALE, Math.min(state.scale * delta, state.maxScale));\n\n if (newScale === currentScale) return;\n\n const containerRect = elements.container.getBoundingClientRect();\n const containerCenterX = containerRect.width / 2;\n const containerCenterY = containerRect.height / 2;\n\n const targetX = pointX ?? containerCenterX;\n const targetY = pointY ?? containerCenterY;\n\n // Calculate the image point under the target coordinate\n const imageX = (targetX - containerCenterX - state.translateX) / currentScale;\n const imageY = (targetY - containerCenterY - state.translateY) / currentScale;\n\n // Update translation to keep that point stationary\n state.translateX = targetX - containerCenterX - imageX * newScale;\n state.translateY = targetY - containerCenterY - imageY * newScale;\n\n // Smooth zoom transition (skipped for reduced motion)\n if (!state.reducedMotion) {\n elements.image.style.transition = 'transform 0.2s ease-out';\n }\n\n state.scale = newScale;\n updateTransform(state, elements);\n onZoom?.(state.scale);\n\n if (!state.reducedMotion) {\n setTimeout(() => {\n if (elements.image) {\n elements.image.style.transition = '';\n }\n }, 200);\n }\n}\n","import type { ZoooomState, ZoooomElements, ZoooomResolvedOptions } from '../types.js';\nimport { calculateMaxScale, centerImage } from './transform.js';\n\n/**\n * Create the loading overlay element (spinner + text).\n * Returns null if loading is disabled.\n */\nexport function createLoadingOverlay(\n container: HTMLElement,\n loading: boolean | string,\n): HTMLElement | null {\n if (loading === false) return null;\n\n const overlay = document.createElement('div');\n overlay.className = 'zoooom-loading';\n overlay.setAttribute('role', 'status');\n overlay.setAttribute('aria-label', 'Loading image');\n\n if (typeof loading === 'string') {\n overlay.innerHTML = loading;\n } else {\n overlay.innerHTML = `\n <div class=\"zoooom-spinner\"></div>\n <div class=\"zoooom-loading-text\">Loading...</div>\n `;\n }\n\n container.appendChild(overlay);\n return overlay;\n}\n\n/** Remove the loading overlay from the DOM */\nfunction removeLoadingOverlay(elements: ZoooomElements): void {\n if (elements.loadingOverlay) {\n elements.loadingOverlay.remove();\n elements.loadingOverlay = null;\n }\n}\n\n/**\n * Load an image into the viewer with preloading, loading state, and fade-in.\n * Decoupled from any data source — just takes a URL and alt text.\n */\nexport function loadImage(\n src: string,\n alt: string,\n state: ZoooomState,\n elements: ZoooomElements,\n options: ZoooomResolvedOptions,\n emit: (event: string, ...args: unknown[]) => void,\n): void {\n // Reset transform state\n state.scale = 1;\n state.translateX = 0;\n state.translateY = 0;\n state.velocityX = 0;\n state.velocityY = 0;\n state.isLoaded = false;\n\n // Remove any existing loading overlay\n removeLoadingOverlay(elements);\n\n // Create loading overlay\n elements.loadingOverlay = createLoadingOverlay(elements.container, options.loading);\n\n // Hide image during load\n elements.image.style.opacity = '0';\n elements.image.style.visibility = 'hidden';\n elements.image.setAttribute('aria-hidden', 'true');\n elements.image.setAttribute('alt', '');\n\n // Preload at full resolution\n const preloader = new Image();\n\n preloader.onload = () => {\n elements.image.src = preloader.src;\n\n elements.image.onload = () => {\n removeLoadingOverlay(elements);\n\n // Restore alt text\n elements.image.setAttribute('alt', alt);\n elements.image.removeAttribute('aria-hidden');\n\n // Fade in (or show immediately for reduced motion)\n if (state.reducedMotion) {\n elements.image.style.opacity = '1';\n elements.image.style.visibility = 'visible';\n } else {\n setTimeout(() => {\n elements.image.style.transition = 'opacity 0.3s ease-in-out';\n elements.image.style.opacity = '1';\n elements.image.style.visibility = 'visible';\n\n // Clear transition after fade\n setTimeout(() => {\n elements.image.style.transition = '';\n }, 300);\n }, 50);\n }\n\n // Calculate max scale from actual dimensions\n if (options.maxScale === 'auto') {\n state.maxScale = calculateMaxScale(elements, options.overscaleFactor);\n }\n\n centerImage(state, elements);\n state.isLoaded = true;\n emit('load');\n options.onLoad?.();\n };\n\n elements.image.onerror = () => {\n removeLoadingOverlay(elements);\n const error = new Error(`Failed to load image: ${src}`);\n emit('error', error);\n options.onError?.(error);\n };\n };\n\n preloader.onerror = () => {\n removeLoadingOverlay(elements);\n const error = new Error(`Failed to load image: ${src}`);\n emit('error', error);\n options.onError?.(error);\n };\n\n preloader.src = src;\n}\n","import type { ZoooomState, ZoooomElements, InputCleanup } from '../types.js';\nimport { updateTransform } from '../core/transform.js';\n\n/**\n * Attach mouse drag-to-pan handlers.\n * Returns a cleanup function to remove all listeners.\n */\nexport function attachMouse(\n state: ZoooomState,\n elements: ZoooomElements,\n onPan?: (x: number, y: number) => void,\n): InputCleanup {\n const { container } = elements;\n\n function handleMouseDown(e: MouseEvent) {\n if (e.button !== 0) return; // Left button only\n state.isDragging = true;\n state.startX = e.clientX;\n state.startY = e.clientY;\n container.style.cursor = 'grabbing';\n e.preventDefault();\n }\n\n function handleMouseMove(e: MouseEvent) {\n if (!state.isDragging) return;\n const dx = e.clientX - state.startX;\n const dy = e.clientY - state.startY;\n state.translateX += dx;\n state.translateY += dy;\n state.startX = e.clientX;\n state.startY = e.clientY;\n updateTransform(state, elements);\n onPan?.(state.translateX, state.translateY);\n }\n\n function handleMouseUp() {\n if (state.isDragging) {\n state.isDragging = false;\n container.style.cursor = 'grab';\n }\n }\n\n container.addEventListener('mousedown', handleMouseDown);\n container.addEventListener('mousemove', handleMouseMove);\n container.addEventListener('mouseup', handleMouseUp);\n container.addEventListener('mouseleave', handleMouseUp);\n\n return () => {\n container.removeEventListener('mousedown', handleMouseDown);\n container.removeEventListener('mousemove', handleMouseMove);\n container.removeEventListener('mouseup', handleMouseUp);\n container.removeEventListener('mouseleave', handleMouseUp);\n };\n}\n","import { MIN_SCALE } from '../core/constants.js';\nimport { calculateMaxScale, updateTransform } from '../core/transform.js';\nimport type { ZoooomState, ZoooomElements, InputCleanup } from '../types.js';\n\nfunction getDistance(e: TouchEvent): number {\n const t1 = e.touches[0];\n const t2 = e.touches[1];\n const dx = t1.clientX - t2.clientX;\n const dy = t1.clientY - t2.clientY;\n return Math.sqrt(dx * dx + dy * dy);\n}\n\n/**\n * Attach touch pan and pinch-to-zoom handlers.\n * Returns a cleanup function to remove all listeners.\n */\nexport function attachTouch(\n state: ZoooomState,\n elements: ZoooomElements,\n overscaleFactor: number,\n onPan?: (x: number, y: number) => void,\n onZoom?: (scale: number) => void,\n): InputCleanup {\n const { container } = elements;\n\n function handleTouchStart(e: TouchEvent) {\n if (e.touches.length === 1) {\n state.isDragging = true;\n state.startX = e.touches[0].clientX;\n state.startY = e.touches[0].clientY;\n state.initialDistance = 0;\n } else if (e.touches.length === 2) {\n state.isDragging = false;\n state.initialDistance = getDistance(e);\n state.initialScale = state.scale;\n state.initialTranslateX = state.translateX;\n state.initialTranslateY = state.translateY;\n\n const t1 = e.touches[0];\n const t2 = e.touches[1];\n const rect = container.getBoundingClientRect();\n state.pinchCenter = {\n x: ((t1.clientX + t2.clientX) / 2) - rect.left,\n y: ((t1.clientY + t2.clientY) / 2) - rect.top,\n };\n }\n }\n\n function handleTouchMove(e: TouchEvent) {\n e.preventDefault();\n\n if (e.touches.length === 1 && state.isDragging) {\n const dx = e.touches[0].clientX - state.startX;\n const dy = e.touches[0].clientY - state.startY;\n state.translateX += dx;\n state.translateY += dy;\n state.startX = e.touches[0].clientX;\n state.startY = e.touches[0].clientY;\n updateTransform(state, elements);\n onPan?.(state.translateX, state.translateY);\n } else if (e.touches.length === 2 && state.initialDistance > 0) {\n const currentDistance = getDistance(e);\n const scaleFactor = currentDistance / state.initialDistance;\n const targetScale = state.initialScale * scaleFactor;\n state.maxScale = calculateMaxScale(elements, overscaleFactor);\n const newScale = Math.max(MIN_SCALE, Math.min(targetScale, state.maxScale));\n\n if (newScale === state.scale) return;\n\n const t1 = e.touches[0];\n const t2 = e.touches[1];\n const rect = container.getBoundingClientRect();\n const currentPinchCenter = {\n x: ((t1.clientX + t2.clientX) / 2) - rect.left,\n y: ((t1.clientY + t2.clientY) / 2) - rect.top,\n };\n\n const containerCenterX = rect.width / 2;\n const containerCenterY = rect.height / 2;\n\n const imageX = (state.pinchCenter.x - containerCenterX - state.initialTranslateX) / state.initialScale;\n const imageY = (state.pinchCenter.y - containerCenterY - state.initialTranslateY) / state.initialScale;\n\n state.translateX = currentPinchCenter.x - containerCenterX - imageX * newScale;\n state.translateY = currentPinchCenter.y - containerCenterY - imageY * newScale;\n\n state.scale = newScale;\n updateTransform(state, elements);\n onZoom?.(state.scale);\n\n state.pinchCenter = currentPinchCenter;\n }\n }\n\n function handleTouchEnd() {\n state.isDragging = false;\n state.initialDistance = 0;\n }\n\n container.addEventListener('touchstart', handleTouchStart, { passive: false });\n container.addEventListener('touchmove', handleTouchMove, { passive: false });\n container.addEventListener('touchend', handleTouchEnd);\n container.addEventListener('touchcancel', handleTouchEnd);\n\n return () => {\n container.removeEventListener('touchstart', handleTouchStart);\n container.removeEventListener('touchmove', handleTouchMove);\n container.removeEventListener('touchend', handleTouchEnd);\n container.removeEventListener('touchcancel', handleTouchEnd);\n };\n}\n","import { ZOOM_FACTOR, TRACKPAD_SENSITIVITY } from '../core/constants.js';\nimport { zoomTowardsPoint } from '../core/transform.js';\nimport type { ZoooomState, ZoooomElements, InputCleanup } from '../types.js';\n\n/**\n * Attach wheel/trackpad zoom handler.\n * Detects trackpad vs mouse wheel via delta magnitude.\n * Handles Ctrl+wheel for pinch gestures on Windows/Linux.\n */\nexport function attachWheel(\n state: ZoooomState,\n elements: ZoooomElements,\n zoomFactor: number = ZOOM_FACTOR,\n trackpadSensitivity: number = TRACKPAD_SENSITIVITY,\n onZoom?: (scale: number) => void,\n): InputCleanup {\n const { container } = elements;\n\n function handleWheel(e: WheelEvent) {\n e.preventDefault();\n\n const rect = container.getBoundingClientRect();\n const pointX = e.clientX - rect.left;\n const pointY = e.clientY - rect.top;\n\n let zoomDelta: number;\n\n if (e.ctrlKey) {\n // Pinch gesture (Ctrl+wheel on Windows/Linux)\n zoomDelta = e.deltaY < 0 ? zoomFactor : 1 / zoomFactor;\n } else {\n // Normalize delta based on deltaMode\n let normalizedDelta: number;\n switch (e.deltaMode) {\n case 1: normalizedDelta = e.deltaY * 20; break; // LINE\n case 2: normalizedDelta = e.deltaY * 100; break; // PAGE\n default: normalizedDelta = e.deltaY; // PIXEL\n }\n\n if (Math.abs(normalizedDelta) < 40) {\n // Trackpad — continuous zoom\n zoomDelta = Math.exp(-normalizedDelta * trackpadSensitivity);\n } else {\n // Mouse wheel — discrete steps\n zoomDelta = normalizedDelta > 0 ? 1 / zoomFactor : zoomFactor;\n }\n }\n\n // Manage scroll state class for CSS transition control\n container.classList.add('zoooom-scrolling');\n if (state.wheelTimeout) clearTimeout(state.wheelTimeout);\n state.wheelTimeout = setTimeout(() => {\n container.classList.remove('zoooom-scrolling');\n }, 200);\n\n zoomTowardsPoint(state, elements, zoomDelta, pointX, pointY, onZoom);\n }\n\n container.addEventListener('wheel', handleWheel, { passive: false });\n\n return () => {\n container.removeEventListener('wheel', handleWheel);\n if (state.wheelTimeout) clearTimeout(state.wheelTimeout);\n };\n}\n","import { PAN_STEP, ZOOM_FACTOR } from '../core/constants.js';\nimport { zoomTowardsPoint, animateMovement, resetView } from '../core/transform.js';\nimport type { ZoooomState, ZoooomElements, InputCleanup } from '../types.js';\n\n/**\n * Attach keyboard navigation handlers.\n * Arrows pan, +/- zoom, R resets, Escape is reserved for parent contexts.\n */\nexport function attachKeyboard(\n state: ZoooomState,\n elements: ZoooomElements,\n panStep: number = PAN_STEP,\n zoomFactor: number = ZOOM_FACTOR,\n onPan?: (x: number, y: number) => void,\n onZoom?: (scale: number) => void,\n): InputCleanup {\n const { container } = elements;\n\n function handleKeyDown(e: KeyboardEvent) {\n let handled = true;\n\n switch (e.key) {\n case 'ArrowLeft':\n state.velocityX = panStep * 0.2;\n animateMovement(state, elements, onPan);\n break;\n case 'ArrowRight':\n state.velocityX = -panStep * 0.2;\n animateMovement(state, elements, onPan);\n break;\n case 'ArrowUp':\n state.velocityY = panStep * 0.2;\n animateMovement(state, elements, onPan);\n break;\n case 'ArrowDown':\n state.velocityY = -panStep * 0.2;\n animateMovement(state, elements, onPan);\n break;\n case '+': case '=':\n zoomTowardsPoint(state, elements, zoomFactor, undefined, undefined, onZoom);\n break;\n case '-':\n zoomTowardsPoint(state, elements, 1 / zoomFactor, undefined, undefined, onZoom);\n break;\n case 'r': case 'R':\n resetView(state, elements);\n break;\n default:\n handled = false;\n }\n\n if (handled) e.preventDefault();\n }\n\n container.addEventListener('keydown', handleKeyDown);\n\n return () => {\n container.removeEventListener('keydown', handleKeyDown);\n };\n}\n","import { ZOOM_FACTOR } from '../core/constants.js';\nimport { zoomTowardsPoint } from '../core/transform.js';\nimport type { ZoooomState, ZoooomElements, InputCleanup } from '../types.js';\n\n/**\n * Attach Safari gesture events (gesturestart/change/end).\n * Only activates in Safari where GestureEvent exists.\n */\nexport function attachGesture(\n state: ZoooomState,\n elements: ZoooomElements,\n onZoom?: (scale: number) => void,\n): InputCleanup {\n const { container } = elements;\n\n // Only Safari supports gesture events\n if (!('ongesturestart' in window)) {\n return () => {};\n }\n\n let startScale = 1;\n\n function handleGestureStart(e: Event) {\n e.preventDefault();\n startScale = state.scale;\n }\n\n function handleGestureChange(e: Event) {\n e.preventDefault();\n const ge = e as unknown as { scale: number };\n const rect = container.getBoundingClientRect();\n const delta = ge.scale > 1 ? ZOOM_FACTOR : 1 / ZOOM_FACTOR;\n zoomTowardsPoint(state, elements, delta, rect.width / 2, rect.height / 2, onZoom);\n }\n\n function handleGestureEnd(e: Event) {\n e.preventDefault();\n }\n\n container.addEventListener('gesturestart', handleGestureStart, { passive: false } as EventListenerOptions);\n container.addEventListener('gesturechange', handleGestureChange, { passive: false } as EventListenerOptions);\n container.addEventListener('gestureend', handleGestureEnd, { passive: false } as EventListenerOptions);\n\n return () => {\n container.removeEventListener('gesturestart', handleGestureStart);\n container.removeEventListener('gesturechange', handleGestureChange);\n container.removeEventListener('gestureend', handleGestureEnd);\n };\n}\n","export const ZOOOOM_CSS = `\n[data-zoooom] {\n --zoooom-bg: #000;\n --zoooom-spinner-color: #2196f3;\n --zoooom-spinner-track: rgba(255, 255, 255, 0.3);\n --zoooom-spinner-size: 40px;\n --zoooom-loading-bg: rgba(0, 0, 0, 0.85);\n --zoooom-loading-radius: 10px;\n --zoooom-cursor: grab;\n --zoooom-cursor-active: grabbing;\n --zoooom-transition-speed: 0.2s;\n --zoooom-fade-speed: 0.3s;\n\n position: relative;\n width: 100%;\n height: 100%;\n background: var(--zoooom-bg);\n overflow: hidden;\n touch-action: none;\n cursor: var(--zoooom-cursor);\n user-select: none;\n -webkit-user-select: none;\n}\n\n[data-zoooom]:focus-visible {\n outline: 2px solid var(--zoooom-spinner-color);\n outline-offset: -2px;\n}\n\n[data-zoooom] .zoooom-image {\n position: absolute;\n top: 50%;\n left: 50%;\n transform: translate(-50%, -50%) scale(1);\n max-width: 100%;\n max-height: 100%;\n object-fit: contain;\n user-select: none;\n -webkit-user-select: none;\n pointer-events: none;\n}\n\n[data-zoooom] .zoooom-loading {\n position: absolute;\n top: 50%;\n left: 50%;\n transform: translate(-50%, -50%);\n display: flex;\n flex-direction: column;\n align-items: center;\n justify-content: center;\n background: var(--zoooom-loading-bg);\n padding: 20px;\n border-radius: var(--zoooom-loading-radius);\n z-index: 10;\n min-width: 120px;\n}\n\n[data-zoooom] .zoooom-spinner {\n width: var(--zoooom-spinner-size);\n height: var(--zoooom-spinner-size);\n border: 4px solid var(--zoooom-spinner-track);\n border-radius: 50%;\n border-top-color: var(--zoooom-spinner-color);\n animation: zoooom-spin 1s linear infinite;\n}\n\n[data-zoooom] .zoooom-loading-text {\n margin-top: 12px;\n font-size: 14px;\n color: #fff;\n font-family: system-ui, -apple-system, sans-serif;\n}\n\n@keyframes zoooom-spin {\n to { transform: rotate(360deg); }\n}\n\n@media (prefers-reduced-motion: reduce) {\n [data-zoooom] .zoooom-spinner {\n animation: none;\n border-top-color: var(--zoooom-spinner-track);\n border-right-color: var(--zoooom-spinner-color);\n }\n\n [data-zoooom] .zoooom-image {\n transition: none !important;\n }\n}\n`;\n\nlet injected = false;\n\nexport function injectCoreStyles(): void {\n if (injected || typeof document === 'undefined') return;\n const style = document.createElement('style');\n style.setAttribute('data-zoooom-core', '');\n style.textContent = ZOOOOM_CSS;\n document.head.appendChild(style);\n injected = true;\n}\n","import type {\n ZoooomOptions,\n ZoooomResolvedOptions,\n ZoooomState,\n ZoooomElements,\n ZoooomEvent,\n ZoooomEventHandler,\n InputCleanup,\n} from '../types.js';\nimport { MIN_SCALE, ZOOM_FACTOR, OVERSCALE_FACTOR, VELOCITY_DAMPING, PAN_STEP, TRACKPAD_SENSITIVITY } from './constants.js';\nimport { updateTransform, zoomTowardsPoint, resetView, centerImage, calculateMaxScale } from './transform.js';\nimport { loadImage } from './loader.js';\nimport { attachMouse } from '../input/mouse.js';\nimport { attachTouch } from '../input/touch.js';\nimport { attachWheel } from '../input/wheel.js';\nimport { attachKeyboard } from '../input/keyboard.js';\nimport { attachGesture } from '../input/gesture.js';\nimport { injectCoreStyles } from '../styles/core.js';\n\nconst DEFAULTS: ZoooomResolvedOptions = {\n src: '',\n alt: 'Image',\n minScale: MIN_SCALE,\n maxScale: 'auto',\n overscaleFactor: OVERSCALE_FACTOR,\n zoomFactor: ZOOM_FACTOR,\n panStep: PAN_STEP,\n velocityDamping: VELOCITY_DAMPING,\n trackpadSensitivity: TRACKPAD_SENSITIVITY,\n mouse: true,\n touch: true,\n wheel: true,\n keyboard: true,\n loading: true,\n injectStyles: true,\n respectReducedMotion: true,\n};\n\nexport class Zoooom {\n private state: ZoooomState;\n private elements: ZoooomElements;\n private options: ZoooomResolvedOptions;\n private cleanups: InputCleanup[] = [];\n private listeners = new Map<string, Set<ZoooomEventHandler>>();\n private resizeHandler: (() => void) | null = null;\n\n constructor(container: string | HTMLElement, options: ZoooomOptions) {\n this.options = { ...DEFAULTS, ...options } as ZoooomResolvedOptions;\n\n // Inject styles\n if (this.options.injectStyles) {\n injectCoreStyles();\n }\n\n // Resolve container\n const el = typeof container === 'string'\n ? document.querySelector<HTMLElement>(container)\n : container;\n\n if (!el) {\n throw new Error(`Zoooom: container \"${container}\" not found`);\n }\n\n // Warn if container has no dimensions\n if (el.clientWidth === 0 || el.clientHeight === 0) {\n console.warn('Zoooom: container has zero dimensions. The viewer needs explicit width/height.');\n }\n\n // Set up container\n el.setAttribute('data-zoooom', '');\n if (!el.hasAttribute('tabindex')) {\n el.setAttribute('tabindex', '0');\n }\n el.setAttribute('role', 'application');\n el.setAttribute('aria-label', 'Image viewer — use arrow keys to pan, +/- to zoom');\n\n // Create image element\n const img = document.createElement('img');\n img.className = 'zoooom-image';\n img.setAttribute('draggable', 'false');\n el.appendChild(img);\n\n this.elements = { container: el, image: img, loadingOverlay: null };\n\n // Detect reduced motion\n const motionQuery = window.matchMedia('(prefers-reduced-motion: reduce)');\n const reducedMotion = this.options.respectReducedMotion && motionQuery.matches;\n\n // Initialize state\n this.state = {\n scale: 1,\n translateX: 0,\n translateY: 0,\n velocityX: 0,\n velocityY: 0,\n maxScale: typeof this.options.maxScale === 'number' ? this.options.maxScale : 10,\n isDragging: false,\n isAnimating: false,\n isLoaded: false,\n startX: 0,\n startY: 0,\n initialDistance: 0,\n initialScale: 1,\n initialTranslateX: 0,\n initialTranslateY: 0,\n pinchCenter: { x: 0, y: 0 },\n wheelTimeout: null,\n reducedMotion,\n };\n\n // Listen for reduced motion changes\n if (this.options.respectReducedMotion) {\n motionQuery.addEventListener('change', (e) => {\n this.state.reducedMotion = e.matches;\n });\n }\n\n // Attach input handlers\n if (this.options.mouse) {\n this.cleanups.push(attachMouse(this.state, this.elements, this.options.onPan));\n }\n if (this.options.touch) {\n this.cleanups.push(attachTouch(\n this.state, this.elements, this.options.overscaleFactor,\n this.options.onPan, this.options.onZoom,\n ));\n }\n if (this.options.wheel) {\n this.cleanups.push(attachWheel(\n this.state, this.elements, this.options.zoomFactor,\n this.options.trackpadSensitivity, this.options.onZoom,\n ));\n }\n if (this.options.keyboard) {\n this.cleanups.push(attachKeyboard(\n this.state, this.elements, this.options.panStep,\n this.options.zoomFactor, this.options.onPan, this.options.onZoom,\n ));\n }\n this.cleanups.push(attachGesture(this.state, this.elements, this.options.onZoom));\n\n // Resize handler\n this.resizeHandler = () => centerImage(this.state, this.elements);\n window.addEventListener('resize', this.resizeHandler);\n\n // Load initial image\n if (this.options.src) {\n this.load(this.options.src, this.options.alt);\n }\n }\n\n // --- Public state ---\n\n get scale(): number { return this.state.scale; }\n get translateX(): number { return this.state.translateX; }\n get translateY(): number { return this.state.translateY; }\n get isLoaded(): boolean { return this.state.isLoaded; }\n\n // --- Public methods ---\n\n zoomIn(): void {\n zoomTowardsPoint(\n this.state, this.elements, this.options.zoomFactor,\n undefined, undefined, this.options.onZoom,\n );\n this.emit('zoom', this.state.scale);\n }\n\n zoomOut(): void {\n zoomTowardsPoint(\n this.state, this.elements, 1 / this.options.zoomFactor,\n undefined, undefined, this.options.onZoom,\n );\n this.emit('zoom', this.state.scale);\n }\n\n /** \"Enhance.\" */\n enhance(): void {\n this.zoomIn();\n }\n\n zoomTo(scale: number): void {\n const delta = scale / this.state.scale;\n zoomTowardsPoint(this.state, this.elements, delta, undefined, undefined, this.options.onZoom);\n this.emit('zoom', this.state.scale);\n }\n\n zoomToPoint(scale: number, x: number, y: number): void {\n const delta = scale / this.state.scale;\n zoomTowardsPoint(this.state, this.elements, delta, x, y, this.options.onZoom);\n this.emit('zoom', this.state.scale);\n }\n\n panTo(x: number, y: number): void {\n this.state.translateX = x;\n this.state.translateY = y;\n updateTransform(this.state, this.elements);\n this.options.onPan?.(x, y);\n this.emit('pan', x, y);\n }\n\n panBy(dx: number, dy: number): void {\n this.state.translateX += dx;\n this.state.translateY += dy;\n updateTransform(this.state, this.elements);\n this.options.onPan?.(this.state.translateX, this.state.translateY);\n this.emit('pan', this.state.translateX, this.state.translateY);\n }\n\n reset(): void {\n resetView(this.state, this.elements);\n this.emit('reset');\n }\n\n center(): void {\n centerImage(this.state, this.elements);\n }\n\n load(src: string, alt?: string): void {\n loadImage(\n src,\n alt ?? this.options.alt,\n this.state,\n this.elements,\n this.options,\n this.emit.bind(this),\n );\n }\n\n /**\n * Apply velocity directly (used by joystick plugin).\n * Sets velocity and lets the rAF loop handle movement.\n */\n applyVelocity(vx: number, vy: number): void {\n this.state.translateX += vx;\n this.state.translateY += vy;\n updateTransform(this.state, this.elements);\n }\n\n /** Get the internal state (for plugin access) */\n getState(): Readonly<ZoooomState> {\n return this.state;\n }\n\n /** Get the managed elements (for plugin access) */\n getElements(): Readonly<ZoooomElements> {\n return this.elements;\n }\n\n // --- Events ---\n\n on(event: ZoooomEvent, handler: ZoooomEventHandler): void {\n if (!this.listeners.has(event)) {\n this.listeners.set(event, new Set());\n }\n this.listeners.get(event)!.add(handler);\n }\n\n off(event: ZoooomEvent, handler: ZoooomEventHandler): void {\n this.listeners.get(event)?.delete(handler);\n }\n\n emit(event: string, ...args: unknown[]): void {\n this.listeners.get(event)?.forEach(fn => fn(...args));\n }\n\n // --- Lifecycle ---\n\n destroy(): void {\n this.cleanups.forEach(fn => fn());\n this.cleanups = [];\n\n if (this.resizeHandler) {\n window.removeEventListener('resize', this.resizeHandler);\n this.resizeHandler = null;\n }\n\n if (this.state.wheelTimeout) {\n clearTimeout(this.state.wheelTimeout);\n }\n\n // Remove DOM\n this.elements.image.remove();\n if (this.elements.loadingOverlay) {\n this.elements.loadingOverlay.remove();\n }\n this.elements.container.removeAttribute('data-zoooom');\n this.elements.container.removeAttribute('role');\n this.elements.container.removeAttribute('aria-label');\n\n this.listeners.clear();\n this.emit('destroy');\n }\n}\n","/**\n * Create the joystick DOM structure.\n * Returns references to key elements for event binding.\n */\nexport interface JoystickDOM {\n wrap: HTMLElement;\n toggle: HTMLButtonElement;\n disc: HTMLElement;\n innerCircle: HTMLElement;\n zoomIn: HTMLElement;\n zoomOut: HTMLElement;\n}\n\nexport function createJoystickDOM(container: HTMLElement): JoystickDOM {\n // Toggle button (compass)\n const toggle = document.createElement('button');\n toggle.className = 'zoooom-joystick-toggle';\n toggle.setAttribute('aria-label', 'Toggle navigation joystick');\n toggle.setAttribute('aria-expanded', 'false');\n toggle.textContent = '\\u2316'; // ⌖ position indicator\n container.appendChild(toggle);\n\n // Joystick wrapper\n const wrap = document.createElement('div');\n wrap.className = 'zoooom-joystick-wrap';\n wrap.setAttribute('aria-hidden', 'true');\n\n // Disc (outer pan area)\n const disc = document.createElement('div');\n disc.className = 'zoooom-disc';\n disc.setAttribute('role', 'slider');\n disc.setAttribute('aria-label', 'Pan navigation control');\n disc.setAttribute('aria-valuenow', '0');\n disc.setAttribute('aria-valuemin', '0');\n disc.setAttribute('aria-valuemax', '1');\n disc.setAttribute('aria-valuetext', 'Center position — not moving');\n disc.setAttribute('tabindex', '0');\n\n // Inner circle (zoom)\n const innerCircle = document.createElement('div');\n innerCircle.className = 'zoooom-inner-circle';\n\n const zoomOut = document.createElement('div');\n zoomOut.className = 'zoooom-zoom-half zoooom-zoom-out';\n zoomOut.setAttribute('role', 'button');\n zoomOut.setAttribute('aria-label', 'Zoom out');\n zoomOut.setAttribute('tabindex', '0');\n zoomOut.textContent = '\\u2212'; // −\n\n const zoomIn = document.createElement('div');\n zoomIn.className = 'zoooom-zoom-half zoooom-zoom-in';\n zoomIn.setAttribute('role', 'button');\n zoomIn.setAttribute('aria-label', 'Zoom in');\n zoomIn.setAttribute('tabindex', '0');\n zoomIn.textContent = '+';\n\n innerCircle.appendChild(zoomOut);\n innerCircle.appendChild(zoomIn);\n\n // Direction arrows\n const arrows = document.createElement('div');\n arrows.className = 'zoooom-arrows';\n arrows.setAttribute('aria-hidden', 'true');\n for (const dir of ['n', 'e', 's', 'w']) {\n const arrow = document.createElement('div');\n arrow.className = `zoooom-arrow zoooom-arrow-${dir}`;\n arrows.appendChild(arrow);\n }\n\n disc.appendChild(innerCircle);\n disc.appendChild(arrows);\n wrap.appendChild(disc);\n container.appendChild(wrap);\n\n return { wrap, toggle, disc, innerCircle, zoomIn, zoomOut };\n}\n\nexport function destroyJoystickDOM(dom: JoystickDOM): void {\n dom.wrap.remove();\n dom.toggle.remove();\n}\n","export const JOYSTICK_CSS = `\n.zoooom-joystick-wrap {\n position: fixed;\n bottom: 20px;\n left: 50%;\n transform: translateX(-50%);\n z-index: 100;\n touch-action: none;\n opacity: 0;\n pointer-events: none;\n transition: opacity 0.3s ease-out, transform 0.3s ease-out;\n}\n\n.zoooom-joystick-wrap.visible {\n opacity: 1;\n pointer-events: auto;\n}\n\n.zoooom-joystick-toggle {\n position: fixed;\n bottom: 20px;\n left: 50%;\n transform: translateX(-50%);\n width: 56px;\n height: 56px;\n border-radius: 50%;\n background: rgba(0, 0, 0, 0.5);\n border: 2px solid rgba(255, 255, 255, 0.6);\n cursor: pointer;\n z-index: 99;\n display: flex;\n align-items: center;\n justify-content: center;\n color: #fff;\n font-size: 20px;\n font-weight: bold;\n backdrop-filter: blur(4px);\n transition: background 0.2s, box-shadow 0.2s;\n}\n\n.zoooom-joystick-toggle:hover {\n background: rgba(0, 0, 0, 0.7);\n box-shadow: 0 0 12px rgba(0, 0, 0, 0.4);\n}\n\n.zoooom-joystick-toggle:focus-visible {\n outline: 2px solid #2196f3;\n outline-offset: 2px;\n}\n\n.zoooom-disc {\n width: 200px;\n height: 200px;\n border-radius: 50%;\n background: rgba(0, 0, 0, 0.4);\n border: 2px solid rgba(255, 255, 255, 0.6);\n position: relative;\n display: flex;\n align-items: center;\n justify-content: center;\n touch-action: none;\n box-shadow: 0 0 10px rgba(0, 0, 0, 0.3);\n}\n\n.zoooom-disc.active {\n border-color: rgba(255, 255, 255, 0.9);\n}\n\n.zoooom-inner-circle {\n width: 72px;\n height: 72px;\n border-radius: 50%;\n background: rgba(255, 255, 255, 0.15);\n border: 1px solid rgba(255, 255, 255, 0.5);\n display: flex;\n position: relative;\n z-index: 3;\n}\n\n.zoooom-zoom-half {\n width: 50%;\n height: 100%;\n display: flex;\n align-items: center;\n justify-content: center;\n cursor: pointer;\n font-weight: bold;\n font-size: 22px;\n color: #fff;\n user-select: none;\n transition: background 0.15s;\n}\n\n.zoooom-zoom-half:hover {\n background: rgba(255, 255, 255, 0.25);\n}\n\n.zoooom-zoom-out {\n border-radius: 36px 0 0 36px;\n border-right: 1px solid rgba(255, 255, 255, 0.4);\n}\n\n.zoooom-zoom-in {\n border-radius: 0 36px 36px 0;\n}\n\n.zoooom-arrows {\n position: absolute;\n width: 100%;\n height: 100%;\n border-radius: 50%;\n pointer-events: none;\n overflow: hidden;\n}\n\n.zoooom-arrow {\n position: absolute;\n width: 0;\n height: 0;\n opacity: 0;\n transition: opacity 0.2s;\n}\n\n.zoooom-arrow-n {\n top: 14px;\n left: 50%;\n transform: translateX(-50%);\n border-left: 10px solid transparent;\n border-right: 10px solid transparent;\n border-bottom: 14px solid rgba(255, 255, 255, 0.7);\n}\n\n.zoooom-arrow-e {\n top: 50%;\n right: 14px;\n transform: translateY(-50%);\n border-top: 10px solid transparent;\n border-bottom: 10px solid transparent;\n border-left: 14px solid rgba(255, 255, 255, 0.7);\n}\n\n.zoooom-arrow-s {\n bottom: 14px;\n left: 50%;\n transform: translateX(-50%);\n border-left: 10px solid transparent;\n border-right: 10px solid transparent;\n border-top: 14px solid rgba(255, 255, 255, 0.7);\n}\n\n.zoooom-arrow-w {\n top: 50%;\n left: 14px;\n transform: translateY(-50%);\n border-top: 10px solid transparent;\n border-bottom: 10px solid transparent;\n border-right: 14px solid rgba(255, 255, 255, 0.7);\n}\n\n.zoooom-disc.north .zoooom-arrow-n,\n.zoooom-disc.south .zoooom-arrow-s,\n.zoooom-disc.east .zoooom-arrow-e,\n.zoooom-disc.west .zoooom-arrow-w,\n.zoooom-disc.north-east .zoooom-arrow-n,\n.zoooom-disc.north-east .zoooom-arrow-e,\n.zoooom-disc.south-east .zoooom-arrow-s,\n.zoooom-disc.south-east .zoooom-arrow-e,\n.zoooom-disc.south-west .zoooom-arrow-s,\n.zoooom-disc.south-west .zoooom-arrow-w,\n.zoooom-disc.north-west .zoooom-arrow-n,\n.zoooom-disc.north-west .zoooom-arrow-w {\n opacity: 1;\n}\n\n@media (max-width: 768px) {\n .zoooom-disc {\n width: 140px;\n height: 140px;\n }\n\n .zoooom-inner-circle {\n width: 56px;\n height: 56px;\n }\n\n .zoooom-joystick-toggle {\n width: 48px;\n height: 48px;\n font-size: 16px;\n }\n}\n\n@media (prefers-reduced-motion: reduce) {\n .zoooom-joystick-wrap {\n transition: none;\n }\n\n .zoooom-arrow {\n transition: none;\n }\n}\n`;\n\nlet injected = false;\n\nexport function injectJoystickStyles(): void {\n if (injected || typeof document === 'undefined') return;\n const style = document.createElement('style');\n style.setAttribute('data-zoooom-joystick', '');\n style.textContent = JOYSTICK_CSS;\n document.head.appendChild(style);\n injected = true;\n}\n","import type { JoystickOptions } from '../types.js';\nimport { JOYSTICK_RADIUS, JOYSTICK_DEADZONE, MAX_JOYSTICK_SPEED, DWELL_TIMEOUT } from '../core/constants.js';\nimport type { Zoooom } from '../core/Zoooom.js';\nimport { createJoystickDOM, destroyJoystickDOM, type JoystickDOM } from './dom.js';\nimport { injectJoystickStyles } from '../styles/joystick.js';\n\nconst DIRECTIONS = [\n 'east', 'south-east', 'south', 'south-west',\n 'west', 'north-west', 'north', 'north-east',\n] as const;\n\nfunction angleToDirection(angle: number): string {\n if (angle >= -22.5 && angle < 22.5) return 'east';\n if (angle >= 22.5 && angle < 67.5) return 'south-east';\n if (angle >= 67.5 && angle < 112.5) return 'south';\n if (angle >= 112.5 && angle < 157.5) return 'south-west';\n if (angle >= 157.5 || angle < -157.5) return 'west';\n if (angle >= -157.5 && angle < -112.5) return 'north-west';\n if (angle >= -112.5 && angle < -67.5) return 'north';\n return 'north-east';\n}\n\nexport class ZoooomJoystick {\n private viewer: Zoooom;\n private dom: JoystickDOM;\n private options: Required<JoystickOptions>;\n private visible = false;\n private active = false;\n private animationId: number | null = null;\n private joystickX = 0;\n private joystickY = 0;\n private currentDirection = '';\n private dwellTimer: ReturnType<typeof setTimeout> | null = null;\n private isDwelling = false;\n private hideTimer: ReturnType<typeof setTimeout> | null = null;\n\n constructor(viewer: Zoooom, options?: JoystickOptions) {\n this.viewer = viewer;\n this.options = {\n radius: options?.radius ?? JOYSTICK_RADIUS,\n deadzone: options?.deadzone ?? JOYSTICK_DEADZONE,\n maxSpeed: options?.maxSpeed ?? MAX_JOYSTICK_SPEED,\n position: options?.position ?? 'bottom-center',\n showToggle: options?.showToggle ?? true,\n dwellTimeout: options?.dwellTimeout ?? DWELL_TIMEOUT,\n };\n\n injectJoystickStyles();\n\n const elements = this.viewer.getElements();\n this.dom = createJoystickDOM(elements.container);\n this.bindEvents();\n }\n\n show(): void {\n this.visible = true;\n this.dom.wrap.classList.add('visible');\n this.dom.wrap.setAttribute('aria-hidden', 'false');\n this.dom.toggle.setAttribute('aria-expanded', 'true');\n if (this.hideTimer) clearTimeout(this.hideTimer);\n }\n\n hide(): void {\n this.visible = false;\n this.dom.wrap.classList.remove('visible');\n this.dom.wrap.setAttribute('aria-hidden', 'true');\n this.dom.toggle.setAttribute('aria-expanded', 'false');\n this.stopMovement();\n this.clearDirection();\n }\n\n destroy(): void {\n this.hide();\n this.stopMovement();\n if (this.dwellTimer) clearTimeout(this.dwellTimer);\n if (this.hideTimer) clearTimeout(this.hideTimer);\n destroyJoystickDOM(this.dom);\n }\n\n private bindEvents(): void {\n const { toggle, disc, zoomIn, zoomOut, innerCircle } = this.dom;\n\n // Toggle button\n toggle.addEventListener('click', () => {\n if (this.visible) this.hide();\n else this.show();\n });\n\n toggle.addEventListener('mouseenter', () => this.show());\n toggle.addEventListener('mouseleave', () => {\n this.hideTimer = setTimeout(() => this.hide(), 15000);\n });\n\n // Disc — panning\n disc.addEventListener('mousemove', (e) => {\n if (e.target !== disc) return;\n if (!this.isDwelling) {\n this.startDwell(e);\n } else {\n this.handleMove(e);\n }\n });\n\n disc.addEventListener('mousedown', (e) => {\n if (e.target !== disc) return;\n e.preventDefault();\n this.handleMove(e);\n\n const moveHandler = (me: MouseEvent) => this.handleMove(me);\n document.addEventListener('mousemove', moveHandler);\n document.addEventListener('mouseup', () => {\n document.removeEventListener('mousemove', moveHandler);\n this.stopDwell();\n this.resetJoystick();\n }, { once: true });\n });\n\n disc.addEventListener('mouseleave', () => {\n this.stopDwell();\n this.resetJoystick();\n });\n\n // Touch on disc\n disc.addEventListener('touchstart', (e) => {\n if (e.target !== disc) return;\n e.preventDefault();\n this.handleMove(e);\n\n const moveHandler = (te: TouchEvent) => this.handleMove(te);\n document.addEventListener('touchmove', moveHandler, { passive: false });\n document.addEventListener('touchend', () => {\n document.removeEventListener('touchmove', moveHandler);\n this.stopDwell();\n this.resetJoystick();\n }, { once: true });\n }, { passive: false });\n\n // Zoom buttons\n zoomIn.addEventListener('click', (e) => {\n e.stopPropagation();\n this.viewer.zoomIn();\n });\n\n zoomOut.addEventListener('click', (e) => {\n e.stopPropagation();\n this.viewer.zoomOut();\n });\n\n // Stop panning when entering inner circle\n innerCircle.addEventListener('mouseenter', () => {\n this.stopDwell();\n this.resetJoystick();\n });\n\n innerCircle.addEventListener('mousedown', (e) => e.stopPropagation());\n innerCircle.addEventListener('touchstart', (e) => e.stopPropagation(), { passive: false });\n }\n\n private handleMove(event: MouseEvent | TouchEvent): void {\n if (!this.visible) return;\n\n const clientX = 'clientX' in event ? event.clientX : event.touches[0]?.clientX ?? 0;\n const clientY = 'clientY' in event ? event.clientY : event.touches[0]?.clientY ?? 0;\n\n const rect = this.dom.disc.getBoundingClientRect();\n const centerX = rect.left + rect.width / 2;\n const centerY = rect.top + rect.height / 2;\n const distX = clientX - centerX;\n const distY = clientY - centerY;\n const distance = Math.sqrt(distX * distX + distY * distY);\n\n // Normalize to -1..1\n let normalizedX = distX / this.options.radius;\n let normalizedY = distY / this.options.radius;\n\n if (distance > this.options.radius) {\n normalizedX = normalizedX * (this.options.radius / distance);\n normalizedY = normalizedY * (this.options.radius / distance);\n }\n\n if (Math.abs(normalizedX) < this.options.deadzone) normalizedX = 0;\n if (Math.abs(normalizedY) < this.options.deadzone) normalizedY = 0;\n\n this.joystickX = normalizedX;\n this.joystickY = normalizedY;\n\n // Direction feedback\n if (distance > this.options.radius * this.options.deadzone) {\n const angle = Math.atan2(distY, distX) * 180 / Math.PI;\n const dir = angleToDirection(angle);\n if (dir !== this.currentDirection) {\n this.clearDirection();\n this.dom.disc.classList.add(dir);\n this.currentDirection = dir;\n }\n } else {\n this.clearDirection();\n }\n\n // Start movement if not already running\n if (!this.animationId && (Math.abs(normalizedX) > this.options.deadzone || Math.abs(normalizedY) > this.options.deadzone)) {\n this.active = true;\n this.dom.disc.classList.add('active');\n this.startMovement();\n this.updateAria(normalizedX, normalizedY);\n } else if (Math.abs(normalizedX) <= this.options.deadzone && Math.abs(normalizedY) <= this.options.deadzone) {\n this.active = false;\n this.dom.disc.classList.remove('active');\n this.stopMovement();\n this.dom.disc.setAttribute('aria-valuenow', '0');\n this.dom.disc.setAttribute('aria-valuetext', 'Center position — not moving');\n }\n }\n\n private startDwell(e: MouseEvent | TouchEvent): void {\n if (this.dwellTimer) clearTimeout(this.dwellTimer);\n this.dwellTimer = setTimeout(() => {\n this.isDwelling = true;\n this.handleMove(e);\n }, this.options.dwellTimeout);\n }\n\n private stopDwell(): void {\n if (this.dwellTimer) {\n clearTimeout(this.dwellTimer);\n this.dwellTimer = null;\n }\n this.isDwelling = false;\n }\n\n private startMovement(): void {\n if (this.animationId) return;\n const step = () => {\n if (!this.active) { this.stopMovement(); return; }\n const vx = -this.joystickX * this.options.maxSpeed;\n const vy = -this.joystickY * this.options.maxSpeed;\n this.viewer.applyVelocity(vx, vy);\n this.animationId = requestAnimationFrame(step);\n };\n this.animationId = requestAnimationFrame(step);\n }\n\n private stopMovement(): void {\n if (this.animationId) {\n cancelAnimationFrame(this.animationId);\n this.animationId = null;\n }\n }\n\n private resetJoystick(): void {\n this.joystickX = 0;\n this.joystickY = 0;\n this.active = false;\n this.stopMovement();\n this.clearDirection();\n this.dom.disc.classList.remove('active');\n }\n\n private clearDirection(): void {\n if (this.currentDirection) {\n this.dom.disc.classList.remove(this.currentDirection);\n this.currentDirection = '';\n }\n }\n\n private updateAria(x: number, y: number): void {\n const magnitude = Math.sqrt(x * x + y * y);\n this.dom.disc.setAttribute('aria-valuenow', magnitude.toFixed(2));\n\n let direction: string;\n if (Math.abs(x) > Math.abs(y)) {\n direction = x > 0 ? 'right' : 'left';\n } else {\n direction = y > 0 ? 'down' : 'up';\n }\n\n const intensity = magnitude > 0.7 ? 'fast' : magnitude > 0.3 ? 'medium' : 'slow';\n this.dom.disc.setAttribute('aria-valuetext', `Moving ${intensity} ${direction}`);\n }\n}\n"]}