@ewjdev/anyclick-react 2.0.0 → 4.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.
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/AnyclickProvider.tsx","../src/ContextMenu.tsx","../src/ScreenshotPreview.tsx","../src/styles.ts","../src/highlight.ts","../src/context.ts","../src/store.ts","../src/FunModeBridge.tsx","../src/InspectDialog/InspectDialogManager.tsx","../src/InspectDialog/InspectSimple.tsx","../src/ide.ts","../src/presets.ts","../src/types.ts","../src/index.ts","../src/AnyclickLogo.tsx"],"sourcesContent":["\"use client\";\n\n/**\n * AnyclickProvider - Main provider component for anyclick functionality.\n *\n * Wraps your app to enable right-click feedback capture. Supports scoped\n * providers and nested theming with inheritance.\n *\n * @module AnyclickProvider\n * @since 1.0.0\n */\nimport React, {\n useCallback,\n useEffect,\n useId,\n useLayoutEffect,\n useMemo,\n useRef,\n useState,\n} from \"react\";\nimport type {\n AnyclickClient,\n AnyclickMenuEvent,\n AnyclickType,\n ScreenshotData,\n} from \"@ewjdev/anyclick-core\";\nimport { createAnyclickClient } from \"@ewjdev/anyclick-core\";\nimport { ContextMenu } from \"./ContextMenu\";\nimport { AnyclickContext, useAnyclick } from \"./context\";\nimport { findContainerParent } from \"./highlight\";\nimport { type ProviderInstance, useProviderStore } from \"./store\";\nimport type {\n AnyclickContextValue,\n AnyclickProviderProps,\n AnyclickTheme,\n ContextMenuItem,\n} from \"./types\";\n\n/**\n * Default menu items shown when no custom items are provided.\n */\nconst defaultMenuItems: ContextMenuItem[] = [\n { label: \"Report an issue\", showComment: true, type: \"issue\" },\n { label: \"Request a feature\", showComment: true, type: \"feature\" },\n { label: \"I like this!\", showComment: false, type: \"like\" },\n];\n\nconst OFFSCREEN_POSITION = { x: -9999, y: -9999 };\n\n/**\n * AnyclickProvider component - wraps your app to enable feedback capture.\n *\n * Supports scoped providers and nested theming with inheritance.\n * Child providers automatically inherit and can override parent themes.\n *\n * @example\n * ```tsx\n * <AnyclickProvider\n * adapter={myAdapter}\n * menuItems={[\n * { type: \"bug\", label: \"Report Bug\", showComment: true },\n * ]}\n * onSubmitSuccess={(payload) => console.log(\"Submitted:\", payload)}\n * >\n * <App />\n * </AnyclickProvider>\n * ```\n *\n * @since 1.0.0\n */\nexport function AnyclickProvider({\n adapter,\n children,\n cooldownMs,\n disabled = false,\n header,\n highlightConfig,\n maxAncestors,\n maxInnerTextLength,\n maxOuterHTMLLength,\n menuClassName,\n menuItems = defaultMenuItems,\n menuStyle,\n metadata,\n onSubmitError,\n onSubmitSuccess,\n scoped = false,\n screenshotConfig,\n stripAttributes,\n targetFilter,\n theme,\n touchHoldDurationMs,\n touchMoveThreshold,\n}: AnyclickProviderProps) {\n const [isSubmitting, setIsSubmitting] = useState(false);\n const [menuVisible, setMenuVisible] = useState(false);\n const [menuPosition, setMenuPosition] = useState(OFFSCREEN_POSITION);\n const [targetElement, setTargetElement] = useState<Element | null>(null);\n const [containerElement, setContainerElement] = useState<Element | null>(\n null,\n );\n\n // Generate a stable ID for this provider instance using React's useId\n const providerId = useId();\n\n // Ref to the container element (for scoped providers)\n const containerRef = useRef<HTMLDivElement | null>(null);\n\n // Track when container is ready for scoped providers\n const [containerReady, setContainerReady] = useState(!scoped);\n\n // Client reference\n const clientRef = useRef<AnyclickClient | null>(null);\n\n // Callback ref to detect when container element is mounted\n const setContainerRef = useCallback(\n (node: HTMLDivElement | null) => {\n containerRef.current = node;\n if (scoped && node) {\n setContainerReady(true);\n // If client already exists, update its container\n if (clientRef.current) {\n clientRef.current.setContainer(node);\n }\n }\n },\n [scoped],\n );\n\n // Access parent context (if nested)\n let parentContext: AnyclickContextValue | null = null;\n try {\n parentContext = useAnyclick();\n } catch {\n parentContext = null;\n }\n\n // Store access\n const {\n findParentProvider,\n getMergedTheme,\n isDisabledByAncestor,\n isElementInAnyScopedProvider,\n isElementInDisabledScope,\n registerProvider,\n unregisterProvider,\n updateProvider,\n } = useProviderStore();\n\n // Determine parent ID\n const parentId = parentContext?.providerId ?? null;\n\n // Calculate depth\n const actualDepth = useMemo(() => {\n if (!parentContext) return 0;\n let d = 0;\n let currentId = parentId;\n const providers = useProviderStore.getState().providers;\n while (currentId) {\n d++;\n const parent = providers.get(currentId);\n currentId = parent?.parentId ?? null;\n }\n return d;\n }, [parentContext, parentId]);\n\n // Determine if disabled by theme\n const isDisabledByTheme = theme === null || theme?.disabled === true;\n const effectiveDisabled = disabled || isDisabledByTheme;\n\n // Build the theme for this provider\n const localTheme: AnyclickTheme = useMemo(() => {\n if (theme === null) {\n return { disabled: true };\n }\n\n const explicitThemeProps: AnyclickTheme = {};\n if (menuStyle) explicitThemeProps.menuStyle = menuStyle;\n if (menuClassName) explicitThemeProps.menuClassName = menuClassName;\n if (highlightConfig) explicitThemeProps.highlightConfig = highlightConfig;\n if (screenshotConfig)\n explicitThemeProps.screenshotConfig = screenshotConfig;\n\n return {\n ...explicitThemeProps,\n ...theme,\n };\n }, [highlightConfig, menuClassName, menuStyle, screenshotConfig, theme]);\n\n // Context menu handler\n const handleContextMenu = useCallback(\n (event: AnyclickMenuEvent, element: Element): boolean => {\n // For non-scoped providers, check if element is in a disabled scope\n if (!scoped && isElementInDisabledScope(element)) {\n return false;\n }\n\n // For non-scoped providers on touch events, defer to scoped providers\n if (!scoped && event.isTouch && isElementInAnyScopedProvider(element)) {\n return false;\n }\n\n const mergedTheme = getMergedTheme(providerId);\n\n setTargetElement(element);\n const container = findContainerParent(\n element,\n mergedTheme.highlightConfig ?? highlightConfig,\n );\n setContainerElement(container);\n setMenuPosition({ x: event.clientX, y: event.clientY });\n setMenuVisible(true);\n\n return true;\n },\n [\n getMergedTheme,\n highlightConfig,\n isElementInAnyScopedProvider,\n isElementInDisabledScope,\n providerId,\n scoped,\n ],\n );\n\n // Register this provider in the store\n useLayoutEffect(() => {\n const providerInstance: ProviderInstance = {\n containerRef: containerRef as React.RefObject<Element | null>,\n depth: actualDepth,\n disabled: effectiveDisabled,\n id: providerId,\n onContextMenu: handleContextMenu,\n parentId,\n scoped,\n theme: localTheme,\n };\n\n registerProvider(providerInstance);\n\n return () => {\n unregisterProvider(providerId);\n };\n }, [\n actualDepth,\n effectiveDisabled,\n handleContextMenu,\n localTheme,\n parentId,\n providerId,\n registerProvider,\n scoped,\n unregisterProvider,\n ]);\n\n // Update provider when config changes\n useEffect(() => {\n updateProvider(providerId, {\n disabled: effectiveDisabled,\n onContextMenu: handleContextMenu,\n theme: localTheme,\n });\n }, [\n effectiveDisabled,\n handleContextMenu,\n localTheme,\n providerId,\n updateProvider,\n ]);\n\n // Create/update the feedback client\n useEffect(() => {\n if (isDisabledByAncestor(providerId)) {\n return;\n }\n\n if (scoped && !containerReady) {\n return;\n }\n\n const client = createAnyclickClient({\n adapter,\n container: scoped ? containerRef.current : null,\n cooldownMs,\n maxAncestors,\n maxInnerTextLength,\n maxOuterHTMLLength,\n stripAttributes,\n targetFilter,\n touchHoldDurationMs,\n touchMoveThreshold,\n });\n\n client.onSubmitSuccess = onSubmitSuccess;\n client.onSubmitError = onSubmitError;\n client.onContextMenu = handleContextMenu;\n\n clientRef.current = client;\n\n if (!effectiveDisabled) {\n client.attach();\n }\n\n return () => {\n client.detach();\n };\n }, [\n adapter,\n containerReady,\n cooldownMs,\n effectiveDisabled,\n handleContextMenu,\n isDisabledByAncestor,\n maxAncestors,\n maxInnerTextLength,\n maxOuterHTMLLength,\n onSubmitError,\n onSubmitSuccess,\n providerId,\n scoped,\n stripAttributes,\n targetFilter,\n touchHoldDurationMs,\n touchMoveThreshold,\n ]);\n\n // Submit feedback with optional screenshots\n const submitAnyclick = useCallback(\n async (\n element: Element,\n type: AnyclickType,\n comment?: string,\n screenshots?: ScreenshotData,\n ) => {\n const client = clientRef.current;\n if (!client) return;\n\n setIsSubmitting(true);\n try {\n await client.submitAnyclick(element, type, {\n comment,\n metadata,\n screenshots,\n });\n } finally {\n setIsSubmitting(false);\n setMenuVisible(false);\n setMenuPosition(OFFSCREEN_POSITION);\n setTargetElement(null);\n setContainerElement(null);\n }\n },\n [metadata],\n );\n\n // Open menu programmatically\n const openMenu = useCallback(\n (element: Element, position: { x: number; y: number }) => {\n setTargetElement(element);\n const mergedTheme = getMergedTheme(providerId);\n const container = findContainerParent(\n element,\n mergedTheme.highlightConfig ?? highlightConfig,\n );\n setContainerElement(container);\n setMenuPosition(position);\n setMenuVisible(true);\n },\n [getMergedTheme, highlightConfig, providerId],\n );\n\n // Close menu\n const closeMenu = useCallback(() => {\n setMenuVisible(false);\n setMenuPosition(OFFSCREEN_POSITION);\n setTargetElement(null);\n setContainerElement(null);\n }, []);\n\n // Handle menu selection\n const handleMenuSelect = useCallback(\n (type: AnyclickType, comment?: string, screenshots?: ScreenshotData) => {\n if (targetElement) {\n submitAnyclick(targetElement, type, comment, screenshots);\n }\n },\n [submitAnyclick, targetElement],\n );\n\n // Get merged theme for this provider\n const inheritedTheme = getMergedTheme(providerId);\n\n // Merge: inherited theme first, then local theme overrides\n const mergedTheme: AnyclickTheme = useMemo(\n () => ({\n ...inheritedTheme,\n ...localTheme,\n highlightConfig: {\n ...inheritedTheme.highlightConfig,\n ...localTheme.highlightConfig,\n colors: {\n ...inheritedTheme.highlightConfig?.colors,\n ...localTheme.highlightConfig?.colors,\n },\n },\n screenshotConfig: {\n ...inheritedTheme.screenshotConfig,\n ...localTheme.screenshotConfig,\n },\n }),\n [inheritedTheme, localTheme],\n );\n\n // Apply merged theme styles\n const effectiveMenuStyle = mergedTheme.menuStyle ?? menuStyle;\n const effectiveMenuClassName = mergedTheme.menuClassName ?? menuClassName;\n const effectiveHighlightConfig =\n mergedTheme.highlightConfig ?? highlightConfig;\n const effectiveScreenshotConfig =\n mergedTheme.screenshotConfig ?? screenshotConfig;\n\n // Context value\n const contextValue: AnyclickContextValue = useMemo(\n () => ({\n closeMenu,\n isEnabled: !effectiveDisabled && !isDisabledByAncestor(providerId),\n isSubmitting,\n openMenu,\n providerId,\n scoped,\n submitAnyclick,\n theme: mergedTheme,\n }),\n [\n closeMenu,\n effectiveDisabled,\n isDisabledByAncestor,\n isSubmitting,\n mergedTheme,\n openMenu,\n providerId,\n scoped,\n submitAnyclick,\n ],\n );\n\n // For scoped providers, wrap children in a container div\n const content = scoped ? (\n <div\n ref={setContainerRef}\n data-anyclick-provider={providerId}\n style={{ display: \"contents\" }}\n >\n {children}\n </div>\n ) : (\n children\n );\n\n return (\n <AnyclickContext.Provider value={contextValue}>\n {content}\n <ContextMenu\n className={effectiveMenuClassName}\n containerElement={containerElement}\n header={header}\n highlightConfig={effectiveHighlightConfig}\n isSubmitting={isSubmitting}\n items={menuItems}\n onClose={closeMenu}\n onSelect={handleMenuSelect}\n position={menuPosition}\n screenshotConfig={effectiveScreenshotConfig}\n style={effectiveMenuStyle}\n targetElement={targetElement}\n visible={menuVisible && !effectiveDisabled}\n />\n </AnyclickContext.Provider>\n );\n}\n\n/**\n * @deprecated Use {@link AnyclickProvider} instead. Will be removed in v2.0.0.\n */\nexport const FeedbackProvider = AnyclickProvider;\n","\"use client\";\n\nimport React, { useCallback, useEffect, useRef, useState } from \"react\";\nimport type { AnyclickType, ScreenshotData } from \"@ewjdev/anyclick-core\";\nimport {\n DEFAULT_SCREENSHOT_CONFIG,\n captureAllScreenshots,\n isScreenshotSupported,\n} from \"@ewjdev/anyclick-core\";\nimport {\n CameraIcon,\n ChevronLeftIcon,\n ChevronRightIcon,\n FlagIcon,\n GripVertical,\n PlusIcon,\n ThumbsUpIcon,\n} from \"lucide-react\";\nimport { ScreenshotPreview } from \"./ScreenshotPreview\";\nimport { applyHighlights, clearHighlights } from \"./highlight\";\nimport { getBadgeStyle, menuStyles } from \"./styles\";\nimport type { ContextMenuItem, ContextMenuProps } from \"./types\";\n\n/** Padding from viewport edges in pixels */\nconst VIEWPORT_PADDING = 10;\n\n/**\n * Default icons for feedback types\n */\nconst defaultIcons: Record<string, React.ReactNode> = {\n feature: <PlusIcon className=\"w-4 h-4\" />,\n issue: <FlagIcon className=\"w-4 h-4\" />,\n like: <ThumbsUpIcon className=\"w-4 h-4\" />,\n};\n\nconst OFFSCREEN_POSITION = { x: -9999, y: -9999 };\n\n/**\n * Default header component for the context menu.\n */\nconst DefaultHeader = ({\n children,\n className,\n styles,\n title = \"Send Feedback\",\n}: {\n children?: React.ReactNode;\n className?: string;\n styles?: React.CSSProperties;\n title?: string;\n}) => {\n return (\n <div style={styles} className={className}>\n <span>{title}</span>\n {children}\n </div>\n );\n};\n\n/**\n * Menu item component with touch-friendly sizing.\n */\nconst MenuItem = React.memo(function MenuItem({\n disabled,\n hasChildren,\n item,\n onClick,\n}: {\n disabled: boolean;\n hasChildren?: boolean;\n item: ContextMenuItem;\n onClick: () => void;\n}) {\n const [isHovered, setIsHovered] = useState(false);\n const [isPressed, setIsPressed] = useState(false);\n const isComingSoon = item.status === \"comingSoon\";\n const badgeLabel = item.badge?.label ?? (isComingSoon ? \"Coming soon\" : null);\n const badgeTone = item.badge?.tone ?? (isComingSoon ? \"neutral\" : \"neutral\");\n\n const badgeStyle = badgeLabel ? getBadgeStyle(badgeTone) : undefined;\n const iconNode = item.icon ?? defaultIcons[item.type];\n\n return (\n <button\n type=\"button\"\n disabled={disabled || isComingSoon}\n onClick={onClick}\n onMouseEnter={() => setIsHovered(true)}\n onMouseLeave={() => {\n setIsHovered(false);\n setIsPressed(false);\n }}\n onTouchCancel={() => setIsPressed(false)}\n onTouchEnd={() => setIsPressed(false)}\n onTouchStart={() => setIsPressed(true)}\n style={{\n ...menuStyles.touchFriendly,\n ...menuStyles.item,\n ...(isHovered || isPressed ? menuStyles.itemHover : {}),\n ...(disabled ? menuStyles.itemDisabled : {}),\n }}\n >\n {iconNode ? <span style={menuStyles.itemIcon}>{iconNode}</span> : null}\n <span style={menuStyles.itemLabel}>\n {item.label}\n {badgeLabel && <span style={badgeStyle}>{badgeLabel}</span>}\n </span>\n {hasChildren && (\n <ChevronRightIcon className=\"w-4 h-4\" style={menuStyles.submenuIcon} />\n )}\n </button>\n );\n});\n\n/**\n * Back button for submenu navigation with touch-friendly sizing.\n */\nconst BackButton = React.memo(function BackButton({\n onClick,\n}: {\n onClick: () => void;\n}) {\n const [isHovered, setIsHovered] = useState(false);\n const [isPressed, setIsPressed] = useState(false);\n\n return (\n <button\n type=\"button\"\n onClick={onClick}\n onMouseEnter={() => setIsHovered(true)}\n onMouseLeave={() => {\n setIsHovered(false);\n setIsPressed(false);\n }}\n onTouchCancel={() => setIsPressed(false)}\n onTouchEnd={() => setIsPressed(false)}\n onTouchStart={() => setIsPressed(true)}\n style={{\n ...menuStyles.item,\n ...menuStyles.backButton,\n ...menuStyles.touchFriendly,\n ...(isHovered || isPressed ? menuStyles.itemHover : {}),\n }}\n >\n <ChevronLeftIcon className=\"w-4 h-4\" style={{ opacity: 0.5 }} />\n <span style={{ opacity: 0.7 }}>Back</span>\n </button>\n );\n});\n\n/**\n * Comment form component.\n */\nconst CommentForm = React.memo(function CommentForm({\n isSubmitting,\n onCancel,\n onSubmit,\n}: {\n isSubmitting: boolean;\n onCancel: () => void;\n onSubmit: (comment: string) => void;\n}) {\n const [comment, setComment] = useState(\"\");\n const inputRef = useRef<HTMLTextAreaElement>(null);\n\n useEffect(() => {\n inputRef.current?.focus();\n }, []);\n\n const handleSubmit = useCallback(() => {\n onSubmit(comment);\n }, [comment, onSubmit]);\n\n const handleKeyDown = useCallback(\n (e: React.KeyboardEvent) => {\n if (e.key === \"Enter\" && (e.metaKey || e.ctrlKey)) {\n handleSubmit();\n } else if (e.key === \"Escape\") {\n onCancel();\n }\n },\n [handleSubmit, onCancel],\n );\n\n return (\n <div style={menuStyles.commentSection}>\n <textarea\n ref={inputRef}\n disabled={isSubmitting}\n onChange={(e) => setComment(e.target.value)}\n onKeyDown={handleKeyDown}\n placeholder=\"Add a comment (optional)...\"\n style={menuStyles.commentInput}\n value={comment}\n />\n <div style={menuStyles.buttonRow}>\n <button\n type=\"button\"\n disabled={isSubmitting}\n onClick={onCancel}\n style={{ ...menuStyles.button, ...menuStyles.cancelButton }}\n >\n Cancel\n </button>\n <button\n type=\"button\"\n disabled={isSubmitting}\n onClick={handleSubmit}\n style={{\n ...menuStyles.button,\n ...menuStyles.submitButton,\n ...(isSubmitting ? menuStyles.submitButtonDisabled : {}),\n }}\n >\n {isSubmitting ? \"Sending...\" : \"Send\"}\n </button>\n </div>\n </div>\n );\n});\n\n/** View states for the context menu */\ntype MenuView = \"comment\" | \"menu\" | \"screenshot-preview\";\n\n/**\n * Calculate adjusted position to keep menu in viewport.\n */\nfunction calculateInViewPosition(\n requestedX: number,\n requestedY: number,\n menuWidth: number,\n menuHeight: number,\n): { x: number; y: number } {\n const viewportHeight = window.innerHeight;\n const viewportWidth = window.innerWidth;\n\n let x = requestedX;\n let y = requestedY;\n\n // Adjust X if menu would go off the right edge\n if (x + menuWidth > viewportWidth - VIEWPORT_PADDING) {\n x = viewportWidth - menuWidth - VIEWPORT_PADDING;\n }\n // Ensure X doesn't go off the left edge\n if (x < VIEWPORT_PADDING) {\n x = VIEWPORT_PADDING;\n }\n\n // Adjust Y if menu would go off the bottom edge\n if (y + menuHeight > viewportHeight - VIEWPORT_PADDING) {\n y = viewportHeight - menuHeight - VIEWPORT_PADDING;\n }\n // Ensure Y doesn't go off the top edge\n if (y < VIEWPORT_PADDING) {\n y = VIEWPORT_PADDING;\n }\n\n return { x, y };\n}\n\n/**\n * Context menu component for selecting feedback type.\n *\n * Displays a customizable context menu with support for:\n * - Custom menu items with icons and badges\n * - Submenus for organizing options\n * - Comment input for detailed feedback\n * - Screenshot preview before sending\n * - Touch-friendly interactions\n * - Dynamic positioning modes\n *\n * @since 1.0.0\n */\nexport function ContextMenu({\n className,\n containerElement,\n footer,\n header,\n highlightConfig,\n isSubmitting,\n items,\n onClose,\n onSelect,\n position,\n positionMode = \"inView\",\n screenshotConfig,\n style,\n targetElement,\n visible,\n}: ContextMenuProps) {\n const [selectedType, setSelectedType] = useState<AnyclickType | null>(null);\n const [currentView, setCurrentView] = useState<MenuView>(\"menu\");\n const [pendingComment, setPendingComment] = useState<string | undefined>();\n const [submenuStack, setSubmenuStack] = useState<ContextMenuItem[][]>([]);\n const [screenshots, setScreenshots] = useState<ScreenshotData | null>(null);\n const [isCapturing, setIsCapturing] = useState(false);\n const menuRef = useRef<HTMLDivElement>(null);\n\n // Position state for different modes\n const [adjustedPosition, setAdjustedPosition] = useState<{\n x: number;\n y: number;\n }>(OFFSCREEN_POSITION);\n const [isDragging, setIsDragging] = useState(false);\n const [dragOffset, setDragOffset] = useState<{ x: number; y: number }>({\n x: 0,\n y: 0,\n });\n const dragStartRef = useRef<{ x: number; y: number } | null>(null);\n\n // Merge screenshot config with defaults\n const mergedScreenshotConfig = React.useMemo(\n () => ({\n ...DEFAULT_SCREENSHOT_CONFIG,\n ...screenshotConfig,\n }),\n [screenshotConfig],\n );\n\n const showPreview =\n mergedScreenshotConfig.showPreview && isScreenshotSupported();\n\n // Current items to display (either root items or submenu items)\n const currentItems =\n submenuStack.length > 0 ? submenuStack[submenuStack.length - 1] : items;\n\n // Capture screenshots\n const captureScreenshots = useCallback(async () => {\n if (!targetElement || !showPreview) return;\n\n setIsCapturing(true);\n try {\n const captured = await captureAllScreenshots(\n targetElement,\n containerElement,\n mergedScreenshotConfig,\n );\n setScreenshots(captured);\n } catch (error) {\n console.error(\"Failed to capture screenshots:\", error);\n setScreenshots(null);\n } finally {\n setIsCapturing(false);\n }\n }, [containerElement, mergedScreenshotConfig, showPreview, targetElement]);\n\n // Reset state when menu closes\n useEffect(() => {\n if (!visible) {\n setSelectedType(null);\n setCurrentView(\"menu\");\n setPendingComment(undefined);\n setSubmenuStack([]);\n setScreenshots(null);\n setIsCapturing(false);\n setIsDragging(false);\n setDragOffset({ x: 0, y: 0 });\n setAdjustedPosition(OFFSCREEN_POSITION);\n dragStartRef.current = null;\n }\n }, [visible]);\n\n // Apply highlights to target element and container when menu opens\n useEffect(() => {\n if (visible && targetElement) {\n clearHighlights();\n applyHighlights(targetElement, highlightConfig);\n } else {\n clearHighlights();\n }\n\n return () => {\n clearHighlights();\n };\n }, [highlightConfig, targetElement, visible]);\n\n // Close menu when clicking outside of it\n useEffect(() => {\n if (!visible) {\n return;\n }\n\n const handlePointerDown = (event: PointerEvent) => {\n if (!menuRef.current) return;\n\n const target = event.target as Node;\n if ((target as HTMLElement).closest?.(\"[data-drag-handle]\")) {\n return;\n }\n if (!menuRef.current.contains(target)) {\n onClose();\n }\n };\n\n document.addEventListener(\"pointerdown\", handlePointerDown);\n return () => {\n document.removeEventListener(\"pointerdown\", handlePointerDown);\n };\n }, [onClose, visible]);\n\n // Reset adjusted position when menu opens at new position\n useEffect(() => {\n if (visible) {\n setAdjustedPosition(position);\n setDragOffset({ x: 0, y: 0 });\n }\n }, [position.x, position.y, visible]);\n\n // Calculate and apply position based on mode\n useEffect(() => {\n if (!visible || !menuRef.current) return;\n\n const updatePosition = () => {\n const menuElement = menuRef.current;\n if (!menuElement) return;\n\n const rect = menuElement.getBoundingClientRect();\n const baseX = position.x + dragOffset.x;\n const baseY = position.y + dragOffset.y;\n\n if (positionMode === \"static\") {\n setAdjustedPosition({ x: baseX, y: baseY });\n } else if (positionMode === \"inView\" || positionMode === \"dynamic\") {\n const adjusted = calculateInViewPosition(\n baseX,\n baseY,\n rect.width,\n rect.height,\n );\n setAdjustedPosition(adjusted);\n }\n };\n\n requestAnimationFrame(updatePosition);\n\n window.addEventListener(\"resize\", updatePosition);\n return () => window.removeEventListener(\"resize\", updatePosition);\n }, [currentView, dragOffset, position, positionMode, visible]);\n\n // Dragging logic for dynamic mode\n useEffect(() => {\n if (!visible || positionMode !== \"dynamic\") return;\n\n const handlePointerMove = (event: PointerEvent) => {\n if (!isDragging || !dragStartRef.current) return;\n\n const deltaX = event.clientX - dragStartRef.current.x;\n const deltaY = event.clientY - dragStartRef.current.y;\n\n setDragOffset((prev) => ({\n x: prev.x + deltaX,\n y: prev.y + deltaY,\n }));\n\n dragStartRef.current = { x: event.clientX, y: event.clientY };\n };\n\n const handlePointerUp = () => {\n setIsDragging(false);\n dragStartRef.current = null;\n };\n\n if (isDragging) {\n document.addEventListener(\"pointermove\", handlePointerMove);\n document.addEventListener(\"pointerup\", handlePointerUp);\n document.addEventListener(\"pointercancel\", handlePointerUp);\n\n return () => {\n document.removeEventListener(\"pointermove\", handlePointerMove);\n document.removeEventListener(\"pointerup\", handlePointerUp);\n document.removeEventListener(\"pointercancel\", handlePointerUp);\n };\n }\n }, [isDragging, positionMode, visible]);\n\n // Handle drag start\n const handleDragStart = useCallback(\n (event: React.PointerEvent) => {\n if (positionMode !== \"dynamic\") return;\n event.preventDefault();\n setIsDragging(true);\n dragStartRef.current = { x: event.clientX, y: event.clientY };\n },\n [positionMode],\n );\n\n // Handle escape key\n useEffect(() => {\n const handleKeyDown = (e: KeyboardEvent) => {\n if (e.key === \"Escape\") {\n if (currentView === \"screenshot-preview\") {\n setCurrentView(\"comment\");\n } else if (currentView === \"comment\") {\n setCurrentView(\"menu\");\n setSelectedType(null);\n setPendingComment(undefined);\n } else if (submenuStack.length > 0) {\n setSubmenuStack((prev) => prev.slice(0, -1));\n } else {\n onClose();\n }\n }\n };\n\n if (visible) {\n document.addEventListener(\"keydown\", handleKeyDown);\n return () => document.removeEventListener(\"keydown\", handleKeyDown);\n }\n }, [currentView, onClose, submenuStack.length, visible]);\n\n // Prevent touch default behaviors on menu container\n useEffect(() => {\n const menuElement = menuRef.current;\n if (!visible || !menuElement) return;\n\n const preventTouchDefault = (e: TouchEvent) => {\n const target = e.target as HTMLElement;\n if (\n target.tagName === \"TEXTAREA\" ||\n target.tagName === \"INPUT\" ||\n target.isContentEditable\n ) {\n return;\n }\n e.preventDefault();\n };\n\n menuElement.addEventListener(\"touchmove\", preventTouchDefault, {\n passive: false,\n });\n\n return () => {\n menuElement.removeEventListener(\"touchmove\", preventTouchDefault);\n };\n }, [visible]);\n\n if (!visible || !targetElement) {\n return null;\n }\n\n const handleItemClick = (item: ContextMenuItem) => {\n if (item.status === \"comingSoon\") {\n return;\n }\n\n if (item.children && item.children.length > 0) {\n setSubmenuStack((prev) => [...prev, item.children!]);\n return;\n }\n\n if (item.onClick) {\n try {\n return item.onClick({\n closeMenu: onClose,\n containerElement,\n targetElement,\n });\n } catch (error) {\n console.error(\"Anyclick menu onClick error:\", error);\n return;\n }\n }\n\n if (item.showComment) {\n setSelectedType(item.type);\n setCurrentView(\"comment\");\n } else {\n if (showPreview) {\n setSelectedType(item.type);\n setCurrentView(\"screenshot-preview\");\n captureScreenshots();\n } else {\n onSelect(item.type);\n }\n }\n };\n\n const handleBack = () => {\n setSubmenuStack((prev) => prev.slice(0, -1));\n };\n\n const handleCommentSubmit = (comment: string) => {\n if (!selectedType) return;\n\n if (showPreview) {\n setPendingComment(comment || undefined);\n setCurrentView(\"screenshot-preview\");\n captureScreenshots();\n } else {\n onSelect(selectedType, comment || undefined);\n }\n };\n\n const handleCommentCancel = () => {\n setCurrentView(\"menu\");\n setSelectedType(null);\n setPendingComment(undefined);\n };\n\n const handleScreenshotConfirm = (confirmedScreenshots: ScreenshotData) => {\n if (selectedType) {\n onSelect(selectedType, pendingComment, confirmedScreenshots);\n }\n };\n\n const handleScreenshotCancel = () => {\n if (pendingComment !== undefined) {\n setCurrentView(\"comment\");\n } else {\n setCurrentView(\"menu\");\n setSelectedType(null);\n }\n setScreenshots(null);\n };\n\n const handleRetakeScreenshots = () => {\n captureScreenshots();\n };\n\n const containerWidth = currentView === \"screenshot-preview\" ? 360 : undefined;\n\n return (\n <div\n ref={menuRef}\n aria-label=\"Feedback options\"\n className={className}\n role=\"menu\"\n style={{\n ...menuStyles.container,\n left: adjustedPosition.x,\n top: adjustedPosition.y,\n ...(containerWidth\n ? { minWidth: containerWidth, width: containerWidth }\n : {}),\n touchAction: \"none\",\n userSelect: \"none\",\n WebkitTouchCallout: \"none\",\n WebkitUserSelect: \"none\",\n ...(isDragging ? { cursor: \"grabbing\" } : {}),\n ...style,\n }}\n >\n {!header && currentView !== \"screenshot-preview\" && (\n <DefaultHeader styles={menuStyles.header} title=\"Send Feedback\">\n {showPreview && (\n <div style={menuStyles.screenshotIndicator}>\n <CameraIcon className=\"w-3 h-3\" />\n </div>\n )}\n {positionMode === \"dynamic\" && (\n <div\n data-drag-handle\n onMouseEnter={(e) => {\n (e.currentTarget as HTMLElement).style.opacity = \"1\";\n }}\n onMouseLeave={(e) => {\n (e.currentTarget as HTMLElement).style.opacity = \"0.5\";\n }}\n onPointerDown={handleDragStart}\n style={{\n ...menuStyles.dragHandle,\n cursor: isDragging ? \"grabbing\" : \"grab\",\n }}\n title=\"Drag to move\"\n >\n <GripVertical className=\"w-4 h-4\" />\n </div>\n )}\n </DefaultHeader>\n )}\n {!!header && header}\n\n {currentView === \"menu\" && (\n <div style={menuStyles.itemList}>\n {submenuStack.length > 0 && <BackButton onClick={handleBack} />}\n {currentItems.map((item) => (\n <MenuItem\n key={item.type}\n disabled={isSubmitting}\n hasChildren={item.children && item.children.length > 0}\n item={item}\n onClick={() => handleItemClick(item)}\n />\n ))}\n </div>\n )}\n\n {currentView === \"comment\" && (\n <CommentForm\n isSubmitting={isSubmitting}\n onCancel={handleCommentCancel}\n onSubmit={handleCommentSubmit}\n />\n )}\n\n {currentView === \"screenshot-preview\" && (\n <ScreenshotPreview\n isLoading={isCapturing}\n isSubmitting={isSubmitting}\n onCancel={handleScreenshotCancel}\n onConfirm={handleScreenshotConfirm}\n onRetake={handleRetakeScreenshots}\n screenshots={screenshots}\n />\n )}\n </div>\n );\n}\n","\"use client\";\n\nimport React, { useMemo, useState } from \"react\";\nimport type { ScreenshotData, ScreenshotError } from \"@ewjdev/anyclick-core\";\nimport { estimateTotalSize, formatBytes } from \"@ewjdev/anyclick-core\";\nimport {\n AlertCircleIcon,\n CheckIcon,\n ExpandIcon,\n ImageIcon,\n Loader2Icon,\n RefreshCwIcon,\n ShrinkIcon,\n XIcon,\n} from \"lucide-react\";\nimport { menuStyles, screenshotPreviewStyles as styles } from \"./styles\";\nimport type { ScreenshotPreviewProps } from \"./types\";\n\n/** Screenshot preview tab types */\ntype TabType = \"container\" | \"element\" | \"viewport\";\n\n/**\n * Screenshot preview component - shows captured screenshots before sending.\n *\n * Displays a preview of captured screenshots with tabs for element, container,\n * and viewport captures. Allows users to review, retake, or proceed without\n * screenshots.\n *\n * @since 1.0.0\n */\nexport const ScreenshotPreview = React.memo(function ScreenshotPreview({\n isLoading,\n isSubmitting,\n onCancel,\n onConfirm,\n onRetake,\n screenshots,\n}: ScreenshotPreviewProps) {\n const [activeTab, setActiveTab] = useState<TabType>(\"element\");\n const [isExpanded, setIsExpanded] = useState(false);\n\n // Get error for a specific tab\n const getError = (key: TabType): ScreenshotError | undefined => {\n return screenshots?.errors?.[key];\n };\n\n // Memoize tabs computation\n const tabs = useMemo(() => {\n if (!screenshots) return [];\n\n const allTabs: {\n data: typeof screenshots.element;\n error?: ScreenshotError;\n key: TabType;\n label: string;\n }[] = [\n {\n data: screenshots.element,\n error: getError(\"element\"),\n key: \"element\" as const,\n label: \"Element\",\n },\n {\n data: screenshots.container,\n error: getError(\"container\"),\n key: \"container\" as const,\n label: \"Container\",\n },\n {\n data: screenshots.viewport,\n error: getError(\"viewport\"),\n key: \"viewport\" as const,\n label: \"Viewport\",\n },\n ];\n\n // Show tabs that have either data or errors\n return allTabs.filter((tab) => tab.data || tab.error);\n }, [screenshots]);\n\n // Memoize total size calculation\n const totalSize = useMemo(\n () => (screenshots ? estimateTotalSize(screenshots) : 0),\n [screenshots],\n );\n\n if (isLoading) {\n return (\n <div style={styles.container}>\n <div style={styles.loadingContainer}>\n <Loader2Icon\n className=\"w-6 h-6 animate-spin\"\n style={{ color: \"#3b82f6\" }}\n />\n <span style={styles.loadingText}>Capturing screenshots...</span>\n </div>\n </div>\n );\n }\n\n if (!screenshots) {\n return (\n <div style={styles.container}>\n <div style={styles.emptyContainer}>\n <ImageIcon className=\"w-8 h-8\" style={{ color: \"#9ca3af\" }} />\n <span style={styles.emptyText}>Screenshots unavailable</span>\n <span style={styles.emptySubtext}>\n Some elements can&apos;t be captured (e.g., gradient text)\n </span>\n <div style={styles.emptyActions}>\n <button\n type=\"button\"\n disabled={isSubmitting}\n onClick={onRetake}\n style={styles.retakeButtonOutline}\n >\n <RefreshCwIcon className=\"w-4 h-4\" />\n Try Again\n </button>\n <button\n type=\"button\"\n disabled={isSubmitting}\n onClick={() =>\n onConfirm({ capturedAt: new Date().toISOString() })\n }\n style={styles.continueButton}\n >\n <CheckIcon className=\"w-4 h-4\" />\n Continue Without\n </button>\n </div>\n </div>\n </div>\n );\n }\n\n const activeScreenshot =\n activeTab === \"element\"\n ? screenshots.element\n : activeTab === \"container\"\n ? screenshots.container\n : screenshots.viewport;\n\n const activeError = getError(activeTab);\n\n return (\n <div\n style={{\n ...styles.container,\n ...(isExpanded ? styles.containerExpanded : {}),\n padding: \"8px\",\n }}\n >\n <div style={styles.header}>\n <span style={styles.headerTitle}>Review Screenshots</span>\n <div style={styles.headerActions}>\n <span style={styles.sizeLabel}>{formatBytes(totalSize)}</span>\n <button\n type=\"button\"\n onClick={() => setIsExpanded(!isExpanded)}\n style={styles.iconButton}\n title={isExpanded ? \"Collapse\" : \"Expand\"}\n >\n {isExpanded ? (\n <ShrinkIcon className=\"w-4 h-4\" />\n ) : (\n <ExpandIcon className=\"w-4 h-4\" />\n )}\n </button>\n </div>\n </div>\n\n {/* Tabs */}\n <div style={styles.tabContainer}>\n {tabs.map((tab) => (\n <button\n key={tab.key}\n type=\"button\"\n onClick={() => setActiveTab(tab.key)}\n style={{\n ...styles.tab,\n ...(activeTab === tab.key ? styles.tabActive : {}),\n ...(tab.error && !tab.data ? styles.tabError : {}),\n }}\n >\n {tab.error && !tab.data && (\n <AlertCircleIcon\n className=\"w-3 h-3\"\n style={{ color: \"#ef4444\" }}\n />\n )}\n {tab.label}\n {tab.data && (\n <span style={styles.tabSize}>\n {formatBytes(tab.data.sizeBytes)}\n </span>\n )}\n </button>\n ))}\n </div>\n\n {/* Preview image */}\n <div\n style={{\n ...styles.previewContainer,\n ...(isExpanded ? styles.previewContainerExpanded : {}),\n }}\n >\n {activeScreenshot ? (\n <img\n alt={`${activeTab} screenshot`}\n src={activeScreenshot.dataUrl}\n style={styles.previewImage}\n />\n ) : activeError ? (\n <div style={styles.errorPreview}>\n <AlertCircleIcon className=\"w-8 h-8\" style={{ color: \"#ef4444\" }} />\n <span style={styles.errorTitle}>Capture Failed</span>\n <span style={styles.errorMessage}>{activeError.message}</span>\n </div>\n ) : (\n <div style={styles.noPreview}>\n <ImageIcon className=\"w-6 h-6\" style={{ color: \"#9ca3af\" }} />\n <span>No {activeTab} screenshot</span>\n </div>\n )}\n </div>\n\n {/* Dimensions info */}\n {activeScreenshot && (\n <div style={styles.dimensionsInfo}>\n {activeScreenshot.width} × {activeScreenshot.height}px\n </div>\n )}\n\n {/* Actions */}\n <div style={styles.actions}>\n <button\n type=\"button\"\n disabled={isSubmitting}\n onClick={onRetake}\n style={styles.retakeButtonSmall}\n >\n <RefreshCwIcon className=\"w-3 h-3\" />\n Retake\n </button>\n <div style={styles.actionsRight}>\n <button\n type=\"button\"\n className=\"flex items-center gap-1\"\n disabled={isSubmitting}\n onClick={onCancel}\n style={{ ...menuStyles.button, ...menuStyles.cancelButton }}\n >\n <XIcon className=\"w-3 h-3\" />\n Cancel\n </button>\n <button\n type=\"button\"\n disabled={isSubmitting}\n onClick={() => onConfirm(screenshots)}\n style={{\n ...menuStyles.button,\n ...menuStyles.submitButton,\n ...(isSubmitting ? menuStyles.submitButtonDisabled : {}),\n }}\n >\n {isSubmitting ? (\n <>\n <Loader2Icon className=\"w-3 h-3 animate-spin\" />\n Sending...\n </>\n ) : (\n <>\n <CheckIcon className=\"w-3 h-3\" />\n Send\n </>\n )}\n </button>\n </div>\n </div>\n </div>\n );\n});\n","/**\n * Style definitions for anyclick-react components.\n *\n * This module provides consolidated styling for all UI components,\n * including CSS custom properties for theming and dark mode support.\n *\n * @module styles\n * @since 1.0.0\n */\nimport type { CSSProperties } from \"react\";\n\n// ============================================================================\n// CSS Custom Properties\n// ============================================================================\n\n/**\n * CSS custom properties for menu theming.\n *\n * These can be overridden via the `style` prop on AnyclickProvider.\n *\n * @example\n * ```tsx\n * <AnyclickProvider\n * theme={{\n * menuStyle: {\n * '--anyclick-menu-bg': 'rgba(0, 0, 0, 0.9)',\n * '--anyclick-menu-text': '#ffffff',\n * '--anyclick-menu-border': 'rgba(255, 255, 255, 0.1)',\n * '--anyclick-menu-hover': 'rgba(255, 255, 255, 0.1)',\n * '--anyclick-menu-accent': '#f59e0b',\n * }\n * }}\n * />\n * ```\n *\n * @since 1.0.0\n */\nexport const menuCSSVariables = {\n \"--anyclick-menu-accent\": \"#0066cc\",\n \"--anyclick-menu-accent-text\": \"#ffffff\",\n \"--anyclick-menu-bg\": \"#ffffff\",\n \"--anyclick-menu-border\": \"#e5e5e5\",\n \"--anyclick-menu-cancel-bg\": \"#f0f0f0\",\n \"--anyclick-menu-cancel-text\": \"#666666\",\n \"--anyclick-menu-hover\": \"#f5f5f5\",\n \"--anyclick-menu-input-bg\": \"#ffffff\",\n \"--anyclick-menu-input-border\": \"#dddddd\",\n \"--anyclick-menu-text\": \"#333333\",\n \"--anyclick-menu-text-muted\": \"#666666\",\n} as const;\n\n// ============================================================================\n// Badge Styles\n// ============================================================================\n\n/**\n * Badge tone color configuration.\n * @internal\n */\nconst badgeToneColors = {\n info: {\n backgroundColor: \"rgba(59, 130, 246, 0.15)\",\n border: \"1px solid rgba(59, 130, 246, 0.3)\",\n color: \"#60a5fa\",\n },\n neutral: {\n backgroundColor: \"rgba(148, 163, 184, 0.15)\",\n border: \"1px solid rgba(148, 163, 184, 0.3)\",\n color: \"#cbd5e1\",\n },\n success: {\n backgroundColor: \"rgba(34, 197, 94, 0.15)\",\n border: \"1px solid rgba(34, 197, 94, 0.3)\",\n color: \"#4ade80\",\n },\n warning: {\n backgroundColor: \"rgba(251, 191, 36, 0.15)\",\n border: \"1px solid rgba(251, 191, 36, 0.3)\",\n color: \"#fbbf24\",\n },\n} as const;\n\n/**\n * Gets badge styles for a specific tone.\n *\n * @param tone - The badge tone (info, neutral, success, warning)\n * @returns CSSProperties for the badge\n *\n * @example\n * ```tsx\n * const style = getBadgeStyle(\"success\");\n * // => { backgroundColor: \"rgba(34, 197, 94, 0.15)\", ... }\n * ```\n *\n * @since 1.2.0\n */\nexport function getBadgeStyle(\n tone: \"info\" | \"neutral\" | \"success\" | \"warning\" = \"neutral\",\n): CSSProperties {\n const toneColors = badgeToneColors[tone];\n return {\n alignItems: \"center\",\n backgroundColor: toneColors.backgroundColor,\n border: toneColors.border,\n borderRadius: \"9999px\",\n color: toneColors.color,\n display: \"inline-flex\",\n fontSize: \"10px\",\n lineHeight: 1.2,\n padding: \"2px 6px\",\n };\n}\n\n// ============================================================================\n// Menu Styles\n// ============================================================================\n\n/**\n * Core menu component styles.\n *\n * @since 1.0.0\n */\nexport const menuStyles: Record<string, CSSProperties> = {\n backButton: {\n borderBottom: \"1px solid var(--anyclick-menu-border, #e5e5e5)\",\n marginBottom: \"4px\",\n minHeight: \"44px\",\n },\n button: {\n border: \"none\",\n borderRadius: \"6px\",\n cursor: \"pointer\",\n fontSize: \"13px\",\n fontWeight: 500,\n padding: \"6px 12px\",\n transition: \"background-color 0.15s, opacity 0.15s\",\n },\n buttonRow: {\n display: \"flex\",\n gap: \"8px\",\n justifyContent: \"flex-end\",\n marginTop: \"8px\",\n },\n cancelButton: {\n alignItems: \"center\",\n backgroundColor: \"var(--anyclick-menu-cancel-bg, #f0f0f0)\",\n color: \"var(--anyclick-menu-cancel-text, #666)\",\n display: \"flex\",\n gap: \"2px\",\n },\n commentInput: {\n backgroundColor: \"var(--anyclick-menu-input-bg, #ffffff)\",\n border: \"1px solid var(--anyclick-menu-input-border, #ddd)\",\n borderRadius: \"6px\",\n boxSizing: \"border-box\" as const,\n color: \"var(--anyclick-menu-text, #333)\",\n fontFamily: \"inherit\",\n fontSize: \"14px\",\n minHeight: \"60px\",\n outline: \"none\",\n padding: \"8px 12px\",\n resize: \"vertical\" as const,\n width: \"100%\",\n },\n commentSection: {\n borderTop: \"1px solid var(--anyclick-menu-border, #e5e5e5)\",\n padding: \"12px 16px\",\n },\n container: {\n backgroundColor: \"var(--anyclick-menu-bg, #ffffff)\",\n borderRadius: \"8px\",\n boxShadow: \"0 4px 12px rgba(0, 0, 0, 0.15), 0 0 0 1px rgba(0, 0, 0, 0.05)\",\n fontFamily:\n '-apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, sans-serif',\n fontSize: \"14px\",\n minWidth: \"200px\",\n overflow: \"hidden\",\n position: \"fixed\",\n zIndex: 9999,\n ...menuCSSVariables,\n },\n dragHandle: {\n alignItems: \"center\",\n borderRadius: \"4px\",\n display: \"flex\",\n marginRight: \"-4px\",\n opacity: 0.5,\n padding: \"4px\",\n transition: \"opacity 0.15s\",\n },\n header: {\n alignItems: \"center\",\n borderBottom: \"1px solid var(--anyclick-menu-border, #e5e5e5)\",\n color: \"var(--anyclick-menu-text-muted, #666)\",\n display: \"flex\",\n fontSize: \"12px\",\n fontWeight: 500,\n justifyContent: \"space-between\",\n letterSpacing: \"0.5px\",\n padding: \"8px 12px\",\n textTransform: \"uppercase\" as const,\n },\n item: {\n alignItems: \"center\",\n backgroundColor: \"transparent\",\n border: \"none\",\n color: \"var(--anyclick-menu-text, #333)\",\n cursor: \"pointer\",\n display: \"flex\",\n fontSize: \"14px\",\n gap: \"10px\",\n padding: \"10px 16px\",\n textAlign: \"left\" as const,\n transition: \"background-color 0.15s\",\n width: \"100%\",\n },\n itemDisabled: {\n cursor: \"not-allowed\",\n opacity: 0.5,\n },\n itemHover: {\n backgroundColor: \"var(--anyclick-menu-hover, #f5f5f5)\",\n },\n itemIcon: {\n alignItems: \"center\",\n display: \"flex\",\n fontSize: \"16px\",\n height: \"20px\",\n justifyContent: \"center\",\n width: \"20px\",\n },\n itemLabel: {\n alignItems: \"center\",\n display: \"inline-flex\",\n flex: 1,\n gap: \"8px\",\n },\n itemList: {\n padding: \"0px 0px\",\n },\n overlay: {\n inset: 0,\n position: \"fixed\",\n zIndex: 9998,\n },\n screenshotIndicator: {\n display: \"flex\",\n flex: 1,\n justifyContent: \"flex-end\",\n marginLeft: \"4px\",\n opacity: 0.7,\n },\n submenuIcon: {\n marginLeft: \"auto\",\n opacity: 0.5,\n },\n submitButton: {\n alignItems: \"center\",\n backgroundColor: \"var(--anyclick-menu-accent, #0066cc)\",\n color: \"var(--anyclick-menu-accent-text, #ffffff)\",\n display: \"flex\",\n gap: \"2px\",\n },\n submitButtonDisabled: {\n cursor: \"not-allowed\",\n opacity: 0.6,\n },\n touchFriendly: {\n minHeight: \"38px\",\n userSelect: \"none\",\n WebkitTouchCallout: \"none\",\n WebkitUserSelect: \"none\",\n },\n};\n\n// ============================================================================\n// Dark Mode Styles\n// ============================================================================\n\n/**\n * Dark mode menu styles.\n *\n * Apply these styles for dark theme support.\n *\n * @since 1.0.0\n */\nexport const darkMenuStyles: Record<string, CSSProperties> = {\n cancelButton: {\n ...menuStyles.cancelButton,\n backgroundColor: \"#333\",\n color: \"#ccc\",\n },\n commentInput: {\n ...menuStyles.commentInput,\n backgroundColor: \"#2a2a2a\",\n border: \"1px solid #444\",\n color: \"#e0e0e0\",\n },\n commentSection: {\n ...menuStyles.commentSection,\n borderTop: \"1px solid #333\",\n },\n container: {\n ...menuStyles.container,\n backgroundColor: \"#1a1a1a\",\n boxShadow:\n \"0 4px 12px rgba(0, 0, 0, 0.4), 0 0 0 1px rgba(255, 255, 255, 0.1)\",\n },\n header: {\n ...menuStyles.header,\n borderBottom: \"1px solid #333\",\n color: \"#888\",\n },\n item: {\n ...menuStyles.item,\n color: \"#e0e0e0\",\n },\n itemHover: {\n backgroundColor: \"#2a2a2a\",\n },\n};\n\n// ============================================================================\n// Screenshot Preview Styles\n// ============================================================================\n\n/**\n * Screenshot preview component styles.\n *\n * @since 1.0.0\n */\nexport const screenshotPreviewStyles: Record<string, CSSProperties> = {\n actions: {\n alignItems: \"center\",\n borderTop: \"1px solid #e5e7eb\",\n display: \"flex\",\n justifyContent: \"space-between\",\n paddingTop: \"8px\",\n },\n actionsRight: {\n display: \"flex\",\n gap: \"8px\",\n },\n container: {\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"8px\",\n width: \"100%\",\n },\n containerExpanded: {\n backgroundColor: \"#fff\",\n borderRadius: \"12px\",\n boxShadow: \"0 25px 50px -12px rgba(0, 0, 0, 0.25)\",\n left: \"50%\",\n maxHeight: \"90vh\",\n maxWidth: \"800px\",\n padding: \"16px\",\n position: \"fixed\",\n top: \"50%\",\n transform: \"translate(-50%, -50%)\",\n width: \"90vw\",\n zIndex: 10000,\n },\n continueButton: {\n alignItems: \"center\",\n backgroundColor: \"#3b82f6\",\n border: \"none\",\n borderRadius: \"6px\",\n color: \"#fff\",\n cursor: \"pointer\",\n display: \"flex\",\n fontSize: \"12px\",\n fontWeight: \"500\",\n gap: \"6px\",\n padding: \"8px 12px\",\n },\n dimensionsInfo: {\n color: \"#9ca3af\",\n fontSize: \"11px\",\n textAlign: \"center\" as const,\n },\n emptyActions: {\n display: \"flex\",\n gap: \"8px\",\n marginTop: \"8px\",\n },\n emptyContainer: {\n alignItems: \"center\",\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"8px\",\n justifyContent: \"center\",\n padding: \"24px\",\n },\n emptySubtext: {\n color: \"#9ca3af\",\n fontSize: \"11px\",\n textAlign: \"center\" as const,\n },\n emptyText: {\n color: \"#6b7280\",\n fontSize: \"13px\",\n fontWeight: \"500\",\n },\n errorMessage: {\n color: \"#6b7280\",\n fontSize: \"12px\",\n lineHeight: \"1.4\",\n maxWidth: \"250px\",\n },\n errorPreview: {\n alignItems: \"center\",\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"8px\",\n justifyContent: \"center\",\n padding: \"16px\",\n textAlign: \"center\" as const,\n },\n errorTitle: {\n color: \"#ef4444\",\n fontSize: \"14px\",\n fontWeight: \"600\",\n },\n header: {\n alignItems: \"center\",\n display: \"flex\",\n justifyContent: \"space-between\",\n padding: \"0 4px\",\n },\n headerActions: {\n alignItems: \"center\",\n display: \"flex\",\n gap: \"8px\",\n },\n headerTitle: {\n color: \"#374151\",\n fontSize: \"12px\",\n fontWeight: \"600\",\n letterSpacing: \"0.05em\",\n textTransform: \"uppercase\" as const,\n },\n iconButton: {\n alignItems: \"center\",\n backgroundColor: \"transparent\",\n border: \"none\",\n borderRadius: \"4px\",\n color: \"#6b7280\",\n cursor: \"pointer\",\n display: \"flex\",\n height: \"24px\",\n justifyContent: \"center\",\n width: \"24px\",\n },\n loadingContainer: {\n alignItems: \"center\",\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"12px\",\n justifyContent: \"center\",\n padding: \"24px\",\n },\n loadingText: {\n color: \"#6b7280\",\n fontSize: \"13px\",\n },\n noPreview: {\n alignItems: \"center\",\n color: \"#9ca3af\",\n display: \"flex\",\n flexDirection: \"column\",\n fontSize: \"12px\",\n gap: \"8px\",\n },\n previewContainer: {\n alignItems: \"center\",\n backgroundColor: \"#f9fafb\",\n borderRadius: \"8px\",\n display: \"flex\",\n height: \"150px\",\n justifyContent: \"center\",\n overflow: \"hidden\",\n position: \"relative\",\n width: \"100%\",\n },\n previewContainerExpanded: {\n height: \"60vh\",\n maxHeight: \"500px\",\n },\n previewImage: {\n maxHeight: \"100%\",\n maxWidth: \"100%\",\n objectFit: \"contain\",\n },\n retakeButton: {\n alignItems: \"center\",\n backgroundColor: \"#3b82f6\",\n border: \"none\",\n borderRadius: \"6px\",\n color: \"#fff\",\n cursor: \"pointer\",\n display: \"flex\",\n fontSize: \"13px\",\n fontWeight: \"500\",\n gap: \"6px\",\n padding: \"8px 16px\",\n },\n retakeButtonOutline: {\n alignItems: \"center\",\n backgroundColor: \"transparent\",\n border: \"1px solid #e5e7eb\",\n borderRadius: \"6px\",\n color: \"#6b7280\",\n cursor: \"pointer\",\n display: \"flex\",\n fontSize: \"12px\",\n gap: \"6px\",\n padding: \"8px 12px\",\n },\n retakeButtonSmall: {\n alignItems: \"center\",\n backgroundColor: \"transparent\",\n border: \"1px solid #e5e7eb\",\n borderRadius: \"4px\",\n color: \"#6b7280\",\n cursor: \"pointer\",\n display: \"flex\",\n fontSize: \"11px\",\n gap: \"4px\",\n padding: \"4px 8px\",\n },\n sizeLabel: {\n color: \"#9ca3af\",\n fontSize: \"11px\",\n },\n tab: {\n alignItems: \"center\",\n backgroundColor: \"transparent\",\n border: \"none\",\n borderRadius: \"4px\",\n color: \"#6b7280\",\n cursor: \"pointer\",\n display: \"flex\",\n fontSize: \"12px\",\n gap: \"4px\",\n padding: \"2px 5px\",\n transition: \"all 0.15s ease\",\n },\n tabActive: {\n backgroundColor: \"#eff6ff\",\n color: \"#3b82f6\",\n fontWeight: \"500\",\n },\n tabContainer: {\n borderBottom: \"1px solid #e5e7eb\",\n display: \"flex\",\n gap: \"4px\",\n paddingBottom: \"8px\",\n },\n tabError: {\n color: \"#ef4444\",\n },\n tabSize: {\n color: \"#9ca3af\",\n fontSize: \"10px\",\n },\n};\n","/**\n * Highlight utilities for feedback target elements.\n *\n * Provides functions to visually highlight DOM elements during feedback selection.\n * Highlights are applied using CSS classes and dynamically generated styles.\n *\n * @module highlight\n * @since 1.0.0\n */\nimport type { HighlightColors, HighlightConfig } from \"./types\";\n\n/** CSS class applied to highlighted target elements */\nconst HIGHLIGHT_TARGET_CLASS = \"uifeedback-highlight-target\";\n\n/** CSS class applied to highlighted container elements */\nconst HIGHLIGHT_CONTAINER_CLASS = \"uifeedback-highlight-container\";\n\n/** ID of the dynamically injected style element */\nconst STYLE_ID = \"uifeedback-highlight-styles\";\n\n/**\n * Default highlight colors used when no custom colors are specified.\n *\n * @example\n * ```ts\n * // Override specific colors\n * const customColors = {\n * ...defaultHighlightColors,\n * targetColor: \"#ef4444\", // Red instead of blue\n * };\n * ```\n *\n * @since 1.0.0\n */\nexport const defaultHighlightColors: Required<HighlightColors> = {\n containerColor: \"#8b5cf6\",\n containerShadowOpacity: 0.1,\n targetColor: \"#3b82f6\",\n targetShadowOpacity: 0.25,\n};\n\n/**\n * Default CSS selectors used to identify container elements.\n *\n * These selectors are checked when traversing up the DOM tree to find\n * a suitable container element to highlight alongside the target.\n *\n * @example\n * ```ts\n * // Add custom selectors\n * const customSelectors = [\n * ...defaultContainerSelectors,\n * \"[data-component]\",\n * \".my-custom-container\",\n * ];\n * ```\n *\n * @since 1.0.0\n */\nexport const defaultContainerSelectors: string[] = [\n \".box\",\n \".card\",\n \".container\",\n \".dialog\",\n \".drawer\",\n \".modal\",\n \".panel\",\n \".section\",\n \".wrapper\",\n '[role=\"article\"]',\n '[role=\"dialog\"]',\n '[role=\"main\"]',\n '[role=\"region\"]',\n \"article\",\n \"aside\",\n \"footer\",\n \"header\",\n \"main\",\n \"nav\",\n \"section\",\n];\n\n/**\n * Generates CSS for highlight effects based on color configuration.\n *\n * @param colors - The highlight color configuration\n * @returns CSS string to be injected into the document\n * @internal\n */\nfunction generateHighlightCSS(colors: Required<HighlightColors>): string {\n const {\n containerColor,\n containerShadowOpacity,\n targetColor,\n targetShadowOpacity,\n } = colors;\n\n /**\n * Converts a hex color to rgba format.\n * @param hex - Hex color string (with or without #)\n * @param alpha - Alpha transparency value\n */\n const hexToRgba = (hex: string, alpha: number): string => {\n const result = /^#?([a-f\\d]{2})([a-f\\d]{2})([a-f\\d]{2})$/i.exec(hex);\n if (!result) return `rgba(0, 0, 0, ${alpha})`;\n return `rgba(${parseInt(result[1], 16)}, ${parseInt(result[2], 16)}, ${parseInt(result[3], 16)}, ${alpha})`;\n };\n\n return `\n.${HIGHLIGHT_TARGET_CLASS} {\n border-radius: 4px !important;\n box-shadow: 0 0 0 4px ${hexToRgba(targetColor, targetShadowOpacity)}, 0 4px 12px ${hexToRgba(targetColor, targetShadowOpacity * 0.6)} !important;\n outline: 2px dashed ${targetColor} !important;\n outline-offset: 2px !important;\n position: relative;\n top: 0;\n z-index: 9997;\n}\n\n/* SVG elements need special handling - don't apply styles that break their rendering */\nsvg.${HIGHLIGHT_TARGET_CLASS},\n.${HIGHLIGHT_TARGET_CLASS} > svg {\n border-radius: 0 !important;\n box-shadow: none !important;\n outline: none !important;\n position: static !important;\n z-index: auto !important;\n}\n\n.${HIGHLIGHT_CONTAINER_CLASS} {\n border-radius: 6px !important;\n box-shadow: 0 0 0 6px ${hexToRgba(containerColor, containerShadowOpacity)} !important;\n outline: 2px dashed ${hexToRgba(containerColor, 0.6)} !important;\n outline-offset: 4px !important;\n position: relative;\n z-index: 9996;\n}\n\n/* SVG elements in containers also need protection */\nsvg.${HIGHLIGHT_CONTAINER_CLASS},\n.${HIGHLIGHT_CONTAINER_CLASS} > svg {\n border-radius: 0 !important;\n box-shadow: none !important;\n outline: none !important;\n position: static !important;\n z-index: auto !important;\n}\n`;\n}\n\n/**\n * Injects or updates highlight styles in the document head.\n *\n * @param colors - The highlight color configuration\n * @internal\n */\nfunction injectStyles(colors: Required<HighlightColors>): void {\n if (typeof document === \"undefined\") return;\n\n // Remove existing styles if present\n const existingStyle = document.getElementById(STYLE_ID);\n if (existingStyle) {\n existingStyle.remove();\n }\n\n const style = document.createElement(\"style\");\n style.id = STYLE_ID;\n style.textContent = generateHighlightCSS(colors);\n document.head.appendChild(style);\n}\n\n/**\n * Finds the closest container parent element for a given target element.\n *\n * Traverses up the DOM tree looking for elements that match container selectors\n * or have multiple meaningful child elements.\n *\n * @param element - The target element to find a container for\n * @param config - Optional highlight configuration with custom selectors\n * @returns The found container element, or null if none found\n *\n * @example\n * ```ts\n * const target = document.querySelector(\".my-button\");\n * const container = findContainerParent(target, {\n * containerSelectors: [\".card\", \".panel\"],\n * minChildrenForContainer: 3,\n * });\n * ```\n *\n * @since 1.0.0\n */\nexport function findContainerParent(\n element: Element,\n config?: HighlightConfig,\n): Element | null {\n const containerSelectors =\n config?.containerSelectors ?? defaultContainerSelectors;\n const minChildren = config?.minChildrenForContainer ?? 2;\n\n let current = element.parentElement;\n let fallbackContainer: Element | null = null;\n\n while (current && current !== document.body) {\n // Check if element matches any container selector\n for (const selector of containerSelectors) {\n try {\n if (current.matches(selector)) {\n return current;\n }\n } catch {\n // Invalid selector, skip\n }\n }\n\n // Check if parent has multiple meaningful children (not just text nodes)\n const meaningfulChildren = Array.from(current.children).filter((child) => {\n const tag = child.tagName.toLowerCase();\n // Exclude script, style, and hidden elements\n if (tag === \"script\" || tag === \"style\" || tag === \"noscript\") {\n return false;\n }\n // Check if element is visible\n const style = window.getComputedStyle(child);\n if (style.display === \"none\" || style.visibility === \"hidden\") {\n return false;\n }\n return true;\n });\n\n // If this parent has enough children, it's likely a container\n if (meaningfulChildren.length >= minChildren && !fallbackContainer) {\n fallbackContainer = current;\n }\n\n // If parent has 3+ children, strongly consider it a container\n if (meaningfulChildren.length >= 3) {\n return current;\n }\n\n current = current.parentElement;\n }\n\n return fallbackContainer;\n}\n\n/**\n * Applies highlight styling to a target element.\n *\n * Injects the necessary CSS styles and adds the highlight class to the element.\n *\n * @param element - The element to highlight\n * @param colors - Optional custom highlight colors\n *\n * @example\n * ```ts\n * const target = document.querySelector(\".my-button\");\n * highlightTarget(target, { targetColor: \"#ef4444\" });\n * ```\n *\n * @since 1.0.0\n */\nexport function highlightTarget(\n element: Element,\n colors?: HighlightColors,\n): void {\n const mergedColors = { ...defaultHighlightColors, ...colors };\n injectStyles(mergedColors);\n element.classList.add(HIGHLIGHT_TARGET_CLASS);\n}\n\n/**\n * Applies highlight styling to a container element.\n *\n * Container highlights are visually distinct from target highlights,\n * typically with a larger outline offset and different color.\n *\n * @param element - The container element to highlight\n * @param colors - Optional custom highlight colors\n *\n * @example\n * ```ts\n * const container = document.querySelector(\".card\");\n * highlightContainer(container, { containerColor: \"#22c55e\" });\n * ```\n *\n * @since 1.0.0\n */\nexport function highlightContainer(\n element: Element,\n colors?: HighlightColors,\n): void {\n const mergedColors = { ...defaultHighlightColors, ...colors };\n injectStyles(mergedColors);\n element.classList.add(HIGHLIGHT_CONTAINER_CLASS);\n}\n\n/**\n * Removes all highlight styling from the document.\n *\n * Clears both target and container highlights from all elements.\n *\n * @example\n * ```ts\n * // Remove highlights when closing the context menu\n * clearHighlights();\n * ```\n *\n * @since 1.0.0\n */\nexport function clearHighlights(): void {\n if (typeof document === \"undefined\") return;\n\n document.querySelectorAll(`.${HIGHLIGHT_TARGET_CLASS}`).forEach((el) => {\n el.classList.remove(HIGHLIGHT_TARGET_CLASS);\n });\n\n document.querySelectorAll(`.${HIGHLIGHT_CONTAINER_CLASS}`).forEach((el) => {\n el.classList.remove(HIGHLIGHT_CONTAINER_CLASS);\n });\n}\n\n/**\n * Applies highlights to both a target element and its container parent.\n *\n * This is the main function for applying highlights during feedback selection.\n * It automatically finds the container parent and applies appropriate styling.\n *\n * @param targetElement - The element to highlight as the target\n * @param config - Optional highlight configuration\n * @returns Object containing the target and container elements\n *\n * @example\n * ```ts\n * const result = applyHighlights(clickedElement, {\n * enabled: true,\n * colors: { targetColor: \"#3b82f6\", containerColor: \"#8b5cf6\" },\n * containerSelectors: [\".card\", \".modal\"],\n * });\n *\n * console.log(result.target); // The highlighted target\n * console.log(result.container); // The highlighted container (or null)\n * ```\n *\n * @since 1.0.0\n */\nexport function applyHighlights(\n targetElement: Element,\n config?: HighlightConfig,\n): {\n container: Element | null;\n target: Element;\n} {\n // If highlights are disabled, don't apply anything\n if (config?.enabled === false) {\n return { container: null, target: targetElement };\n }\n\n clearHighlights();\n\n const colors = { ...defaultHighlightColors, ...config?.colors };\n\n highlightTarget(targetElement, colors);\n\n const container = findContainerParent(targetElement, config);\n if (container && container !== targetElement) {\n highlightContainer(container, colors);\n }\n\n return { container, target: targetElement };\n}\n","\"use client\";\n\nimport { createContext, useContext } from \"react\";\nimport type { AnyclickContextValue } from \"./types\";\n\n/**\n * React context for anyclick functionality.\n *\n * Provides access to anyclick state and methods throughout the component tree.\n * Use the {@link useAnyclick} hook for type-safe access.\n *\n * @example\n * ```tsx\n * // Using the context directly (advanced)\n * const context = useContext(AnyclickContext);\n * if (context) {\n * context.openMenu(element, { x: 100, y: 100 });\n * }\n * ```\n *\n * @see {@link useAnyclick} for the recommended way to access this context\n * @since 1.0.0\n */\nexport const AnyclickContext = createContext<AnyclickContextValue | null>(null);\n\n/**\n * @deprecated Use {@link AnyclickContext} instead. Will be removed in v2.0.0.\n * @see {@link AnyclickContext}\n */\nexport const FeedbackContext = AnyclickContext;\n\n/**\n * Hook to access anyclick context values and methods.\n *\n * Provides access to:\n * - `isEnabled` - Whether anyclick is currently enabled\n * - `isSubmitting` - Whether a submission is in progress\n * - `submitAnyclick` - Function to submit feedback programmatically\n * - `openMenu` - Function to open the context menu programmatically\n * - `closeMenu` - Function to close the context menu\n * - `theme` - The current merged theme configuration\n * - `scoped` - Whether the current provider is scoped\n * - `providerId` - The unique ID of the current provider\n *\n * @returns {AnyclickContextValue} The anyclick context value\n * @throws {Error} When used outside of an AnyclickProvider\n *\n * @example\n * ```tsx\n * function FeedbackButton() {\n * const { openMenu, isSubmitting, isEnabled } = useAnyclick();\n *\n * const handleClick = (event: React.MouseEvent) => {\n * if (isEnabled && !isSubmitting) {\n * openMenu(event.currentTarget, {\n * x: event.clientX,\n * y: event.clientY,\n * });\n * }\n * };\n *\n * return (\n * <button onClick={handleClick} disabled={!isEnabled || isSubmitting}>\n * Send Feedback\n * </button>\n * );\n * }\n * ```\n *\n * @since 1.0.0\n */\nexport function useAnyclick(): AnyclickContextValue {\n const context = useContext(AnyclickContext);\n if (!context) {\n throw new Error(\"useAnyclick must be used within an AnyclickProvider\");\n }\n return context;\n}\n\n/**\n * @deprecated Use {@link useAnyclick} instead. Will be removed in v2.0.0.\n * @see {@link useAnyclick}\n */\nexport function useFeedback(): AnyclickContextValue {\n const context = useContext(AnyclickContext);\n if (!context) {\n throw new Error(\"useFeedback must be used within a FeedbackProvider\");\n }\n return context;\n}\n","/**\n * Provider registry store for managing anyclick provider instances.\n *\n * Uses Zustand to maintain a global registry of all AnyclickProvider instances,\n * enabling features like nested providers, theme inheritance, and scoped contexts.\n *\n * @module store\n * @since 1.0.0\n */\n\"use client\";\n\nimport type { AnyclickMenuEvent } from \"@ewjdev/anyclick-core\";\nimport { create } from \"zustand\";\nimport type { AnyclickTheme } from \"./types\";\n\n/**\n * Registered provider instance in the provider registry.\n *\n * Each AnyclickProvider creates an instance of this type when mounted,\n * enabling the store to track and manage provider hierarchies.\n *\n * @since 1.0.0\n */\nexport interface ProviderInstance {\n /** Reference to the provider's container element (null if not scoped) */\n containerRef: React.RefObject<Element | null>;\n /** Depth in the provider hierarchy (0 = root) */\n depth: number;\n /** Whether this provider is disabled */\n disabled: boolean;\n /** Unique identifier for this provider instance */\n id: string;\n /** Handler to call when an event occurs in this provider's scope */\n onContextMenu?: (\n event: AnyclickMenuEvent,\n element: Element,\n ) => boolean | void;\n /** Parent provider ID (if nested) */\n parentId: string | null;\n /** Whether this provider is scoped to its container */\n scoped: boolean;\n /** The provider's theme configuration */\n theme: AnyclickTheme | null;\n}\n\n/**\n * Provider registry store state and actions.\n * @internal\n */\ninterface ProviderStore {\n /** Map of provider ID to provider instance */\n providers: Map<string, ProviderInstance>;\n\n /**\n * Finds all providers that contain a given element, sorted by depth (nearest first).\n * @param element - The DOM element to find providers for\n * @returns Array of matching providers, sorted by depth (deepest first)\n */\n findProvidersForElement: (element: Element) => ProviderInstance[];\n\n /**\n * Finds the nearest parent provider for a given container.\n * @param container - The container element to find a parent for\n * @param excludeId - Optional provider ID to exclude from search\n * @returns The nearest parent provider, or null if none found\n */\n findParentProvider: (\n container: Element | null,\n excludeId?: string,\n ) => ProviderInstance | null;\n\n /**\n * Gets the merged theme for a provider (includes inherited parent themes).\n * @param providerId - The ID of the provider to get the merged theme for\n * @returns The merged theme configuration\n */\n getMergedTheme: (providerId: string) => AnyclickTheme;\n\n /**\n * Checks if any ancestor provider has disabled anyclick.\n * @param providerId - The ID of the provider to check\n * @returns True if any ancestor is disabled\n */\n isDisabledByAncestor: (providerId: string) => boolean;\n\n /**\n * Checks if an element is inside any scoped provider's container.\n * Used to prevent the global provider from handling touch events.\n * @param element - The element to check\n * @returns True if element is inside any scoped provider\n */\n isElementInAnyScopedProvider: (element: Element) => boolean;\n\n /**\n * Checks if an element is inside a disabled scoped provider's container.\n * @param element - The element to check\n * @returns True if element is inside a disabled scope\n */\n isElementInDisabledScope: (element: Element) => boolean;\n\n /**\n * Registers a new provider in the store.\n * @param provider - The provider instance to register\n */\n registerProvider: (provider: ProviderInstance) => void;\n\n /**\n * Unregisters a provider from the store.\n * @param id - The ID of the provider to unregister\n */\n unregisterProvider: (id: string) => void;\n\n /**\n * Updates a provider's configuration.\n * @param id - The ID of the provider to update\n * @param updates - Partial updates to apply\n */\n updateProvider: (id: string, updates: Partial<ProviderInstance>) => void;\n}\n\n/** Counter for generating unique provider IDs */\nlet providerIdCounter = 0;\n\n/**\n * Generates a unique ID for a provider instance.\n *\n * @returns A unique provider ID string\n *\n * @example\n * ```ts\n * const id = generateProviderId();\n * // => \"anyclick-provider-1\"\n * ```\n *\n * @since 1.0.0\n */\nexport function generateProviderId(): string {\n return `anyclick-provider-${++providerIdCounter}`;\n}\n\n/**\n * Zustand store hook for managing provider instances.\n *\n * This store maintains a global registry of all AnyclickProvider instances,\n * enabling features like:\n * - Nested provider hierarchies\n * - Theme inheritance\n * - Scoped contexts\n * - Event routing\n *\n * @example\n * ```ts\n * // Get providers for an element\n * const providers = useProviderStore.getState().findProvidersForElement(element);\n *\n * // Get merged theme for a provider\n * const { getMergedTheme } = useProviderStore();\n * const theme = getMergedTheme(providerId);\n * ```\n *\n * @since 1.0.0\n */\nexport const useProviderStore = create<ProviderStore>((set, get) => ({\n providers: new Map(),\n\n findProvidersForElement: (element) => {\n const { providers } = get();\n const matching: ProviderInstance[] = [];\n\n for (const provider of providers.values()) {\n // Skip disabled providers\n if (provider.disabled) continue;\n\n const container = provider.containerRef.current;\n\n // For scoped providers, check if element is within container\n if (provider.scoped && container) {\n if (container.contains(element)) {\n matching.push(provider);\n }\n } else if (!provider.scoped) {\n // Non-scoped providers match all elements\n matching.push(provider);\n }\n }\n\n // Sort by depth (nearest/deepest first)\n return matching.sort((a, b) => b.depth - a.depth);\n },\n\n findParentProvider: (container, excludeId) => {\n const { providers } = get();\n\n if (!container) return null;\n\n let nearestParent: ProviderInstance | null = null;\n let nearestDepth = -1;\n\n for (const provider of providers.values()) {\n if (provider.id === excludeId) continue;\n\n const providerContainer = provider.containerRef.current;\n if (!providerContainer) continue;\n\n // Check if this provider's container contains our container\n if (providerContainer.contains(container)) {\n // This is a potential parent - check if it's the nearest one\n if (provider.depth > nearestDepth) {\n nearestParent = provider;\n nearestDepth = provider.depth;\n }\n }\n }\n\n return nearestParent;\n },\n\n getMergedTheme: (providerId) => {\n const { providers } = get();\n const provider = providers.get(providerId);\n\n if (!provider) {\n return {};\n }\n\n // Build ancestor chain\n const ancestors: ProviderInstance[] = [];\n let current: ProviderInstance | undefined = provider;\n\n while (current) {\n ancestors.unshift(current);\n current = current.parentId ? providers.get(current.parentId) : undefined;\n }\n\n // Merge themes from root to current (later themes override earlier)\n const mergedTheme: AnyclickTheme = {};\n\n for (const ancestor of ancestors) {\n if (ancestor.theme) {\n // Deep merge for nested objects\n Object.assign(mergedTheme, ancestor.theme);\n\n // Special handling for highlightConfig and screenshotConfig\n if (ancestor.theme.highlightConfig) {\n mergedTheme.highlightConfig = {\n ...mergedTheme.highlightConfig,\n ...ancestor.theme.highlightConfig,\n colors: {\n ...mergedTheme.highlightConfig?.colors,\n ...ancestor.theme.highlightConfig.colors,\n },\n };\n }\n\n if (ancestor.theme.screenshotConfig) {\n mergedTheme.screenshotConfig = {\n ...mergedTheme.screenshotConfig,\n ...ancestor.theme.screenshotConfig,\n };\n }\n }\n }\n\n return mergedTheme;\n },\n\n isDisabledByAncestor: (providerId) => {\n const { providers } = get();\n const provider = providers.get(providerId);\n\n if (!provider) return false;\n\n // Check this provider and all ancestors\n let current: ProviderInstance | undefined = provider;\n\n while (current) {\n if (current.disabled || current.theme?.disabled) {\n return true;\n }\n current = current.parentId ? providers.get(current.parentId) : undefined;\n }\n\n return false;\n },\n\n isElementInAnyScopedProvider: (element) => {\n const { providers } = get();\n\n // Check all scoped providers (enabled or disabled)\n for (const provider of providers.values()) {\n // Only check scoped providers\n if (!provider.scoped) continue;\n\n const container = provider.containerRef.current;\n if (!container) continue;\n\n // If element is inside this scoped provider's container\n if (container.contains(element)) {\n return true;\n }\n }\n\n return false;\n },\n\n isElementInDisabledScope: (element) => {\n const { providers } = get();\n\n // Check all scoped providers (including disabled ones)\n for (const provider of providers.values()) {\n // Only check scoped providers that are disabled\n if (!provider.scoped) continue;\n if (!provider.disabled && !provider.theme?.disabled) continue;\n\n const container = provider.containerRef.current;\n if (!container) continue;\n\n // If element is inside this disabled scoped provider's container\n if (container.contains(element)) {\n return true;\n }\n }\n\n return false;\n },\n\n registerProvider: (provider) => {\n set((state) => {\n const newProviders = new Map(state.providers);\n newProviders.set(provider.id, provider);\n return { providers: newProviders };\n });\n },\n\n unregisterProvider: (id) => {\n set((state) => {\n const newProviders = new Map(state.providers);\n newProviders.delete(id);\n return { providers: newProviders };\n });\n },\n\n updateProvider: (id, updates) => {\n set((state) => {\n const newProviders = new Map(state.providers);\n const existing = newProviders.get(id);\n if (existing) {\n newProviders.set(id, { ...existing, ...updates });\n }\n return { providers: newProviders };\n });\n },\n}));\n\n/**\n * Dispatches a context menu event to all matching providers.\n *\n * Routes the event through the provider hierarchy, calling handlers\n * from the nearest (deepest) provider first.\n *\n * @param event - The original mouse event\n * @param element - The target element\n *\n * @example\n * ```ts\n * document.addEventListener(\"contextmenu\", (event) => {\n * dispatchContextMenuEvent(event, event.target as Element);\n * });\n * ```\n *\n * @since 1.0.0\n */\nexport function dispatchContextMenuEvent(\n event: MouseEvent,\n element: Element,\n): void {\n const store = useProviderStore.getState();\n const providers = store.findProvidersForElement(element);\n\n // Convert MouseEvent to AnyclickMenuEvent\n const menuEvent: AnyclickMenuEvent = {\n clientX: event.clientX,\n clientY: event.clientY,\n isTouch: false,\n originalEvent: event,\n };\n\n // Call handlers from nearest to outermost\n for (const provider of providers) {\n // Check if disabled by theme or prop\n if (store.isDisabledByAncestor(provider.id)) {\n continue;\n }\n\n if (provider.onContextMenu) {\n provider.onContextMenu(menuEvent, element);\n // After the first handler processes, we don't need to call others\n break;\n }\n }\n}\n","\"use client\";\n\nimport { useEffect, useMemo, useRef } from \"react\";\nimport {\n type FunModeConfig,\n type PointerConfig,\n usePointer,\n} from \"@ewjdev/anyclick-pointer\";\nimport { useProviderStore } from \"./store\";\nimport type { AnyclickTheme, FunModeThemeConfig } from \"./types\";\n\nfunction isFunModeEnabled(\n theme?: AnyclickTheme | null,\n): theme is AnyclickTheme {\n if (!theme) return false;\n if (theme.funMode === undefined) return false;\n if (typeof theme.funMode === \"boolean\") return theme.funMode;\n return theme.funMode.enabled ?? true;\n}\n\nfunction buildFunConfig(\n theme: AnyclickTheme | null | undefined,\n container: Element,\n): FunModeConfig {\n const funTheme =\n typeof theme?.funMode === \"object\"\n ? (theme.funMode as FunModeThemeConfig)\n : {};\n const resolveTrackElement = (): HTMLElement => {\n // Some scoped containers use display: contents and report zero bounds.\n // Walk up to the first ancestor with a real box; fall back to body.\n let el: HTMLElement | null = container as HTMLElement | null;\n while (el) {\n const rect = el.getBoundingClientRect();\n if (rect.width > 0 && rect.height > 0) {\n return el;\n }\n el = el.parentElement;\n }\n return document.body;\n };\n\n const getTrackElement = () => resolveTrackElement();\n return {\n maxSpeed: funTheme.maxSpeed,\n acceleration: funTheme.acceleration,\n getTrackElement,\n getObstacles: () => {\n // Obstacles = siblings + children (lightweight bounding boxes)\n const trackElement = getTrackElement();\n const obstacles: DOMRect[] = [];\n const parent = trackElement.parentElement;\n if (parent) {\n Array.from(parent.children).forEach((sibling) => {\n if (sibling !== trackElement) {\n obstacles.push(sibling.getBoundingClientRect());\n }\n });\n }\n Array.from(trackElement.children).forEach((child) => {\n obstacles.push(child.getBoundingClientRect());\n });\n return obstacles;\n },\n };\n}\n\n/**\n * FunModeBridge watches Anyclick scoped providers and toggles the pointer\n * into fun mode (go-kart) when the cursor is within a provider with funMode enabled.\n * Requires a PointerProvider higher in the tree.\n */\nexport function FunModeBridge() {\n const { setConfig } = usePointer();\n const providerStore = useProviderStore();\n const activeProviderRef = useRef<string | null>(null);\n const cachedConfigs = useRef<Record<string, PointerConfig>>({});\n\n const findActiveFunProvider = useMemo(() => {\n return (el: Element | null) => {\n if (!el) return null;\n const providers = providerStore.findProvidersForElement(el);\n for (const provider of providers) {\n if (\n provider.scoped &&\n !provider.disabled &&\n isFunModeEnabled(provider.theme)\n ) {\n return provider;\n }\n }\n return null;\n };\n }, [providerStore]);\n\n useEffect(() => {\n const handleMove = (event: PointerEvent) => {\n const el = document.elementFromPoint(event.clientX, event.clientY);\n const provider = findActiveFunProvider(el as Element | null);\n\n if (!provider || !provider.containerRef.current) {\n if (activeProviderRef.current !== null) {\n activeProviderRef.current = null;\n setConfig({ mode: \"normal\" });\n }\n return;\n }\n\n if (activeProviderRef.current === provider.id) {\n return;\n }\n\n activeProviderRef.current = provider.id;\n if (!cachedConfigs.current[provider.id]) {\n cachedConfigs.current[provider.id] = {\n mode: \"fun\",\n funConfig: buildFunConfig(\n provider.theme,\n provider.containerRef.current,\n ),\n };\n }\n setConfig(cachedConfigs.current[provider.id]);\n };\n\n window.addEventListener(\"pointermove\", handleMove, { passive: true });\n return () => {\n window.removeEventListener(\"pointermove\", handleMove);\n };\n }, [findActiveFunProvider, setConfig]);\n\n return null;\n}\n\nexport default FunModeBridge;\n","\"use client\";\n\nimport React, { useCallback, useEffect, useState } from \"react\";\nimport type { IDEConfig } from \"../ide\";\nimport type { HighlightColors } from \"../types\";\nimport {\n type CompactModeConfig,\n InspectSimple,\n type PinnedPosition,\n} from \"./InspectSimple\";\n\n/**\n * Custom event name for triggering the inspect dialog\n */\nexport const INSPECT_DIALOG_EVENT = \"anyclick:inspect\";\n\n/**\n * Custom event detail for the inspect dialog\n */\nexport interface InspectDialogEventDetail {\n targetElement: Element;\n}\n\n/**\n * Dispatch an event to open the inspect dialog for an element\n */\nexport function openInspectDialog(targetElement: Element): void {\n if (typeof window === \"undefined\") return;\n\n const event = new CustomEvent<InspectDialogEventDetail>(\n INSPECT_DIALOG_EVENT,\n {\n detail: { targetElement },\n bubbles: true,\n cancelable: true,\n },\n );\n\n window.dispatchEvent(event);\n}\n\n/**\n * Props for InspectDialogManager\n */\nexport interface InspectDialogManagerProps {\n /** IDE configuration for \"Open in IDE\" feature */\n ideConfig?: Partial<IDEConfig>;\n /** Custom styles for the dialog */\n dialogStyle?: React.CSSProperties;\n /** Custom class name for the dialog */\n dialogClassName?: string;\n /** Custom highlight colors for the element highlight */\n highlightColors?: HighlightColors;\n /** Whether to show box model overlay (padding/margin visualization). Defaults to true. */\n showBoxModelOverlay?: boolean;\n /** Initial pinned position for the dialog. Defaults to \"floating\" (centered) */\n initialPinnedPosition?: PinnedPosition;\n /** Custom compact mode configuration. Partially override DEFAULT_COMPACT_CONFIG */\n compactConfig?: Partial<CompactModeConfig>;\n}\n\n/**\n * InspectDialogManager - A component that listens for inspect events and renders the dialog\n *\n * Place this component once in your app (e.g., alongside AnyclickProvider) to enable\n * the inspect dialog functionality from the chrome preset.\n *\n * @example\n * ```tsx\n * <AnyclickProvider adapter={adapter}>\n * <InspectDialogManager ideConfig={{ protocol: \"cursor\", basePath: \"/Users/me/project\" }} />\n * {children}\n * </AnyclickProvider>\n * ```\n */\nexport function InspectDialogManager({\n ideConfig,\n dialogStyle,\n dialogClassName,\n highlightColors,\n showBoxModelOverlay = true,\n initialPinnedPosition = \"floating\",\n compactConfig,\n}: InspectDialogManagerProps) {\n const [visible, setVisible] = useState(false);\n const [targetElement, setTargetElement] = useState<Element | null>(null);\n\n const handleClose = useCallback(() => {\n setVisible(false);\n setTargetElement(null);\n }, []);\n\n // Handle selecting a different element (e.g., from modified elements list)\n const handleSelectElement = useCallback((element: Element) => {\n setTargetElement(element);\n // Keep dialog visible, just switch the target\n }, []);\n\n useEffect(() => {\n const handleInspectEvent = (event: Event) => {\n const customEvent = event as CustomEvent<InspectDialogEventDetail>;\n if (customEvent.detail?.targetElement) {\n setTargetElement(customEvent.detail.targetElement);\n setVisible(true);\n }\n };\n\n window.addEventListener(INSPECT_DIALOG_EVENT, handleInspectEvent);\n\n return () => {\n window.removeEventListener(INSPECT_DIALOG_EVENT, handleInspectEvent);\n };\n }, []);\n\n return (\n <InspectSimple\n visible={visible}\n targetElement={targetElement}\n onClose={handleClose}\n onSelectElement={handleSelectElement}\n ideConfig={ideConfig}\n style={dialogStyle}\n className={dialogClassName}\n highlightColors={highlightColors}\n showBoxModelOverlay={showBoxModelOverlay}\n initialPinnedPosition={initialPinnedPosition}\n compactConfig={compactConfig}\n />\n );\n}\n\nexport default InspectDialogManager;\n","\"use client\";\n\nimport React, { useEffect, useMemo, useRef, useState } from \"react\";\nimport {\n type ElementInspectInfo,\n captureScreenshot,\n getElementInspectInfo,\n} from \"@ewjdev/anyclick-core\";\nimport { Camera, Code, Copy, ExternalLink, FileText, X } from \"lucide-react\";\nimport {\n clearHighlights,\n findContainerParent,\n highlightContainer,\n highlightTarget,\n} from \"../highlight\";\nimport {\n type IDEConfig,\n type SourceLocation,\n findSourceLocationInAncestors,\n formatSourceLocation,\n openInIDE,\n} from \"../ide\";\nimport type { HighlightColors } from \"../types\";\n\nexport type PinnedPosition = \"left\" | \"right\" | \"top\" | \"bottom\" | \"floating\";\n\nexport interface CompactModeConfig {\n scale: number;\n fonts: {\n base: number;\n title: number;\n tag: number;\n selector: number;\n section: number;\n badge: number;\n property: number;\n styleRow: number;\n button: number;\n };\n spacing: {\n headerPadding: string;\n identityPadding: string;\n sectionHeaderPadding: string;\n sectionContentPadding: string;\n footerPadding: string;\n selectorCodePadding: string;\n buttonPadding: string;\n buttonPrimaryPadding: string;\n buttonDangerPadding: string;\n badgePadding: string;\n propertyRowPadding: string;\n styleRowPadding: string;\n };\n gaps: {\n headerTitle: string;\n pinButtons: string;\n propertyRow: string;\n propertyValue: string;\n button: string;\n footer: string;\n };\n sizes: {\n dialogWidth: number;\n closeButton: number;\n copyButtonSmall: number;\n styleValueMaxWidth: number;\n categoryMarginBottom: number;\n styleCategoryHeaderMarginBottom: number;\n };\n letterSpacing: {\n sectionTitle: string;\n };\n}\n\nexport const DEFAULT_COMPACT_CONFIG: CompactModeConfig = {\n scale: 0.5,\n fonts: {\n base: 12,\n title: 14,\n tag: 12,\n selector: 11,\n section: 12,\n badge: 11,\n property: 12,\n styleRow: 11,\n button: 12,\n },\n spacing: {\n headerPadding: \"8px 12px\",\n identityPadding: \"8px 12px\",\n sectionHeaderPadding: \"6px 12px\",\n sectionContentPadding: \"8px 12px\",\n footerPadding: \"8px 12px\",\n selectorCodePadding: \"6px 10px\",\n buttonPadding: \"6px 10px\",\n buttonPrimaryPadding: \"6px 12px\",\n buttonDangerPadding: \"6px 8px\",\n badgePadding: \"2px 6px\",\n propertyRowPadding: \"4px 6px\",\n styleRowPadding: \"4px 6px\",\n },\n gaps: {\n headerTitle: \"8px\",\n pinButtons: \"4px\",\n propertyRow: \"4px\",\n propertyValue: \"6px\",\n button: \"6px\",\n footer: \"8px\",\n },\n sizes: {\n dialogWidth: 420,\n closeButton: 18,\n copyButtonSmall: 16,\n styleValueMaxWidth: 240,\n categoryMarginBottom: 8,\n styleCategoryHeaderMarginBottom: 6,\n },\n letterSpacing: {\n sectionTitle: \"0.04em\",\n },\n};\n\nexport interface InspectSimpleProps {\n visible: boolean;\n targetElement: Element | null;\n onClose: () => void;\n onSelectElement?: (element: Element) => void;\n ideConfig?: Partial<IDEConfig>;\n style?: React.CSSProperties;\n className?: string;\n highlightColors?: HighlightColors;\n showBoxModelOverlay?: boolean;\n initialPinnedPosition?: PinnedPosition;\n compactConfig?: Partial<CompactModeConfig>;\n}\n\nfunction copy(text: string): Promise<boolean> {\n if (!text) return Promise.resolve(false);\n if (typeof navigator === \"undefined\" || !navigator.clipboard) {\n return Promise.resolve(false);\n }\n return navigator.clipboard\n .writeText(text)\n .then(() => true)\n .catch(() => false);\n}\n\nfunction downloadDataUrl(dataUrl: string, filename: string) {\n const link = document.createElement(\"a\");\n link.href = dataUrl;\n link.download = filename;\n link.click();\n}\n\nfunction useIsMobile() {\n const [isMobile, setIsMobile] = useState(false);\n\n useEffect(() => {\n const mq = window.matchMedia(\"(max-width: 640px)\");\n setIsMobile(mq.matches);\n const handler = (e: MediaQueryListEvent) => setIsMobile(e.matches);\n mq.addEventListener(\"change\", handler);\n return () => mq.removeEventListener(\"change\", handler);\n }, []);\n\n return isMobile;\n}\n\nexport function InspectSimple({\n visible,\n targetElement,\n onClose,\n ideConfig,\n style,\n className,\n highlightColors,\n}: InspectSimpleProps) {\n const [info, setInfo] = useState<ElementInspectInfo | null>(null);\n const [sourceLocation, setSourceLocation] = useState<SourceLocation | null>(\n null,\n );\n const [status, setStatus] = useState<string | null>(null);\n const [saving, setSaving] = useState(false);\n const dialogRef = useRef<HTMLDivElement>(null);\n const isMobile = useIsMobile();\n\n // Auto-dismiss status message after 5 seconds\n useEffect(() => {\n if (!status) return;\n const timer = setTimeout(() => setStatus(null), 5000);\n return () => clearTimeout(timer);\n }, [status]);\n\n useEffect(() => {\n if (!visible || !targetElement) return;\n\n try {\n clearHighlights();\n highlightTarget(targetElement, highlightColors);\n const container = findContainerParent(targetElement);\n if (container) highlightContainer(container, highlightColors);\n } catch {\n // ignore highlight errors\n }\n\n const nextInfo = getElementInspectInfo(targetElement);\n setInfo(nextInfo);\n setSourceLocation(\n findSourceLocationInAncestors(targetElement) ??\n nextInfo.sourceLocation ??\n null,\n );\n\n return () => {\n clearHighlights();\n };\n }, [visible, targetElement, highlightColors]);\n\n // Handle outside click\n useEffect(() => {\n if (!visible) return;\n\n const handleClickOutside = (e: MouseEvent) => {\n if (dialogRef.current && !dialogRef.current.contains(e.target as Node)) {\n onClose();\n }\n };\n\n // Delay adding the listener to avoid immediate close\n const timeoutId = setTimeout(() => {\n document.addEventListener(\"mousedown\", handleClickOutside);\n }, 100);\n\n return () => {\n clearTimeout(timeoutId);\n document.removeEventListener(\"mousedown\", handleClickOutside);\n };\n }, [visible, onClose]);\n\n const identityLabel = useMemo(() => {\n if (!info) return \"Select an element\";\n const classes = info.classNames[0] ? `.${info.classNames[0]}` : \"\";\n const id = info.id ? `#${info.id}` : \"\";\n return `${info.tagName}${id}${classes}`;\n }, [info]);\n\n const handleCopySelector = async () => {\n if (!info?.selector) {\n setStatus(\"No selector available\");\n return;\n }\n const ok = await copy(info.selector);\n setStatus(\n ok ? \"✓ Selector copied to clipboard\" : \"Failed to copy selector\",\n );\n };\n\n const handleCopyText = async () => {\n if (!info?.innerText) {\n setStatus(\"No text content to copy\");\n return;\n }\n const ok = await copy(info.innerText);\n setStatus(\n ok ? \"✓ Text content copied to clipboard\" : \"Failed to copy text\",\n );\n };\n\n const handleSaveScreenshot = async () => {\n if (!targetElement) return;\n setSaving(true);\n setStatus(\"Capturing screenshot…\");\n const result = await captureScreenshot(targetElement, null, \"element\");\n setSaving(false);\n if (result.capture?.dataUrl) {\n downloadDataUrl(result.capture.dataUrl, \"anyclick-inspect.png\");\n setStatus(\"✓ Screenshot saved to downloads\");\n } else {\n setStatus(result.error?.message || \"Screenshot capture failed\");\n }\n };\n\n const handleCopyOuterHTML = async () => {\n if (!info?.outerHTML) {\n setStatus(\"No HTML to copy\");\n return;\n }\n const ok = await copy(info.outerHTML);\n setStatus(ok ? \"✓ HTML markup copied to clipboard\" : \"Failed to copy HTML\");\n };\n\n const handleOpenIDE = () => {\n if (!sourceLocation) return;\n openInIDE(sourceLocation, ideConfig);\n };\n\n if (!visible || !targetElement) return null;\n\n const dialogStyles: React.CSSProperties = isMobile\n ? {\n position: \"fixed\",\n left: 0,\n right: 0,\n bottom: 0,\n zIndex: 9999,\n width: \"100%\",\n maxWidth: \"100%\",\n background: \"#0f172a\",\n color: \"#e2e8f0\",\n borderTop: \"1px solid #1e293b\",\n borderRadius: \"16px 16px 0 0\",\n boxShadow: \"0 -8px 32px rgba(0,0,0,0.4)\",\n fontFamily: \"Inter, system-ui, -apple-system, sans-serif\",\n fontSize: 13,\n overflow: \"hidden\",\n ...style,\n }\n : {\n position: \"fixed\",\n right: 16,\n bottom: 16,\n zIndex: 9999,\n width: 320,\n maxWidth: \"90vw\",\n background: \"#0f172a\",\n color: \"#e2e8f0\",\n border: \"1px solid #1e293b\",\n borderRadius: 12,\n boxShadow: \"0 18px 48px rgba(0,0,0,0.45)\",\n fontFamily: \"Inter, system-ui, -apple-system, sans-serif\",\n fontSize: 13,\n overflow: \"hidden\",\n ...style,\n };\n\n return (\n <>\n {/* Backdrop overlay */}\n <div\n style={{\n position: \"fixed\",\n inset: 0,\n zIndex: 9998,\n background: isMobile ? \"rgba(0,0,0,0.5)\" : \"transparent\",\n pointerEvents: isMobile ? \"auto\" : \"none\",\n }}\n onClick={onClose}\n onKeyDown={(e) => e.key === \"Escape\" && onClose()}\n role=\"presentation\"\n />\n\n <div\n ref={dialogRef}\n className={`anyclick-tiny-inspect ${className ?? \"\"}`}\n style={dialogStyles}\n >\n {/* Header with close button */}\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"space-between\",\n padding: isMobile ? \"12px 16px\" : \"8px 10px\",\n background: \"#0b1220\",\n borderBottom: \"1px solid #1e293b\",\n }}\n >\n {/* Mobile drawer handle */}\n {isMobile && (\n <div\n style={{\n position: \"absolute\",\n top: 6,\n left: \"50%\",\n transform: \"translateX(-50%)\",\n width: 36,\n height: 4,\n borderRadius: 2,\n background: \"#475569\",\n }}\n />\n )}\n\n <div style={{ display: \"flex\", alignItems: \"center\", gap: 6 }}>\n <span\n style={{\n padding: \"3px 8px\",\n borderRadius: 6,\n background: \"#1e293b\",\n color: \"#e2e8f0\",\n fontSize: 12,\n fontWeight: 600,\n fontFamily: \"monospace\",\n }}\n >\n {identityLabel}\n </span>\n {sourceLocation && (\n <button\n type=\"button\"\n onClick={handleOpenIDE}\n title={formatSourceLocation(sourceLocation)}\n style={iconBtnStyle}\n >\n <ExternalLink size={14} />\n </button>\n )}\n </div>\n\n <button\n type=\"button\"\n onClick={onClose}\n style={iconBtnStyle}\n aria-label=\"Close inspector\"\n >\n <X size={16} />\n </button>\n </div>\n\n {/* Compact content */}\n <div\n style={{\n padding: isMobile ? \"12px 16px 20px\" : \"10px\",\n display: \"flex\",\n flexDirection: \"column\",\n gap: 8,\n }}\n >\n {/* Selector row */}\n {info?.selector && (\n <code\n style={{\n fontSize: 11,\n color: \"#94a3b8\",\n background: \"#111827\",\n padding: \"6px 8px\",\n borderRadius: 6,\n wordBreak: \"break-all\",\n display: \"block\",\n }}\n >\n {info.selector}\n </code>\n )}\n\n {/* Status feedback message - above buttons */}\n {status && (\n <div\n style={{\n fontSize: 12,\n color: status.startsWith(\"✓\")\n ? \"#4ade80\"\n : status.toLowerCase().includes(\"failed\") ||\n status.toLowerCase().includes(\"error\")\n ? \"#f87171\"\n : \"#94a3b8\",\n padding: \"4px 0\",\n fontWeight: 500,\n }}\n >\n {status}\n </div>\n )}\n\n {/* Actions - icon-only row */}\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n gap: 6,\n }}\n >\n <button\n type=\"button\"\n onClick={handleCopySelector}\n style={iconActionStyle}\n title=\"Copy CSS selector\"\n aria-label=\"Copy CSS selector\"\n >\n <Copy size={15} />\n </button>\n <button\n type=\"button\"\n onClick={handleCopyText}\n style={iconActionStyle}\n title=\"Copy text content\"\n aria-label=\"Copy text content\"\n >\n <FileText size={15} />\n </button>\n <button\n type=\"button\"\n onClick={handleCopyOuterHTML}\n style={iconActionStyle}\n title=\"Copy HTML markup\"\n aria-label=\"Copy HTML markup\"\n >\n <Code size={15} />\n </button>\n <button\n type=\"button\"\n onClick={handleSaveScreenshot}\n style={{\n ...iconActionStyle,\n ...(saving ? { opacity: 0.5, cursor: \"wait\" } : {}),\n }}\n disabled={saving}\n title=\"Save screenshot\"\n aria-label=\"Save screenshot\"\n >\n <Camera size={15} />\n </button>\n </div>\n </div>\n </div>\n </>\n );\n}\n\nconst iconBtnStyle: React.CSSProperties = {\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n width: 28,\n height: 28,\n borderRadius: 6,\n border: \"1px solid #1e293b\",\n background: \"#0b1220\",\n color: \"#94a3b8\",\n cursor: \"pointer\",\n padding: 0,\n};\n\nconst iconActionStyle: React.CSSProperties = {\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n width: 32,\n height: 32,\n borderRadius: 8,\n border: \"1px solid #1e293b\",\n background: \"#0b1220\",\n color: \"#94a3b8\",\n cursor: \"pointer\",\n padding: 0,\n transition: \"background 0.15s, color 0.15s, border-color 0.15s\",\n};\n","/**\n * IDE protocol handler integration for opening files directly in IDEs.\n * Supports VS Code, Cursor, WebStorm, and other IDEs that support URL protocols.\n */\n\n/**\n * Supported IDE protocol types\n */\nexport type IDEProtocol =\n | \"vscode\"\n | \"cursor\"\n | \"webstorm\"\n | \"intellij\"\n | \"phpstorm\"\n | \"sublime\"\n | \"atom\"\n | \"custom\";\n\n/**\n * Configuration for IDE integration\n */\nexport interface IDEConfig {\n /** The IDE protocol to use */\n protocol: IDEProtocol;\n /** Custom protocol string (only used when protocol is 'custom') */\n customProtocol?: string;\n /** Base path to prepend to file paths (for mapping web paths to file system) */\n basePath?: string;\n /** Path transformations to apply (regex find/replace) */\n pathTransforms?: Array<{\n find: string | RegExp;\n replace: string;\n }>;\n}\n\n/**\n * Source location information\n */\nexport interface SourceLocation {\n /** File path */\n file: string;\n /** Line number (1-indexed) */\n line: number;\n /** Column number (1-indexed, optional) */\n column?: number;\n}\n\n/**\n * Default IDE configuration\n */\nconst DEFAULT_IDE_CONFIG: IDEConfig = {\n protocol: \"cursor\",\n};\n\n/**\n * Protocol URL templates for different IDEs\n * {file} = file path, {line} = line number, {column} = column number\n */\nconst PROTOCOL_TEMPLATES: Record<IDEProtocol, string> = {\n vscode: \"vscode://file/{file}:{line}:{column}\",\n cursor: \"cursor://file/{file}:{line}:{column}\",\n webstorm: \"webstorm://open?file={file}&line={line}&column={column}\",\n intellij: \"idea://open?file={file}&line={line}&column={column}\",\n phpstorm: \"phpstorm://open?file={file}&line={line}&column={column}\",\n sublime: \"subl://open?url=file://{file}&line={line}&column={column}\",\n atom: \"atom://open?url=file://{file}&line={line}&column={column}\",\n custom: \"\", // Placeholder, will use customProtocol\n};\n\n/**\n * Build the URL for opening a file in an IDE\n */\nexport function buildIDEUrl(\n location: SourceLocation,\n config: Partial<IDEConfig> = {},\n): string {\n const mergedConfig: IDEConfig = { ...DEFAULT_IDE_CONFIG, ...config };\n let filePath = location.file;\n\n // Apply base path if provided\n if (mergedConfig.basePath) {\n // Remove leading slash from file path if base path doesn't end with one\n if (!mergedConfig.basePath.endsWith(\"/\") && filePath.startsWith(\"/\")) {\n filePath = filePath.slice(1);\n }\n filePath = `${mergedConfig.basePath}/${filePath}`.replace(/\\/+/g, \"/\");\n }\n\n // Apply path transformations\n if (mergedConfig.pathTransforms) {\n for (const transform of mergedConfig.pathTransforms) {\n filePath = filePath.replace(transform.find, transform.replace);\n }\n }\n\n // Get the template\n let template =\n mergedConfig.protocol === \"custom\"\n ? mergedConfig.customProtocol || \"\"\n : PROTOCOL_TEMPLATES[mergedConfig.protocol];\n\n // Replace placeholders\n const url = template\n .replace(\"{file}\", encodeURIComponent(filePath))\n .replace(\"{line}\", String(location.line))\n .replace(\"{column}\", String(location.column || 1));\n\n return url;\n}\n\n/**\n * Open a file in the IDE using the protocol handler\n */\nexport function openInIDE(\n location: SourceLocation,\n config: Partial<IDEConfig> = {},\n): boolean {\n if (typeof window === \"undefined\") {\n console.warn(\"openInIDE: Cannot open IDE in non-browser environment\");\n return false;\n }\n\n try {\n const url = buildIDEUrl(location, config);\n\n // Use window.open with a short timeout to avoid popup blockers\n // The protocol handler should intercept this\n window.location.href = url;\n\n return true;\n } catch (error) {\n console.error(\"Failed to open file in IDE:\", error);\n return false;\n }\n}\n\n/**\n * Check if the current environment likely supports IDE protocol handlers\n * Note: This is a heuristic and may not be 100% accurate\n */\nexport function isIDEProtocolSupported(): boolean {\n if (typeof window === \"undefined\") return false;\n\n // Protocol handlers are generally supported on desktop browsers\n // but not on mobile or in some restricted environments\n const userAgent = navigator.userAgent.toLowerCase();\n\n // Mobile browsers generally don't support custom protocol handlers well\n if (/mobile|android|iphone|ipad/i.test(userAgent)) {\n return false;\n }\n\n return true;\n}\n\n/**\n * Detect the most likely IDE based on environment\n * This is a heuristic based on common development setups\n */\nexport function detectPreferredIDE(): IDEProtocol {\n if (typeof window === \"undefined\") return \"vscode\";\n\n // Check for Cursor-specific indicators\n // Cursor sets some specific user agent or environment hints\n const userAgent = navigator.userAgent;\n\n // For now, default to Cursor since this is the anyclick project\n // In production, this could be enhanced with better detection\n return \"cursor\";\n}\n\n/**\n * Try to extract source location from element data attributes\n */\nexport function getSourceLocationFromElement(\n element: Element,\n): SourceLocation | null {\n const htmlElement = element as HTMLElement;\n const dataset = htmlElement.dataset || {};\n\n // Try different data attribute conventions\n const file =\n dataset.sourceFile ||\n dataset[\"source-file\"] ||\n element.getAttribute(\"data-source-file\") ||\n dataset.file ||\n element.getAttribute(\"data-file\");\n\n const line =\n dataset.sourceLine ||\n dataset[\"source-line\"] ||\n element.getAttribute(\"data-source-line\") ||\n dataset.line ||\n element.getAttribute(\"data-line\");\n\n if (!file || !line) {\n return null;\n }\n\n const column =\n dataset.sourceColumn ||\n dataset[\"source-column\"] ||\n element.getAttribute(\"data-source-column\") ||\n dataset.column ||\n element.getAttribute(\"data-column\");\n\n return {\n file,\n line: parseInt(line, 10),\n column: column ? parseInt(column, 10) : undefined,\n };\n}\n\n/**\n * Walk up the DOM tree to find source location from any ancestor\n */\nexport function findSourceLocationInAncestors(\n element: Element,\n maxDepth: number = 10,\n): SourceLocation | null {\n let current: Element | null = element;\n let depth = 0;\n\n while (current && depth < maxDepth) {\n const location = getSourceLocationFromElement(current);\n if (location) {\n return location;\n }\n current = current.parentElement;\n depth++;\n }\n\n return null;\n}\n\n/**\n * Create a configured IDE opener function\n */\nexport function createIDEOpener(\n config: Partial<IDEConfig> = {},\n): (location: SourceLocation) => boolean {\n return (location: SourceLocation) => openInIDE(location, config);\n}\n\n/**\n * Format a source location as a readable string\n */\nexport function formatSourceLocation(location: SourceLocation): string {\n const { file, line, column } = location;\n if (column !== undefined) {\n return `${file}:${line}:${column}`;\n }\n return `${file}:${line}`;\n}\n","/**\n * Role-based preset configurations for common user types.\n *\n * Provides pre-configured menu items, screenshot settings, and themes\n * tailored for specific roles like QA, PM, Designer, and Developer.\n *\n * @module presets\n * @since 1.2.0\n *\n * @example\n * ```tsx\n * import { AnyclickProvider, createPresetMenu } from \"@ewjdev/anyclick-react\";\n *\n * const qaPreset = createPresetMenu(\"qa\");\n *\n * function App() {\n * return (\n * <AnyclickProvider\n * adapter={adapter}\n * menuItems={qaPreset.menuItems}\n * screenshotConfig={qaPreset.screenshotConfig}\n * theme={qaPreset.theme}\n * >\n * <YourApp />\n * </AnyclickProvider>\n * );\n * }\n * ```\n */\nimport { CSSProperties } from \"react\";\nimport type { ScreenshotConfig } from \"@ewjdev/anyclick-core\";\nimport { openInspectDialog } from \"./InspectDialog/InspectDialogManager\";\nimport type { AnyclickTheme, ContextMenuItem, HighlightConfig } from \"./types\";\n\n/**\n * Available preset role identifiers.\n *\n * - `qa` - QA/Testing focused menu with bug reporting and repro steps\n * - `pm` - Product Manager focused menu with feature ideas and impact sizing\n * - `designer` - Designer focused menu with visual QA and accessibility\n * - `developer` - Developer focused menu with diagnostics and debugging\n * - `chrome` - Chrome-like context menu with browser actions\n *\n * @since 1.2.0\n */\nexport type PresetRole = \"chrome\" | \"designer\" | \"developer\" | \"pm\" | \"qa\";\n\n/**\n * Complete preset configuration for a role.\n *\n * Contains all the settings needed to configure an AnyclickProvider\n * for a specific user role.\n *\n * @since 1.2.0\n */\nexport interface PresetConfig {\n /** Human-readable description of the preset */\n description: string;\n /** Optional highlight configuration */\n highlightConfig?: HighlightConfig;\n /** Human-readable label for the preset */\n label: string;\n /** Context menu items for this preset */\n menuItems: ContextMenuItem[];\n /** Additional metadata to include with submissions */\n metadata?: Record<string, unknown>;\n /** The preset role identifier */\n role: PresetRole;\n /** Screenshot capture configuration */\n screenshotConfig?: Partial<ScreenshotConfig>;\n /** Theme configuration including styles and highlighting */\n theme?: AnyclickTheme;\n}\n\n/**\n * Options for customizing preset menu creation.\n *\n * @since 1.2.0\n */\nexport interface CreatePresetMenuOptions {\n /**\n * Whether to include coming-soon items in the menu.\n * Coming-soon items are shown but disabled.\n * @default true\n */\n includeComingSoon?: boolean;\n /**\n * Optional overrides for menu items, screenshot config, metadata, or theme.\n * Useful when you want to tweak a preset without rebuilding it manually.\n *\n * @example\n * ```ts\n * const qaPreset = createPresetMenu(\"qa\", {\n * overrides: {\n * screenshotConfig: { quality: 0.9 },\n * theme: { highlightConfig: { colors: { targetColor: \"#ef4444\" } } },\n * },\n * });\n * ```\n */\n overrides?: Partial<Omit<PresetConfig, \"description\" | \"label\" | \"role\">>;\n}\n\n/**\n * Default preset configurations for each role.\n *\n * These are the base configurations that {@link createPresetMenu} uses.\n * You can use them directly if you don't need any customization.\n *\n * @since 1.2.0\n */\nconst presetDefaults: Record<PresetRole, PresetConfig> = {\n chrome: {\n description:\n \"Chrome-like context menu with core browser actions and native styling.\",\n label: \"Chrome\",\n menuItems: [\n {\n label: \"Reload page\",\n onClick: ({ closeMenu }) => {\n closeMenu();\n if (typeof window !== \"undefined\") {\n window.location.reload();\n }\n return false;\n },\n showComment: false,\n type: \"reload_page\",\n },\n {\n label: \"Print…\",\n onClick: ({ closeMenu }) => {\n closeMenu();\n if (typeof window !== \"undefined\") {\n window.print();\n }\n return false;\n },\n showComment: false,\n type: \"print_page\",\n },\n {\n label: 'Search \"Google\"',\n onClick: ({ closeMenu }) => {\n closeMenu();\n if (typeof window === \"undefined\") return false;\n const selection = window.getSelection()?.toString().trim();\n const query = selection && selection.length > 0 ? selection : \"\";\n const url = query\n ? `https://www.google.com/search?q=${encodeURIComponent(query)}`\n : \"https://www.google.com\";\n window.open(url, \"_blank\", \"noopener,noreferrer\");\n return false;\n },\n showComment: false,\n type: \"search_google\",\n },\n {\n label: \"Share…\",\n onClick: async ({ closeMenu }) => {\n closeMenu();\n if (typeof window === \"undefined\") return false;\n const shareData = {\n text: document.title,\n title: document.title,\n url: window.location.href,\n };\n try {\n if (navigator.share) {\n await navigator.share(shareData);\n } else if (navigator.clipboard?.writeText) {\n await navigator.clipboard.writeText(window.location.href);\n }\n } catch {\n // Silently ignore share/clipboard errors to match native feel\n }\n return false;\n },\n showComment: false,\n type: \"share_page\",\n },\n {\n label: \"Inspect\",\n onClick: ({ closeMenu, targetElement }) => {\n closeMenu();\n if (targetElement) {\n openInspectDialog(targetElement);\n }\n return false;\n },\n showComment: false,\n type: \"inspect\",\n },\n ],\n role: \"chrome\",\n screenshotConfig: {\n enabled: false,\n },\n theme: {\n highlightConfig: {\n enabled: false,\n },\n menuStyle: {\n \"--anyclick-menu-accent\": \"#8ab4f8\",\n \"--anyclick-menu-accent-text\": \"#0b1117\",\n \"--anyclick-menu-bg\": \"#202124\",\n \"--anyclick-menu-border\": \"#3c4043\",\n \"--anyclick-menu-cancel-bg\": \"#2f3135\",\n \"--anyclick-menu-cancel-text\": \"#9aa0a6\",\n \"--anyclick-menu-hover\": \"#2f3135\",\n \"--anyclick-menu-input-bg\": \"#2f3135\",\n \"--anyclick-menu-input-border\": \"#3c4043\",\n \"--anyclick-menu-text\": \"#e8eaed\",\n \"--anyclick-menu-text-muted\": \"#9aa0a6\",\n backgroundColor: \"#202124\",\n border: \"1px solid #3c4043\",\n borderRadius: 6,\n boxShadow: \"0 8px 18px rgba(0, 0, 0, 0.4)\",\n color: \"#e8eaed\",\n fontFamily:\n 'Roboto, \"Segoe UI\", -apple-system, BlinkMacSystemFont, sans-serif',\n fontSize: 14,\n letterSpacing: 0,\n minWidth: 240,\n padding: 0,\n } as CSSProperties,\n },\n },\n designer: {\n description: \"Visual QA with contrast and motion cues.\",\n label: \"Designer\",\n menuItems: [\n { label: \"Visual bug\", showComment: true, type: \"visual_bug\" },\n { label: \"Accessibility\", showComment: true, type: \"accessibility\" },\n { label: \"Copy / tone\", showComment: true, type: \"copy_tone\" },\n {\n badge: { label: \"Coming soon\", tone: \"info\" },\n label: \"Motion glitch\",\n showComment: true,\n status: \"comingSoon\",\n type: \"motion_glitch\",\n },\n ],\n metadata: {\n capture: {\n colorContrast: true,\n prefersReducedMotion: true,\n },\n },\n role: \"designer\",\n screenshotConfig: {\n enabled: true,\n padding: 32,\n quality: 0.75,\n showPreview: true,\n },\n theme: {\n highlightConfig: {\n colors: {\n containerColor: \"#22d3ee\",\n targetColor: \"#a855f7\",\n },\n },\n },\n },\n developer: {\n description: \"Debug-ready menu with diagnostics placeholders.\",\n label: \"Developer\",\n menuItems: [\n { label: \"Bug\", showComment: true, type: \"bug\" },\n { label: \"Refactor request\", showComment: true, type: \"refactor\" },\n {\n children: [\n {\n badge: { label: \"Coming soon\", tone: \"info\" },\n label: \"Console snapshot\",\n showComment: false,\n status: \"comingSoon\",\n type: \"console_snapshot\",\n },\n {\n badge: { label: \"Coming soon\", tone: \"info\" },\n label: \"Network trace\",\n showComment: false,\n status: \"comingSoon\",\n type: \"network_trace\",\n },\n {\n label: \"Copy CSS selector\",\n showComment: false,\n type: \"copy_selector\",\n },\n ],\n label: \"Diagnostics\",\n type: \"diagnostics\",\n },\n ],\n metadata: {\n capture: {\n console: \"errors\",\n network: \"errors\",\n reduxState: \"opt-in\",\n },\n },\n role: \"developer\",\n screenshotConfig: {\n enabled: true,\n padding: 20,\n quality: 0.7,\n showPreview: true,\n },\n theme: {\n highlightConfig: {\n colors: {\n containerColor: \"#0ea5e9\",\n targetColor: \"#22c55e\",\n },\n },\n },\n },\n pm: {\n description: \"Idea-first menu with quick impact sizing.\",\n label: \"PM\",\n menuItems: [\n { label: \"Feature idea\", showComment: true, type: \"feature\" },\n { label: \"UX papercut\", showComment: true, type: \"ux_papercut\" },\n { label: \"Customer quote\", showComment: true, type: \"success_story\" },\n {\n badge: { label: \"Coming soon\", tone: \"neutral\" },\n label: \"Impact / priority\",\n showComment: true,\n status: \"comingSoon\",\n type: \"impact_sizing\",\n },\n ],\n metadata: {\n capture: {\n audience: \"pm\",\n sentiment: true,\n },\n },\n role: \"pm\",\n screenshotConfig: {\n enabled: true,\n padding: 16,\n quality: 0.65,\n showPreview: true,\n },\n },\n qa: {\n description: \"Defect-first menu tuned for repros and logs.\",\n label: \"QA\",\n menuItems: [\n { label: \"Bug / defect\", showComment: true, type: \"bug\" },\n { label: \"UX papercut\", showComment: true, type: \"ux_papercut\" },\n { label: \"Repro steps\", showComment: true, type: \"repro_steps\" },\n {\n badge: { label: \"Coming soon\", tone: \"info\" },\n label: \"Performance trace\",\n showComment: true,\n status: \"comingSoon\",\n type: \"perf_trace\",\n },\n {\n badge: { label: \"Coming soon\", tone: \"info\" },\n label: \"Video capture\",\n showComment: false,\n status: \"comingSoon\",\n type: \"video_capture\",\n },\n ],\n metadata: {\n capture: {\n console: \"errors\",\n domSnapshot: true,\n network: \"errors\",\n },\n },\n role: \"qa\",\n screenshotConfig: {\n enabled: true,\n padding: 24,\n quality: 0.7,\n showPreview: true,\n },\n },\n};\n\n/**\n * Creates a preset menu configuration for a specific role.\n *\n * Returns a complete configuration that can be spread into AnyclickProvider props.\n * Coming-soon items are included by default but shown as disabled.\n *\n * @param role - The preset role to create a menu for\n * @param options - Optional customization options\n * @returns A complete preset configuration\n * @throws {Error} If an unknown role is specified\n *\n * @example\n * ```tsx\n * // Basic usage\n * const qaPreset = createPresetMenu(\"qa\");\n *\n * // With customization\n * const devPreset = createPresetMenu(\"developer\", {\n * includeComingSoon: false,\n * overrides: {\n * screenshotConfig: { quality: 0.9 },\n * },\n * });\n *\n * <AnyclickProvider\n * adapter={adapter}\n * menuItems={qaPreset.menuItems}\n * screenshotConfig={qaPreset.screenshotConfig}\n * theme={qaPreset.theme}\n * >\n * <App />\n * </AnyclickProvider>\n * ```\n *\n * @since 1.2.0\n */\nexport function createPresetMenu(\n role: PresetRole,\n options: CreatePresetMenuOptions = {},\n): PresetConfig {\n const preset = presetDefaults[role];\n if (!preset) {\n throw new Error(`Unknown preset role: ${role}`);\n }\n\n const includeComingSoon = options.includeComingSoon ?? true;\n const menuItems = (options.overrides?.menuItems ?? preset.menuItems).filter(\n (item) => (includeComingSoon ? true : item.status !== \"comingSoon\"),\n );\n\n // Shallow-clone menu items so consumers can mutate safely\n const clonedMenuItems: ContextMenuItem[] = menuItems.map((item) => ({\n ...item,\n children: item.children\n ? item.children.map((child) => ({ ...child }))\n : undefined,\n }));\n\n return {\n description: preset.description,\n label: preset.label,\n menuItems: clonedMenuItems,\n metadata: {\n ...preset.metadata,\n ...options.overrides?.metadata,\n },\n role: preset.role,\n screenshotConfig: {\n ...preset.screenshotConfig,\n ...options.overrides?.screenshotConfig,\n },\n theme: {\n ...preset.theme,\n ...options.overrides?.theme,\n },\n };\n}\n\n/**\n * Lists all available preset configurations.\n *\n * Returns cloned copies of all presets so they can be safely modified.\n * Useful for displaying available options or building custom preset selectors.\n *\n * @returns Array of all preset configurations\n *\n * @example\n * ```tsx\n * const presets = listPresets();\n *\n * function PresetSelector({ onSelect }) {\n * return (\n * <select onChange={(e) => onSelect(e.target.value)}>\n * {presets.map((preset) => (\n * <option key={preset.role} value={preset.role}>\n * {preset.label} - {preset.description}\n * </option>\n * ))}\n * </select>\n * );\n * }\n * ```\n *\n * @since 1.2.0\n */\nexport function listPresets(): PresetConfig[] {\n return Object.values(presetDefaults).map((preset) => ({\n ...preset,\n menuItems: preset.menuItems.map((item) => ({\n ...item,\n children: item.children\n ? item.children.map((child) => ({ ...child }))\n : undefined,\n })),\n }));\n}\n\nexport { presetDefaults };\n","/**\n * Type definitions for @ewjdev/anyclick-react.\n *\n * Contains all public interfaces, types, and utility functions\n * for configuring anyclick providers, menus, and themes.\n *\n * @module types\n * @since 1.0.0\n */\nimport type { CSSProperties, ReactNode } from \"react\";\nimport type {\n AnyclickAdapter,\n AnyclickPayload,\n AnyclickTriggerEvent,\n AnyclickType,\n ScreenshotConfig,\n ScreenshotData,\n} from \"@ewjdev/anyclick-core\";\nimport { CompactModeConfig } from \"./InspectDialog/InspectSimple\";\n\n// ============================================================================\n// Theme Configuration\n// ============================================================================\n\n/**\n * Theme configuration for AnyclickProvider.\n *\n * Supports nested theming with inheritance - child providers automatically\n * inherit and can override parent theme settings.\n *\n * @example\n * ```tsx\n * const theme: AnyclickTheme = {\n * menuStyle: { backgroundColor: \"#1a1a1a\" },\n * highlightConfig: {\n * colors: { targetColor: \"#ef4444\" },\n * },\n * };\n *\n * <AnyclickProvider adapter={adapter} theme={theme}>\n * <App />\n * </AnyclickProvider>\n * ```\n *\n * @since 1.0.0\n */\nexport interface AnyclickTheme {\n /** Whether anyclick functionality is disabled in this theme */\n disabled?: boolean;\n /**\n * Enable fun mode (go-kart cursor) within this scoped provider.\n * When true/configured, a FunModeBridge can hand off the track to the pointer.\n */\n funMode?: boolean | FunModeThemeConfig;\n /** Configuration for element highlighting */\n highlightConfig?: HighlightConfig;\n /** Custom class name for the context menu */\n menuClassName?: string;\n /** Custom styles for the context menu */\n menuStyle?: CSSProperties;\n /** Configuration for screenshot capture */\n screenshotConfig?: ScreenshotConfig;\n}\n\n/**\n * Optional fun mode configuration (forwarded to pointer fun mode).\n *\n * @since 1.3.0\n */\nexport interface FunModeThemeConfig {\n /** Optional acceleration override */\n acceleration?: number;\n /** Whether fun mode is enabled (default: true) */\n enabled?: boolean;\n /** Optional max speed override for this provider */\n maxSpeed?: number;\n}\n\n// ============================================================================\n// Menu Configuration\n// ============================================================================\n\n/**\n * Menu positioning modes for the context menu.\n *\n * - `static` - Menu stays at exact click position (may go off-screen)\n * - `inView` - Menu adjusts position to stay fully visible in viewport\n * - `dynamic` - User can drag the menu to reposition it\n *\n * @since 1.1.0\n */\nexport type MenuPositionMode = \"dynamic\" | \"inView\" | \"static\";\n\n/**\n * Menu item displayed in the Anyclick context menu.\n *\n * @example\n * ```tsx\n * const menuItems: ContextMenuItem[] = [\n * {\n * type: \"bug\",\n * label: \"Report Bug\",\n * icon: <BugIcon />,\n * showComment: true,\n * },\n * {\n * type: \"feature\",\n * label: \"Request Feature\",\n * showComment: true,\n * requiredRoles: [\"admin\", \"developer\"],\n * },\n * ];\n * ```\n *\n * @since 1.0.0\n */\nexport interface ContextMenuItem {\n /** Optional badge to render next to the label */\n badge?: FeedbackMenuBadge;\n /** Child menu items (creates a submenu) */\n children?: ContextMenuItem[];\n /** Optional icon */\n icon?: ReactNode;\n /** Display label */\n label: string;\n /**\n * Optional click handler for custom behavior.\n * Return `false` (or a Promise resolving to false) to skip the default submission flow.\n */\n onClick?: (context: {\n closeMenu: () => void;\n containerElement: Element | null;\n targetElement: Element | null;\n }) => boolean | Promise<boolean | void> | void;\n /** Optional role(s) required to see this menu item */\n requiredRoles?: string[];\n /** Whether to show a comment input for this type */\n showComment?: boolean;\n /** Optional status to signal availability (e.g., coming soon) */\n status?: FeedbackMenuStatus;\n /** Feedback type for this option (use unique identifier for parent items with children) */\n type: AnyclickType;\n}\n\n/**\n * Visual badge for menu items.\n *\n * @example\n * ```tsx\n * const badge: FeedbackMenuBadge = {\n * label: \"New\",\n * tone: \"success\",\n * };\n * ```\n *\n * @since 1.2.0\n */\nexport interface FeedbackMenuBadge {\n /** Text shown inside the badge */\n label: string;\n /** Optional tone to drive styling */\n tone?: \"info\" | \"neutral\" | \"success\" | \"warning\";\n}\n\n/**\n * Status of a menu item used for presets.\n *\n * - `available` - Item is fully functional\n * - `comingSoon` - Item is visible but disabled\n *\n * @since 1.2.0\n */\nexport type FeedbackMenuStatus = \"available\" | \"comingSoon\";\n\n// ============================================================================\n// Highlight Configuration\n// ============================================================================\n\n/**\n * Configuration for highlight colors.\n *\n * @example\n * ```tsx\n * const colors: HighlightColors = {\n * targetColor: \"#ef4444\", // Red for target\n * containerColor: \"#3b82f6\", // Blue for container\n * targetShadowOpacity: 0.3,\n * containerShadowOpacity: 0.15,\n * };\n * ```\n *\n * @since 1.0.0\n */\nexport interface HighlightColors {\n /** Color for the container element highlight (default: #8b5cf6 - purple) */\n containerColor?: string;\n /** Opacity for the container shadow (default: 0.1) */\n containerShadowOpacity?: number;\n /** Color for the target element highlight (default: #3b82f6 - blue) */\n targetColor?: string;\n /** Opacity for the target shadow (default: 0.25) */\n targetShadowOpacity?: number;\n}\n\n/**\n * Configuration for highlight behavior.\n *\n * @example\n * ```tsx\n * const highlightConfig: HighlightConfig = {\n * enabled: true,\n * colors: { targetColor: \"#ef4444\" },\n * containerSelectors: [\".card\", \".modal\", \"[data-container]\"],\n * minChildrenForContainer: 3,\n * };\n * ```\n *\n * @since 1.0.0\n */\nexport interface HighlightConfig {\n /** Custom colors for highlights */\n colors?: HighlightColors;\n /** CSS selectors to identify container elements */\n containerSelectors?: string[];\n /** Whether to show highlights (default: true) */\n enabled?: boolean;\n /** Minimum number of children for an element to be considered a container (default: 2) */\n minChildrenForContainer?: number;\n}\n\n// ============================================================================\n// User Context\n// ============================================================================\n\n/**\n * User context for role-based menu filtering.\n *\n * @example\n * ```tsx\n * const userContext: AnyclickUserContext = {\n * id: \"user-123\",\n * email: \"user@example.com\",\n * roles: [\"admin\", \"developer\"],\n * };\n *\n * const visibleItems = filterMenuItemsByRole(allMenuItems, userContext);\n * ```\n *\n * @since 1.2.0\n */\nexport interface AnyclickUserContext {\n /** User email */\n email?: string;\n /** User ID */\n id?: string;\n /** User's role(s) */\n roles?: string[];\n}\n\n/**\n * Filters menu items based on user context and required roles.\n *\n * Items without required roles are shown to everyone.\n * Items with required roles are only shown to users who have at least one matching role.\n *\n * @param items - Menu items to filter\n * @param userContext - Optional user context with roles\n * @returns Filtered menu items visible to the user\n *\n * @example\n * ```tsx\n * const allItems: ContextMenuItem[] = [\n * { type: \"bug\", label: \"Report Bug\" },\n * { type: \"admin\", label: \"Admin Panel\", requiredRoles: [\"admin\"] },\n * ];\n *\n * const userContext = { roles: [\"user\"] };\n * const visibleItems = filterMenuItemsByRole(allItems, userContext);\n * // => [{ type: \"bug\", label: \"Report Bug\" }]\n * ```\n *\n * @since 1.2.0\n */\nexport function filterMenuItemsByRole(\n items: ContextMenuItem[],\n userContext?: AnyclickUserContext,\n): ContextMenuItem[] {\n if (!userContext) {\n // If no user context, only show items without required roles\n return items.filter(\n (item) => !item.requiredRoles || item.requiredRoles.length === 0,\n );\n }\n\n const userRoles = userContext.roles ?? [];\n\n return items.filter((item) => {\n // If no required roles, show to everyone\n if (!item.requiredRoles || item.requiredRoles.length === 0) {\n return true;\n }\n // Check if user has any of the required roles\n return item.requiredRoles.some((role) => userRoles.includes(role));\n });\n}\n\n// ============================================================================\n// Provider Props\n// ============================================================================\n\n/**\n * Props for the AnyclickProvider component.\n *\n * @example\n * ```tsx\n * <AnyclickProvider\n * adapter={myAdapter}\n * menuItems={customMenuItems}\n * highlightConfig={{ colors: { targetColor: \"#ef4444\" } }}\n * screenshotConfig={{ enabled: true, showPreview: true }}\n * onSubmitSuccess={(payload) => console.log(\"Submitted:\", payload)}\n * >\n * <App />\n * </AnyclickProvider>\n * ```\n *\n * @since 1.0.0\n */\nexport interface AnyclickProviderProps {\n /** The adapter to use for submitting anyclick */\n adapter: AnyclickAdapter;\n /** Child components */\n children: ReactNode;\n /** Cooldown in milliseconds between submissions (rate limiting) */\n cooldownMs?: number;\n /** Whether the provider is disabled */\n disabled?: boolean;\n /** Header content */\n header?: ReactNode | null;\n /** Configuration for element highlighting */\n highlightConfig?: HighlightConfig;\n /** Maximum number of ancestors to capture */\n maxAncestors?: number;\n /** Maximum length for innerText capture */\n maxInnerTextLength?: number;\n /** Maximum length for outerHTML capture */\n maxOuterHTMLLength?: number;\n /** Custom class name for the context menu */\n menuClassName?: string;\n /** Custom menu items (defaults to Issue, Feature, Like) */\n menuItems?: ContextMenuItem[];\n /** Menu positioning mode (default: 'inView') */\n menuPositionMode?: MenuPositionMode;\n /** Custom styles for the context menu */\n menuStyle?: CSSProperties;\n /** Additional metadata to include with every submission */\n metadata?: Record<string, unknown>;\n /** Callback after failed submission */\n onSubmitError?: (error: Error, payload: AnyclickPayload) => void;\n /** Callback after successful submission */\n onSubmitSuccess?: (payload: AnyclickPayload) => void;\n /**\n * Whether to scope this provider to its children only.\n * When true, events will only be captured for elements within this provider's subtree.\n * When false (default), events are captured for the entire document.\n */\n scoped?: boolean;\n /** Configuration for screenshot capture */\n screenshotConfig?: ScreenshotConfig;\n /** Attributes to strip from outerHTML for privacy */\n stripAttributes?: string[];\n /**\n * Filter function to determine if anyclick should be captured for a target element.\n * Return true to allow anyclick, false to ignore.\n * Accepts both MouseEvent (right-click) and TouchEvent (press-and-hold).\n */\n targetFilter?: (event: AnyclickTriggerEvent, target: Element) => boolean;\n /**\n * Theme configuration for this provider.\n * Themes are inherited from parent providers and merged (child overrides parent).\n * Set to null or { disabled: true } to disable anyclick in this subtree.\n */\n theme?: AnyclickTheme | null;\n /** Duration in ms to hold touch before triggering context menu (default: 500) */\n touchHoldDurationMs?: number;\n /** Maximum movement in px before touch hold is cancelled (default: 10) */\n touchMoveThreshold?: number;\n}\n\n// ============================================================================\n// Context Value\n// ============================================================================\n\n/**\n * Context value exposed by AnyclickProvider.\n *\n * Access via the {@link useAnyclick} hook.\n *\n * @example\n * ```tsx\n * function MyComponent() {\n * const {\n * isEnabled,\n * isSubmitting,\n * openMenu,\n * closeMenu,\n * submitAnyclick,\n * theme,\n * } = useAnyclick();\n *\n * // ...\n * }\n * ```\n *\n * @since 1.0.0\n */\nexport interface AnyclickContextValue {\n /** Close the anyclick menu */\n closeMenu: () => void;\n /** Whether anyclick is currently enabled */\n isEnabled: boolean;\n /** Whether a submission is in progress */\n isSubmitting: boolean;\n /** Open the anyclick menu programmatically */\n openMenu: (element: Element, position: { x: number; y: number }) => void;\n /** The provider's unique ID */\n providerId: string;\n /** Whether this provider is scoped */\n scoped: boolean;\n /** Submit anyclick for a specific element */\n submitAnyclick: (\n element: Element,\n type: AnyclickType,\n comment?: string,\n ) => Promise<void>;\n /** The current merged theme (inherited from ancestors) */\n theme: AnyclickTheme;\n}\n\n// ============================================================================\n// Component Props\n// ============================================================================\n\n/**\n * Props for the ContextMenu component.\n *\n * @since 1.0.0\n */\nexport interface ContextMenuProps {\n /** Custom class name */\n className?: string;\n /** Container element found by highlight logic */\n containerElement: Element | null;\n /** Footer content */\n footer?: ReactNode;\n /** Header content */\n header?: ReactNode;\n /** Configuration for element highlighting */\n highlightConfig?: HighlightConfig;\n /** Whether submission is in progress */\n isSubmitting: boolean;\n /** Menu items to display */\n items: ContextMenuItem[];\n /** Callback when menu is closed */\n onClose: () => void;\n /** Callback when an item is selected */\n onSelect: (\n type: AnyclickType,\n comment?: string,\n screenshots?: ScreenshotData,\n ) => void;\n /** Position of the menu */\n position: { x: number; y: number };\n /** Menu positioning mode (default: 'inView') */\n positionMode?: MenuPositionMode;\n /** Configuration for screenshot capture */\n screenshotConfig?: ScreenshotConfig;\n /** Custom styles */\n style?: CSSProperties;\n /** Target element for anyclick */\n targetElement: Element | null;\n /** Whether the menu is visible */\n visible: boolean;\n}\n\n/**\n * Props for the ScreenshotPreview component.\n *\n * @since 1.0.0\n */\nexport interface ScreenshotPreviewProps {\n /** Whether screenshots are loading */\n isLoading: boolean;\n /** Whether submission is in progress */\n isSubmitting: boolean;\n /** Callback when user cancels */\n onCancel: () => void;\n /** Callback when user confirms screenshots */\n onConfirm: (screenshots: ScreenshotData) => void;\n /** Callback when user wants to retake screenshots */\n onRetake: () => void;\n /** Captured screenshot data */\n screenshots: ScreenshotData | null;\n}\n\n// ============================================================================\n// Utility Functions\n// ============================================================================\n\n/**\n * Generates compact styles from a CompactModeConfig.\n *\n * Used internally by InspectDialog to apply compact mode styling.\n *\n * @param config - The compact mode configuration\n * @returns Record of style objects keyed by component name\n * @internal\n */\nexport function generateCompactStyles(\n config: CompactModeConfig,\n): Record<string, React.CSSProperties> {\n return {\n actionButton: {\n fontSize: `${config.fonts.button}px`,\n gap: config.gaps.button,\n padding: config.spacing.buttonPadding,\n },\n actionButtonDanger: {\n fontSize: `${config.fonts.button}px`,\n padding: config.spacing.buttonDangerPadding,\n },\n actionButtonPrimary: {\n fontSize: `${config.fonts.button}px`,\n gap: config.gaps.button,\n padding: config.spacing.buttonPrimaryPadding,\n },\n badge: {\n fontSize: `${config.fonts.badge}px`,\n padding: config.spacing.badgePadding,\n },\n classes: {\n fontSize: `${config.fonts.tag}px`,\n },\n closeButton: {\n height: `${config.sizes.closeButton}px`,\n width: `${config.sizes.closeButton}px`,\n },\n copyButtonSmall: {\n height: `${config.sizes.copyButtonSmall}px`,\n width: `${config.sizes.copyButtonSmall}px`,\n },\n dialog: {\n fontSize: `${config.fonts.base}px`,\n width: `${config.sizes.dialogWidth}px`,\n },\n footer: {\n gap: config.gaps.footer,\n padding: config.spacing.footerPadding,\n },\n header: {\n padding: config.spacing.headerPadding,\n },\n headerTitle: {\n fontSize: `${config.fonts.title}px`,\n gap: config.gaps.headerTitle,\n },\n id: {\n fontSize: `${config.fonts.tag}px`,\n },\n identity: {\n padding: config.spacing.identityPadding,\n },\n pinButtons: {\n gap: config.gaps.pinButtons,\n padding: \"1px\",\n },\n propertyLabel: {\n fontSize: `${config.fonts.property}px`,\n },\n propertyRow: {\n gap: config.gaps.propertyRow,\n padding: config.spacing.propertyRowPadding,\n },\n propertyValue: {\n fontSize: `${config.fonts.property}px`,\n gap: config.gaps.propertyValue,\n },\n sectionContent: {\n padding: config.spacing.sectionContentPadding,\n },\n sectionHeader: {\n fontSize: `${config.fonts.section}px`,\n padding: config.spacing.sectionHeaderPadding,\n },\n sectionTitle: {\n letterSpacing: config.letterSpacing.sectionTitle,\n },\n selectorCode: {\n fontSize: `${config.fonts.selector}px`,\n padding: config.spacing.selectorCodePadding,\n },\n styleCategory: {\n marginBottom: `${config.sizes.categoryMarginBottom}px`,\n },\n styleCategoryHeader: {\n fontSize: `${config.fonts.property}px`,\n marginBottom: `${config.sizes.styleCategoryHeaderMarginBottom}px`,\n },\n styleRow: {\n fontSize: `${config.fonts.styleRow}px`,\n padding: config.spacing.styleRowPadding,\n },\n styleValue: {\n maxWidth: `${config.sizes.styleValueMaxWidth}px`,\n },\n tag: {\n fontSize: `${config.fonts.tag}px`,\n },\n };\n}\n","/**\n * @ewjdev/anyclick-react\n *\n * React provider and context menu UI for UI feedback capture.\n * Enables right-click context menus for submitting feedback, capturing screenshots,\n * and integrating with various adapters (GitHub, AI agents, etc.)\n *\n * @packageDocumentation\n * @module @ewjdev/anyclick-react\n * @since 1.0.0\n *\n * @example\n * ```tsx\n * import { AnyclickProvider } from \"@ewjdev/anyclick-react\";\n * import { createHttpAdapter } from \"@ewjdev/anyclick-github\";\n *\n * const adapter = createHttpAdapter({ endpoint: \"/api/feedback\" });\n *\n * function App() {\n * return (\n * <AnyclickProvider adapter={adapter}>\n * <YourApp />\n * </AnyclickProvider>\n * );\n * }\n * ```\n */\n\"use client\";\n\n// ============================================================================\n// Core Components\n// ============================================================================\n\n/**\n * Main provider component for anyclick functionality.\n * Wraps your app to enable right-click feedback capture.\n * @see {@link AnyclickProviderProps} for configuration options\n */\nexport { AnyclickProvider } from \"./AnyclickProvider\";\n\n/**\n * Bridge component for enabling fun mode (go-kart cursor) within a scoped provider.\n * @tag {experimental}\n */\nexport { FunModeBridge } from \"./FunModeBridge\";\n\n/**\n * Standalone context menu component for custom implementations.\n * @see {@link ContextMenuProps} for configuration options\n */\nexport { ContextMenu } from \"./ContextMenu\";\n\n/**\n * Screenshot preview component displayed before sending feedback.\n * @see {@link ScreenshotPreviewProps} for configuration options\n */\nexport { ScreenshotPreview } from \"./ScreenshotPreview\";\n\n// ============================================================================\n// Deprecated Exports (Backward Compatibility)\n// ============================================================================\n\n/**\n * @deprecated Use {@link AnyclickProvider} instead. Will be removed in v2.0.0.\n */\nexport { FeedbackProvider } from \"./AnyclickProvider\";\n\n// ============================================================================\n// Context and Hooks\n// ============================================================================\n\n/**\n * React context for anyclick functionality.\n * Use with `useContext` for custom implementations.\n */\nexport { AnyclickContext } from \"./context\";\n\n/**\n * Hook to access anyclick context values.\n * @throws {Error} When used outside of AnyclickProvider\n * @example\n * ```tsx\n * function MyComponent() {\n * const { openMenu, isSubmitting } = useAnyclick();\n * // ...\n * }\n * ```\n */\nexport { useAnyclick } from \"./context\";\n\n/**\n * @deprecated Use {@link AnyclickContext} instead. Will be removed in v2.0.0.\n */\nexport { FeedbackContext } from \"./context\";\n\n/**\n * @deprecated Use {@link useAnyclick} instead. Will be removed in v2.0.0.\n */\nexport { useFeedback } from \"./context\";\n\n// ============================================================================\n// Store (Advanced Use Cases)\n// ============================================================================\n\n/**\n * Zustand store hook for managing provider instances.\n * For advanced use cases like custom provider hierarchies.\n */\nexport { useProviderStore } from \"./store\";\n\n/**\n * Generates a unique ID for a provider instance.\n */\nexport { generateProviderId } from \"./store\";\n\n/**\n * Dispatches a context menu event to matching providers.\n */\nexport { dispatchContextMenuEvent } from \"./store\";\n\n/**\n * Provider instance type for advanced store management.\n */\nexport type { ProviderInstance } from \"./store\";\n\n// ============================================================================\n// Types\n// ============================================================================\n\nexport type {\n /** Props for AnyclickProvider component */\n AnyclickProviderProps,\n /** Context value exposed by AnyclickProvider */\n AnyclickContextValue,\n /** Theme configuration for AnyclickProvider */\n AnyclickTheme,\n /** Menu item configuration */\n ContextMenuItem,\n /** Fun mode theme configuration */\n FunModeThemeConfig,\n /** Props for ContextMenu component */\n ContextMenuProps,\n /** Highlight color configuration */\n HighlightColors,\n /** Highlight behavior configuration */\n HighlightConfig,\n /** User context for role-based filtering */\n AnyclickUserContext,\n /** Props for ScreenshotPreview component */\n ScreenshotPreviewProps,\n /** Menu positioning modes */\n MenuPositionMode,\n /** Visual badge for menu items */\n FeedbackMenuBadge,\n /** Status of a menu item */\n FeedbackMenuStatus,\n} from \"./types\";\n\n// ============================================================================\n// Presets\n// ============================================================================\n\n/**\n * Creates a preset menu configuration for a specific role.\n * @param role - The preset role (qa, pm, designer, developer, chrome)\n * @param options - Optional configuration overrides\n * @returns A complete preset configuration\n * @example\n * ```tsx\n * const qaPreset = createPresetMenu(\"qa\");\n * <AnyclickProvider\n * adapter={adapter}\n * menuItems={qaPreset.menuItems}\n * screenshotConfig={qaPreset.screenshotConfig}\n * />\n * ```\n */\nexport { createPresetMenu } from \"./presets\";\n\n/**\n * Lists all available preset configurations.\n */\nexport { listPresets } from \"./presets\";\n\n/**\n * Default preset configurations by role.\n */\nexport { presetDefaults } from \"./presets\";\n\nexport type {\n /** Available preset roles */\n PresetRole,\n /** Preset configuration structure */\n PresetConfig,\n /** Options for creating preset menus */\n CreatePresetMenuOptions,\n} from \"./presets\";\n\n// ============================================================================\n// Utilities\n// ============================================================================\n\n/**\n * Filters menu items based on user roles.\n * @param items - Menu items to filter\n * @param userContext - User context with roles\n * @returns Filtered menu items visible to the user\n */\nexport { filterMenuItemsByRole } from \"./types\";\n\n// ============================================================================\n// Core Re-exports\n// ============================================================================\n\nexport type {\n /** Feedback type identifier */\n AnyclickType,\n /** Feedback submission payload */\n AnyclickPayload,\n /** Adapter interface for submitting feedback */\n AnyclickAdapter,\n /** DOM element context information */\n ElementContext,\n /** Page-level context information */\n PageContext,\n /** Captured screenshot data */\n ScreenshotData,\n /** Screenshot capture configuration */\n ScreenshotConfig,\n /** Individual screenshot capture */\n ScreenshotCapture,\n /** Screenshot capture mode */\n ScreenshotCaptureMode,\n} from \"@ewjdev/anyclick-core\";\n\nexport {\n /** Captures all configured screenshots */\n captureAllScreenshots,\n /** Captures a single screenshot */\n captureScreenshot,\n /** Checks if screenshot capture is supported */\n isScreenshotSupported,\n /** Formats bytes to human-readable string */\n formatBytes,\n /** Estimates total size of screenshot data */\n estimateTotalSize,\n /** Default screenshot configuration */\n DEFAULT_SCREENSHOT_CONFIG,\n /** Default sensitive element selectors */\n DEFAULT_SENSITIVE_SELECTORS,\n} from \"@ewjdev/anyclick-core\";\n\n// ============================================================================\n// Styles\n// ============================================================================\n\n/**\n * Default menu styles for customization.\n */\nexport { menuStyles } from \"./styles\";\n\n/**\n * Dark mode menu styles.\n */\nexport { darkMenuStyles } from \"./styles\";\n\n/**\n * CSS custom properties for menu theming.\n * Override these via the `style` prop on AnyclickProvider.\n */\nexport { menuCSSVariables } from \"./styles\";\n\n/**\n * Gets badge styles for a specific tone.\n */\nexport { getBadgeStyle } from \"./styles\";\n\n// ============================================================================\n// Highlight Utilities\n// ============================================================================\n\n/**\n * Finds the closest container parent element based on configuration.\n */\nexport { findContainerParent } from \"./highlight\";\n\n/**\n * Applies highlight styling to target element.\n */\nexport { highlightTarget } from \"./highlight\";\n\n/**\n * Applies highlight styling to container element.\n */\nexport { highlightContainer } from \"./highlight\";\n\n/**\n * Removes all highlight styling from the document.\n */\nexport { clearHighlights } from \"./highlight\";\n\n/**\n * Applies highlights to both target and container elements.\n */\nexport { applyHighlights } from \"./highlight\";\n\n/**\n * Default highlight colors.\n */\nexport { defaultHighlightColors } from \"./highlight\";\n\n/**\n * Default CSS selectors for identifying container elements.\n */\nexport { defaultContainerSelectors } from \"./highlight\";\n\n// ============================================================================\n// Inspect Simple (Lightweight Inspector)\n// ============================================================================\n\n/**\n * Lightweight element inspector component for mobile-friendly inspection.\n */\nexport { InspectSimple } from \"./InspectDialog/InspectSimple\";\n\n/**\n * Default compact mode configuration for InspectSimple.\n */\nexport { DEFAULT_COMPACT_CONFIG } from \"./InspectDialog/InspectSimple\";\n\nexport type {\n /** Props for InspectSimple component */\n InspectSimpleProps,\n /** Dialog pinned position options */\n PinnedPosition,\n /** Compact mode configuration */\n CompactModeConfig,\n} from \"./InspectDialog/InspectSimple\";\n\n/**\n * Manager component that listens for inspect events and renders InspectSimple.\n * Place this component once in your app to enable inspect functionality.\n */\nexport { InspectDialogManager } from \"./InspectDialog/InspectDialogManager\";\n\n/**\n * Opens the inspect dialog for a given element.\n */\nexport { openInspectDialog } from \"./InspectDialog/InspectDialogManager\";\n\n/**\n * Event name for inspect dialog events.\n */\nexport { INSPECT_DIALOG_EVENT } from \"./InspectDialog/InspectDialogManager\";\n\nexport type {\n /** Props for InspectDialogManager component */\n InspectDialogManagerProps,\n /** Event detail for inspect dialog events */\n InspectDialogEventDetail,\n} from \"./InspectDialog/InspectDialogManager\";\n\n// ============================================================================\n// Branding\n// ============================================================================\n\n/**\n * Anyclick logo component for branding.\n */\nexport { AnyclickLogo } from \"./AnyclickLogo\";\n\nexport type {\n /** Props for AnyclickLogo component */\n AnyclickLogoProps,\n} from \"./AnyclickLogo\";\n\n// ============================================================================\n// IDE Integration\n// ============================================================================\n\n/**\n * Opens a source file in the preferred IDE.\n */\nexport { openInIDE } from \"./ide\";\n\n/**\n * Builds a URL for opening a file in an IDE.\n */\nexport { buildIDEUrl } from \"./ide\";\n\n/**\n * Checks if an IDE protocol is supported.\n */\nexport { isIDEProtocolSupported } from \"./ide\";\n\n/**\n * Detects the user's preferred IDE from environment.\n */\nexport { detectPreferredIDE } from \"./ide\";\n\n/**\n * Extracts source location from element's data attributes.\n */\nexport { getSourceLocationFromElement } from \"./ide\";\n\n/**\n * Finds source location by searching ancestor elements.\n */\nexport { findSourceLocationInAncestors } from \"./ide\";\n\n/**\n * Creates a configured IDE opener function.\n */\nexport { createIDEOpener } from \"./ide\";\n\n/**\n * Formats source location as a readable string.\n */\nexport { formatSourceLocation } from \"./ide\";\n\nexport type {\n /** Supported IDE protocols */\n IDEProtocol,\n /** IDE configuration options */\n IDEConfig,\n /** Source file location information */\n SourceLocation,\n} from \"./ide\";\n\n// ============================================================================\n// Inspect Utilities (Core Re-exports)\n// ============================================================================\n\nexport {\n /** Gets computed styles for an element */\n getComputedStyles,\n /** Gets accessibility information for an element */\n getAccessibilityInfo,\n /** Gets box model information for an element */\n getBoxModelInfo,\n /** Gets element attributes */\n getAttributes,\n /** Gets comprehensive element inspect information */\n getElementInspectInfo,\n /** Formats styles as CSS string */\n formatStylesAsCSS,\n /** Formats box model as readable string */\n formatBoxModel,\n /** Curated list of important CSS properties */\n CURATED_STYLE_PROPERTIES,\n /** All curated CSS properties */\n ALL_CURATED_PROPERTIES,\n} from \"@ewjdev/anyclick-core\";\n\nexport type {\n /** Computed styles information */\n ComputedStylesInfo,\n /** Accessibility information */\n AccessibilityInfo,\n /** Box model information */\n BoxModelInfo,\n /** Element inspection information */\n ElementInspectInfo,\n} from \"@ewjdev/anyclick-core\";\n","\"use client\";\n\nimport React from \"react\";\n\nexport interface AnyclickLogoProps {\n /** Size of the logo in pixels. Defaults to 64 */\n size?: number;\n /** Border width in pixels. Defaults to 2 (same as default cursor stroke) */\n borderWidth?: number;\n /** Primary color for the circle border and cursor. Defaults to #3b82f6 (blue-500) */\n primaryColor?: string;\n /** Background color of the circle. Defaults to rgba(59, 130, 246, 0.1) */\n backgroundColor?: string;\n /** Custom class name */\n className?: string;\n /** Custom styles */\n style?: React.CSSProperties;\n /** Click handler */\n onClick?: () => void;\n}\n\n/**\n * Anyclick Logo - A circle with a cursor pointer in the center\n * The cursor is styled similarly to the default system cursor\n */\nexport function AnyclickLogo({\n size = 64,\n borderWidth = 2,\n primaryColor = \"#3b82f6\",\n backgroundColor = \"rgba(59, 130, 246, 0.1)\",\n className,\n style,\n onClick,\n}: AnyclickLogoProps) {\n // Cursor size is proportional to the circle size\n const cursorSize = size * 0.45;\n const cursorStroke = borderWidth;\n\n return (\n <svg\n width={size}\n height={size}\n viewBox={`0 0 ${size} ${size}`}\n fill=\"none\"\n xmlns=\"http://www.w3.org/2000/svg\"\n className={className}\n style={{ cursor: onClick ? \"pointer\" : undefined, ...style }}\n onClick={onClick}\n role={onClick ? \"button\" : \"img\"}\n aria-label=\"Anyclick Logo\"\n >\n {/* Circle background */}\n <circle\n cx={size / 2}\n cy={size / 2}\n r={size / 2 - borderWidth / 2}\n fill={backgroundColor}\n stroke={primaryColor}\n strokeWidth={borderWidth}\n />\n\n {/* Cursor pointer - centered in the circle */}\n <g\n transform={`translate(${(size - cursorSize) / 2}, ${(size - cursorSize) / 2})`}\n >\n {/* Cursor shape - classic pointer arrow */}\n <path\n d={`\n M ${cursorSize * 0.15} ${cursorSize * 0.08}\n L ${cursorSize * 0.15} ${cursorSize * 0.85}\n L ${cursorSize * 0.35} ${cursorSize * 0.65}\n L ${cursorSize * 0.55} ${cursorSize * 0.85}\n L ${cursorSize * 0.65} ${cursorSize * 0.75}\n L ${cursorSize * 0.45} ${cursorSize * 0.55}\n L ${cursorSize * 0.7} ${cursorSize * 0.55}\n Z\n `}\n fill=\"white\"\n stroke={primaryColor}\n strokeWidth={cursorStroke}\n strokeLinejoin=\"round\"\n strokeLinecap=\"round\"\n />\n </g>\n </svg>\n );\n}\n\nexport default AnyclickLogo;\n"],"mappings":"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","names":["useCallback","useEffect","useMemo","useRef","useState","React","useState","ScreenshotPreview","jsx","jsxs","React","MenuItem","useState","BackButton","CommentForm","jsx","jsxs","OFFSCREEN_POSITION","useState","useRef","useCallback","useMemo","mergedTheme","useEffect","useEffect","useMemo","useRef","useRef","useMemo","useEffect","useCallback","useEffect","useState","useEffect","useMemo","useRef","useState","Fragment","jsx","jsxs","useState","useEffect","useRef","useMemo","jsx","useState","useCallback","useEffect","captureAllScreenshots","captureScreenshot","isScreenshotSupported","formatBytes","estimateTotalSize","DEFAULT_SCREENSHOT_CONFIG","jsx","jsxs","getElementInspectInfo"]}
1
+ {"version":3,"sources":["../src/AnyclickProvider.tsx","../src/ContextMenu.tsx","../src/QuickChat/QuickChat.tsx","../src/QuickChat/styles.ts","../src/QuickChat/useQuickChat.ts","../src/QuickChat/store.ts","../src/QuickChat/types.ts","../src/QuickChat/useQuickChat.context.ts","../src/QuickChat/useQuickChat.debug.ts","../src/QuickChat/useQuickChat.messages.ts","../src/QuickChat/useQuickChat.rateLimit.ts","../src/ScreenshotPreview.tsx","../src/styles.ts","../src/highlight.ts","../src/context.ts","../src/store.ts","../src/FunModeBridge.tsx","../src/ui/button.tsx","../src/utils/cn.ts","../src/ui/input.tsx","../src/InspectDialog/InspectDialogManager.tsx","../src/InspectDialog/InspectSimple.tsx","../src/ide.ts","../src/presets.ts","../src/types.ts","../src/index.ts","../src/AnyclickLogo.tsx"],"sourcesContent":["\"use client\";\n\n/**\n * AnyclickProvider - Main provider component for anyclick functionality.\n *\n * Wraps your app to enable right-click feedback capture. Supports scoped\n * providers and nested theming with inheritance.\n *\n * @module AnyclickProvider\n * @since 1.0.0\n */\nimport React, {\n useCallback,\n useEffect,\n useId,\n useLayoutEffect,\n useMemo,\n useRef,\n useState,\n} from \"react\";\nimport type {\n AnyclickClient,\n AnyclickMenuEvent,\n AnyclickType,\n ScreenshotData,\n} from \"@ewjdev/anyclick-core\";\nimport { createAnyclickClient } from \"@ewjdev/anyclick-core\";\nimport { ContextMenu } from \"./ContextMenu\";\nimport { AnyclickContext, useAnyclick } from \"./context\";\nimport { findContainerParent } from \"./highlight\";\nimport { type ProviderInstance, useProviderStore } from \"./store\";\nimport type {\n AnyclickContextValue,\n AnyclickProviderProps,\n AnyclickTheme,\n ContextMenuItem,\n} from \"./types\";\n\n/**\n * Default menu items shown when no custom items are provided.\n */\nconst defaultMenuItems: ContextMenuItem[] = [\n { label: \"Report an issue\", showComment: true, type: \"issue\" },\n { label: \"Request a feature\", showComment: true, type: \"feature\" },\n { label: \"I like this!\", showComment: false, type: \"like\" },\n];\n\nconst OFFSCREEN_POSITION = { x: -9999, y: -9999 };\n\n/**\n * AnyclickProvider component - wraps your app to enable feedback capture.\n *\n * Supports scoped providers and nested theming with inheritance.\n * Child providers automatically inherit and can override parent themes.\n *\n * @example\n * ```tsx\n * <AnyclickProvider\n * adapter={myAdapter}\n * menuItems={[\n * { type: \"bug\", label: \"Report Bug\", showComment: true },\n * ]}\n * onSubmitSuccess={(payload) => console.log(\"Submitted:\", payload)}\n * >\n * <App />\n * </AnyclickProvider>\n * ```\n *\n * @since 1.0.0\n */\nexport function AnyclickProvider({\n adapter,\n children,\n cooldownMs,\n disabled = false,\n header,\n highlightConfig,\n maxAncestors,\n maxInnerTextLength,\n maxOuterHTMLLength,\n menuClassName,\n menuItems = defaultMenuItems,\n menuStyle,\n metadata,\n onSubmitError,\n onSubmitSuccess,\n quickChatConfig,\n scoped = false,\n screenshotConfig,\n stripAttributes,\n targetFilter,\n theme,\n touchHoldDurationMs,\n touchMoveThreshold,\n}: AnyclickProviderProps) {\n const [isSubmitting, setIsSubmitting] = useState(false);\n const [menuVisible, setMenuVisible] = useState(false);\n const [menuPosition, setMenuPosition] = useState(OFFSCREEN_POSITION);\n const [targetElement, setTargetElement] = useState<Element | null>(null);\n const [containerElement, setContainerElement] = useState<Element | null>(\n null,\n );\n\n // Generate a stable ID for this provider instance using React's useId\n const providerId = useId();\n\n // Ref to the container element (for scoped providers)\n const containerRef = useRef<HTMLDivElement | null>(null);\n\n // Track when container is ready for scoped providers\n const [containerReady, setContainerReady] = useState(!scoped);\n\n // Client reference\n const clientRef = useRef<AnyclickClient | null>(null);\n\n // Callback ref to detect when container element is mounted\n const setContainerRef = useCallback(\n (node: HTMLDivElement | null) => {\n containerRef.current = node;\n if (scoped && node) {\n setContainerReady(true);\n // If client already exists, update its container\n if (clientRef.current) {\n clientRef.current.setContainer(node);\n }\n }\n },\n [scoped],\n );\n\n // Access parent context (if nested)\n let parentContext: AnyclickContextValue | null = null;\n try {\n parentContext = useAnyclick();\n } catch {\n parentContext = null;\n }\n\n // Store access\n const {\n findParentProvider,\n getMergedTheme,\n isDisabledByAncestor,\n isElementInAnyScopedProvider,\n isElementInDisabledScope,\n registerProvider,\n unregisterProvider,\n updateProvider,\n } = useProviderStore();\n\n // Determine parent ID\n const parentId = parentContext?.providerId ?? null;\n\n // Calculate depth\n const actualDepth = useMemo(() => {\n if (!parentContext) return 0;\n let d = 0;\n let currentId = parentId;\n const providers = useProviderStore.getState().providers;\n while (currentId) {\n d++;\n const parent = providers.get(currentId);\n currentId = parent?.parentId ?? null;\n }\n return d;\n }, [parentContext, parentId]);\n\n // Determine if disabled by theme\n const isDisabledByTheme = theme === null || theme?.disabled === true;\n const effectiveDisabled = disabled || isDisabledByTheme;\n\n // Build the theme for this provider\n const localTheme: AnyclickTheme = useMemo(() => {\n if (theme === null) {\n return { disabled: true };\n }\n\n const explicitThemeProps: AnyclickTheme = {};\n if (menuStyle) explicitThemeProps.menuStyle = menuStyle;\n if (menuClassName) explicitThemeProps.menuClassName = menuClassName;\n if (highlightConfig) explicitThemeProps.highlightConfig = highlightConfig;\n if (screenshotConfig)\n explicitThemeProps.screenshotConfig = screenshotConfig;\n\n return {\n ...explicitThemeProps,\n ...theme,\n };\n }, [highlightConfig, menuClassName, menuStyle, screenshotConfig, theme]);\n\n // Context menu handler\n const handleContextMenu = useCallback(\n (event: AnyclickMenuEvent, element: Element): boolean => {\n // For non-scoped providers, check if element is in a disabled scope\n if (!scoped && isElementInDisabledScope(element)) {\n return false;\n }\n\n // For non-scoped providers on touch events, defer to scoped providers\n if (!scoped && event.isTouch && isElementInAnyScopedProvider(element)) {\n return false;\n }\n\n const mergedTheme = getMergedTheme(providerId);\n\n setTargetElement(element);\n const container = findContainerParent(\n element,\n mergedTheme.highlightConfig ?? highlightConfig,\n );\n setContainerElement(container);\n setMenuPosition({ x: event.clientX, y: event.clientY });\n setMenuVisible(true);\n\n return true;\n },\n [\n getMergedTheme,\n highlightConfig,\n isElementInAnyScopedProvider,\n isElementInDisabledScope,\n providerId,\n scoped,\n ],\n );\n\n // Register this provider in the store\n useLayoutEffect(() => {\n const providerInstance: ProviderInstance = {\n containerRef: containerRef as React.RefObject<Element | null>,\n depth: actualDepth,\n disabled: effectiveDisabled,\n id: providerId,\n onContextMenu: handleContextMenu,\n parentId,\n scoped,\n theme: localTheme,\n };\n\n registerProvider(providerInstance);\n\n return () => {\n unregisterProvider(providerId);\n };\n }, [\n actualDepth,\n effectiveDisabled,\n handleContextMenu,\n localTheme,\n parentId,\n providerId,\n registerProvider,\n scoped,\n unregisterProvider,\n ]);\n\n // Update provider when config changes\n useEffect(() => {\n updateProvider(providerId, {\n disabled: effectiveDisabled,\n onContextMenu: handleContextMenu,\n theme: localTheme,\n });\n }, [\n effectiveDisabled,\n handleContextMenu,\n localTheme,\n providerId,\n updateProvider,\n ]);\n\n // Create/update the feedback client\n useEffect(() => {\n if (isDisabledByAncestor(providerId)) {\n return;\n }\n\n if (scoped && !containerReady) {\n return;\n }\n\n const client = createAnyclickClient({\n adapter,\n container: scoped ? containerRef.current : null,\n cooldownMs,\n maxAncestors,\n maxInnerTextLength,\n maxOuterHTMLLength,\n stripAttributes,\n targetFilter,\n touchHoldDurationMs,\n touchMoveThreshold,\n });\n\n client.onSubmitSuccess = onSubmitSuccess;\n client.onSubmitError = onSubmitError;\n client.onContextMenu = handleContextMenu;\n\n clientRef.current = client;\n\n if (!effectiveDisabled) {\n client.attach();\n }\n\n return () => {\n client.detach();\n };\n }, [\n adapter,\n containerReady,\n cooldownMs,\n effectiveDisabled,\n handleContextMenu,\n isDisabledByAncestor,\n maxAncestors,\n maxInnerTextLength,\n maxOuterHTMLLength,\n onSubmitError,\n onSubmitSuccess,\n providerId,\n scoped,\n stripAttributes,\n targetFilter,\n touchHoldDurationMs,\n touchMoveThreshold,\n ]);\n\n // Submit feedback with optional screenshots\n const submitAnyclick = useCallback(\n async (\n element: Element,\n type: AnyclickType,\n comment?: string,\n screenshots?: ScreenshotData,\n ) => {\n const client = clientRef.current;\n if (!client) return;\n\n setIsSubmitting(true);\n try {\n await client.submitAnyclick(element, type, {\n comment,\n metadata,\n screenshots,\n });\n } finally {\n setIsSubmitting(false);\n setMenuVisible(false);\n setMenuPosition(OFFSCREEN_POSITION);\n setTargetElement(null);\n setContainerElement(null);\n }\n },\n [metadata],\n );\n\n // Open menu programmatically\n const openMenu = useCallback(\n (element: Element, position: { x: number; y: number }) => {\n setTargetElement(element);\n const mergedTheme = getMergedTheme(providerId);\n const container = findContainerParent(\n element,\n mergedTheme.highlightConfig ?? highlightConfig,\n );\n setContainerElement(container);\n setMenuPosition(position);\n setMenuVisible(true);\n },\n [getMergedTheme, highlightConfig, providerId],\n );\n\n // Close menu\n const closeMenu = useCallback(() => {\n setMenuVisible(false);\n setMenuPosition(OFFSCREEN_POSITION);\n setTargetElement(null);\n setContainerElement(null);\n }, []);\n\n // Handle menu selection\n const handleMenuSelect = useCallback(\n (type: AnyclickType, comment?: string, screenshots?: ScreenshotData) => {\n if (targetElement) {\n submitAnyclick(targetElement, type, comment, screenshots);\n }\n },\n [submitAnyclick, targetElement],\n );\n\n // Get merged theme for this provider\n const inheritedTheme = getMergedTheme(providerId);\n\n // Merge: inherited theme first, then local theme overrides\n const mergedTheme: AnyclickTheme = useMemo(\n () => ({\n ...inheritedTheme,\n ...localTheme,\n highlightConfig: {\n ...inheritedTheme.highlightConfig,\n ...localTheme.highlightConfig,\n colors: {\n ...inheritedTheme.highlightConfig?.colors,\n ...localTheme.highlightConfig?.colors,\n },\n },\n screenshotConfig: {\n ...inheritedTheme.screenshotConfig,\n ...localTheme.screenshotConfig,\n },\n }),\n [inheritedTheme, localTheme],\n );\n\n // Apply merged theme styles\n const effectiveMenuStyle = mergedTheme.menuStyle ?? menuStyle;\n const effectiveMenuClassName = mergedTheme.menuClassName ?? menuClassName;\n const effectiveHighlightConfig =\n mergedTheme.highlightConfig ?? highlightConfig;\n const effectiveScreenshotConfig =\n mergedTheme.screenshotConfig ?? screenshotConfig;\n\n // Context value\n const contextValue: AnyclickContextValue = useMemo(\n () => ({\n closeMenu,\n isEnabled: !effectiveDisabled && !isDisabledByAncestor(providerId),\n isSubmitting,\n openMenu,\n providerId,\n scoped,\n submitAnyclick,\n theme: mergedTheme,\n }),\n [\n closeMenu,\n effectiveDisabled,\n isDisabledByAncestor,\n isSubmitting,\n mergedTheme,\n openMenu,\n providerId,\n scoped,\n submitAnyclick,\n ],\n );\n\n // For scoped providers, wrap children in a container div\n const content = scoped ? (\n <div\n ref={setContainerRef}\n data-anyclick-provider={providerId}\n style={{ display: \"contents\" }}\n >\n {children}\n </div>\n ) : (\n children\n );\n\n return (\n <AnyclickContext.Provider value={contextValue}>\n <div data-anyclick-root>\n {content}\n <ContextMenu\n className={effectiveMenuClassName}\n containerElement={containerElement}\n header={header}\n highlightConfig={effectiveHighlightConfig}\n isSubmitting={isSubmitting}\n items={menuItems}\n onClose={closeMenu}\n onSelect={handleMenuSelect}\n position={menuPosition}\n quickChatConfig={quickChatConfig}\n screenshotConfig={effectiveScreenshotConfig}\n style={effectiveMenuStyle}\n targetElement={targetElement}\n visible={menuVisible && !effectiveDisabled}\n />\n </div>\n </AnyclickContext.Provider>\n );\n}\n\n/**\n * @deprecated Use {@link AnyclickProvider} instead. Will be removed in v2.0.0.\n */\nexport const FeedbackProvider = AnyclickProvider;\n","\"use client\";\n\nimport React, { useCallback, useEffect, useRef, useState } from \"react\";\nimport type { AnyclickType, ScreenshotData } from \"@ewjdev/anyclick-core\";\nimport {\n DEFAULT_SCREENSHOT_CONFIG,\n captureAllScreenshots,\n isScreenshotSupported,\n} from \"@ewjdev/anyclick-core\";\nimport {\n CameraIcon,\n ChevronLeftIcon,\n ChevronRightIcon,\n FlagIcon,\n GripVertical,\n PlusIcon,\n Sparkles,\n ThumbsUpIcon,\n} from \"lucide-react\";\nimport { QuickChat } from \"./QuickChat\";\nimport { ScreenshotPreview } from \"./ScreenshotPreview\";\nimport { applyHighlights, clearHighlights } from \"./highlight\";\nimport { getBadgeStyle, menuStyles } from \"./styles\";\nimport type { ContextMenuItem, ContextMenuProps } from \"./types\";\n\n/** Padding from viewport edges in pixels */\nconst VIEWPORT_PADDING = 10;\n\n/**\n * Default icons for feedback types\n */\nconst defaultIcons: Record<string, React.ReactNode> = {\n feature: <PlusIcon className=\"w-4 h-4\" />,\n issue: <FlagIcon className=\"w-4 h-4\" />,\n like: <ThumbsUpIcon className=\"w-4 h-4\" />,\n};\n\nconst OFFSCREEN_POSITION = { x: -9999, y: -9999 };\n\n/**\n * Default header component for the context menu.\n */\nconst DefaultHeader = ({\n children,\n className,\n styles,\n title = \"Send Feedback\",\n}: {\n children?: React.ReactNode;\n className?: string;\n styles?: React.CSSProperties;\n title?: string;\n}) => {\n return (\n <div style={styles} className={className}>\n <span>{title}</span>\n {children}\n </div>\n );\n};\n\n/**\n * Menu item component with touch-friendly sizing.\n */\nconst MenuItem = React.memo(function MenuItem({\n disabled,\n hasChildren,\n item,\n onClick,\n}: {\n disabled: boolean;\n hasChildren?: boolean;\n item: ContextMenuItem;\n onClick: () => void;\n}) {\n const [isHovered, setIsHovered] = useState(false);\n const [isPressed, setIsPressed] = useState(false);\n const isComingSoon = item.status === \"comingSoon\";\n const badgeLabel = item.badge?.label ?? (isComingSoon ? \"Coming soon\" : null);\n const badgeTone = item.badge?.tone ?? (isComingSoon ? \"neutral\" : \"neutral\");\n\n const badgeStyle = badgeLabel ? getBadgeStyle(badgeTone) : undefined;\n const iconNode = item.icon ?? defaultIcons[item.type];\n\n return (\n <button\n type=\"button\"\n disabled={disabled || isComingSoon}\n onClick={onClick}\n onMouseEnter={() => setIsHovered(true)}\n onMouseLeave={() => {\n setIsHovered(false);\n setIsPressed(false);\n }}\n onTouchCancel={() => setIsPressed(false)}\n onTouchEnd={() => setIsPressed(false)}\n onTouchStart={() => setIsPressed(true)}\n style={{\n ...menuStyles.touchFriendly,\n ...menuStyles.item,\n ...(isHovered || isPressed ? menuStyles.itemHover : {}),\n ...(disabled ? menuStyles.itemDisabled : {}),\n }}\n >\n {iconNode ? <span style={menuStyles.itemIcon}>{iconNode}</span> : null}\n <span style={menuStyles.itemLabel}>\n {item.label}\n {badgeLabel && <span style={badgeStyle}>{badgeLabel}</span>}\n </span>\n {hasChildren && (\n <ChevronRightIcon className=\"w-4 h-4\" style={menuStyles.submenuIcon} />\n )}\n </button>\n );\n});\n\n/**\n * Back button for submenu navigation with touch-friendly sizing.\n */\nconst BackButton = React.memo(function BackButton({\n onClick,\n}: {\n onClick: () => void;\n}) {\n const [isHovered, setIsHovered] = useState(false);\n const [isPressed, setIsPressed] = useState(false);\n\n return (\n <button\n type=\"button\"\n onClick={onClick}\n onMouseEnter={() => setIsHovered(true)}\n onMouseLeave={() => {\n setIsHovered(false);\n setIsPressed(false);\n }}\n onTouchCancel={() => setIsPressed(false)}\n onTouchEnd={() => setIsPressed(false)}\n onTouchStart={() => setIsPressed(true)}\n style={{\n ...menuStyles.item,\n ...menuStyles.backButton,\n ...menuStyles.touchFriendly,\n ...(isHovered || isPressed ? menuStyles.itemHover : {}),\n }}\n >\n <ChevronLeftIcon className=\"w-4 h-4\" style={{ opacity: 0.5 }} />\n <span style={{ opacity: 0.7 }}>Back</span>\n </button>\n );\n});\n\n/**\n * Comment form component.\n */\nconst CommentForm = React.memo(function CommentForm({\n isSubmitting,\n onCancel,\n onSubmit,\n}: {\n isSubmitting: boolean;\n onCancel: () => void;\n onSubmit: (comment: string) => void;\n}) {\n const [comment, setComment] = useState(\"\");\n const inputRef = useRef<HTMLTextAreaElement>(null);\n\n useEffect(() => {\n inputRef.current?.focus();\n }, []);\n\n const handleSubmit = useCallback(() => {\n onSubmit(comment);\n }, [comment, onSubmit]);\n\n const handleKeyDown = useCallback(\n (e: React.KeyboardEvent) => {\n if (e.key === \"Enter\" && (e.metaKey || e.ctrlKey)) {\n handleSubmit();\n } else if (e.key === \"Escape\") {\n onCancel();\n }\n },\n [handleSubmit, onCancel],\n );\n\n return (\n <div style={menuStyles.commentSection}>\n <textarea\n ref={inputRef}\n disabled={isSubmitting}\n onChange={(e) => setComment(e.target.value)}\n onKeyDown={handleKeyDown}\n placeholder=\"Add a comment (optional)...\"\n style={menuStyles.commentInput}\n value={comment}\n />\n <div style={menuStyles.buttonRow}>\n <button\n type=\"button\"\n disabled={isSubmitting}\n onClick={onCancel}\n style={{ ...menuStyles.button, ...menuStyles.cancelButton }}\n >\n Cancel\n </button>\n <button\n type=\"button\"\n disabled={isSubmitting}\n onClick={handleSubmit}\n style={{\n ...menuStyles.button,\n ...menuStyles.submitButton,\n ...(isSubmitting ? menuStyles.submitButtonDisabled : {}),\n }}\n >\n {isSubmitting ? \"Sending...\" : \"Send\"}\n </button>\n </div>\n </div>\n );\n});\n\n/** View states for the context menu */\ntype MenuView = \"comment\" | \"menu\" | \"screenshot-preview\" | \"quick-chat\";\n\n/**\n * Calculate adjusted position to keep menu in viewport.\n */\nfunction calculateInViewPosition(\n requestedX: number,\n requestedY: number,\n menuWidth: number,\n menuHeight: number,\n): { x: number; y: number } {\n const viewportHeight = window.innerHeight;\n const viewportWidth = window.innerWidth;\n\n let x = requestedX;\n let y = requestedY;\n\n // Adjust X if menu would go off the right edge\n if (x + menuWidth > viewportWidth - VIEWPORT_PADDING) {\n x = viewportWidth - menuWidth - VIEWPORT_PADDING;\n }\n // Ensure X doesn't go off the left edge\n if (x < VIEWPORT_PADDING) {\n x = VIEWPORT_PADDING;\n }\n\n // Adjust Y if menu would go off the bottom edge\n if (y + menuHeight > viewportHeight - VIEWPORT_PADDING) {\n y = viewportHeight - menuHeight - VIEWPORT_PADDING;\n }\n // Ensure Y doesn't go off the top edge\n if (y < VIEWPORT_PADDING) {\n y = VIEWPORT_PADDING;\n }\n\n return { x, y };\n}\n\n/**\n * Context menu component for selecting feedback type.\n *\n * Displays a customizable context menu with support for:\n * - Custom menu items with icons and badges\n * - Submenus for organizing options\n * - Comment input for detailed feedback\n * - Screenshot preview before sending\n * - Touch-friendly interactions\n * - Dynamic positioning modes\n *\n * @since 1.0.0\n */\nexport function ContextMenu({\n className,\n containerElement,\n footer,\n header,\n highlightConfig,\n isSubmitting,\n items,\n onClose,\n onSelect,\n position,\n positionMode = \"inView\",\n quickChatConfig,\n screenshotConfig,\n style,\n targetElement,\n visible,\n}: ContextMenuProps) {\n const [selectedType, setSelectedType] = useState<AnyclickType | null>(null);\n const [currentView, setCurrentView] = useState<MenuView>(\"menu\");\n const [pendingComment, setPendingComment] = useState<string | undefined>();\n const [submenuStack, setSubmenuStack] = useState<ContextMenuItem[][]>([]);\n const [screenshots, setScreenshots] = useState<ScreenshotData | null>(null);\n const [isCapturing, setIsCapturing] = useState(false);\n // Initialize pinned state from session storage\n const [isQuickChatPinned, setIsQuickChatPinned] = useState(() => {\n if (typeof window === \"undefined\") return false;\n try {\n return sessionStorage.getItem(\"anyclick-quick-chat-pinned\") === \"true\";\n } catch {\n return false;\n }\n });\n const menuRef = useRef<HTMLDivElement>(null);\n\n // Position state for different modes\n const [adjustedPosition, setAdjustedPosition] = useState<{\n x: number;\n y: number;\n }>(OFFSCREEN_POSITION);\n const [isDragging, setIsDragging] = useState(false);\n const [dragOffset, setDragOffset] = useState<{ x: number; y: number }>({\n x: 0,\n y: 0,\n });\n const dragStartRef = useRef<{ x: number; y: number } | null>(null);\n\n // Merge screenshot config with defaults\n const mergedScreenshotConfig = React.useMemo(\n () => ({\n ...DEFAULT_SCREENSHOT_CONFIG,\n ...screenshotConfig,\n }),\n [screenshotConfig],\n );\n\n const showPreview =\n mergedScreenshotConfig.showPreview && isScreenshotSupported();\n\n // Current items to display (either root items or submenu items)\n const currentItems =\n submenuStack.length > 0 ? submenuStack[submenuStack.length - 1] : items;\n\n // Capture screenshots\n const captureScreenshots = useCallback(async () => {\n if (!targetElement || !showPreview) return;\n\n setIsCapturing(true);\n try {\n const captured = await captureAllScreenshots(\n targetElement,\n containerElement,\n mergedScreenshotConfig,\n );\n setScreenshots(captured);\n } catch (error) {\n console.error(\"Failed to capture screenshots:\", error);\n setScreenshots(null);\n } finally {\n setIsCapturing(false);\n }\n }, [containerElement, mergedScreenshotConfig, showPreview, targetElement]);\n\n // Reset state when menu closes\n useEffect(() => {\n if (!visible) {\n setSelectedType(null);\n // Always reset to menu view when closing (pinned chat stays open separately)\n setCurrentView(\"menu\");\n setPendingComment(undefined);\n setSubmenuStack([]);\n setScreenshots(null);\n setIsCapturing(false);\n setIsDragging(false);\n setDragOffset({ x: 0, y: 0 });\n setAdjustedPosition(OFFSCREEN_POSITION);\n dragStartRef.current = null;\n }\n }, [visible]);\n\n // Apply highlights to target element and container when menu opens\n useEffect(() => {\n if (visible && targetElement) {\n clearHighlights();\n applyHighlights(targetElement, highlightConfig);\n } else {\n clearHighlights();\n }\n\n return () => {\n clearHighlights();\n };\n }, [highlightConfig, targetElement, visible]);\n\n // Close menu when clicking outside of it\n useEffect(() => {\n if (!visible) {\n return;\n }\n\n const handlePointerDown = (event: PointerEvent) => {\n if (!menuRef.current) return;\n\n const target = event.target as Node;\n if ((target as HTMLElement).closest?.(\"[data-drag-handle]\")) {\n return;\n }\n if (!menuRef.current.contains(target)) {\n onClose();\n }\n };\n\n document.addEventListener(\"pointerdown\", handlePointerDown);\n return () => {\n document.removeEventListener(\"pointerdown\", handlePointerDown);\n };\n }, [onClose, visible]);\n\n // Reset adjusted position when menu opens at new position\n useEffect(() => {\n if (visible) {\n setAdjustedPosition(position);\n setDragOffset({ x: 0, y: 0 });\n }\n }, [position.x, position.y, visible]);\n\n // Calculate and apply position based on mode\n useEffect(() => {\n if (!visible || !menuRef.current) return;\n\n const updatePosition = () => {\n const menuElement = menuRef.current;\n if (!menuElement) return;\n\n const rect = menuElement.getBoundingClientRect();\n const baseX = position.x + dragOffset.x;\n const baseY = position.y + dragOffset.y;\n\n if (positionMode === \"static\") {\n setAdjustedPosition({ x: baseX, y: baseY });\n } else if (positionMode === \"inView\" || positionMode === \"dynamic\") {\n const adjusted = calculateInViewPosition(\n baseX,\n baseY,\n rect.width,\n rect.height,\n );\n setAdjustedPosition(adjusted);\n }\n };\n\n requestAnimationFrame(updatePosition);\n\n window.addEventListener(\"resize\", updatePosition);\n return () => window.removeEventListener(\"resize\", updatePosition);\n }, [currentView, dragOffset, position, positionMode, visible]);\n\n // Dragging logic for dynamic mode\n useEffect(() => {\n if (!visible || positionMode !== \"dynamic\") return;\n\n const handlePointerMove = (event: PointerEvent) => {\n if (!isDragging || !dragStartRef.current) return;\n\n const deltaX = event.clientX - dragStartRef.current.x;\n const deltaY = event.clientY - dragStartRef.current.y;\n\n setDragOffset((prev) => ({\n x: prev.x + deltaX,\n y: prev.y + deltaY,\n }));\n\n dragStartRef.current = { x: event.clientX, y: event.clientY };\n };\n\n const handlePointerUp = () => {\n setIsDragging(false);\n dragStartRef.current = null;\n };\n\n if (isDragging) {\n document.addEventListener(\"pointermove\", handlePointerMove);\n document.addEventListener(\"pointerup\", handlePointerUp);\n document.addEventListener(\"pointercancel\", handlePointerUp);\n\n return () => {\n document.removeEventListener(\"pointermove\", handlePointerMove);\n document.removeEventListener(\"pointerup\", handlePointerUp);\n document.removeEventListener(\"pointercancel\", handlePointerUp);\n };\n }\n }, [isDragging, positionMode, visible]);\n\n // Handle drag start\n const handleDragStart = useCallback(\n (event: React.PointerEvent) => {\n if (positionMode !== \"dynamic\") return;\n event.preventDefault();\n setIsDragging(true);\n dragStartRef.current = { x: event.clientX, y: event.clientY };\n },\n [positionMode],\n );\n\n // Track initial input for type-to-chat feature\n const [initialChatInput, setInitialChatInput] = useState<string>(\"\");\n\n // Handle keyboard input - escape and type-to-chat\n useEffect(() => {\n const handleKeyDown = (e: KeyboardEvent) => {\n // Handle escape key\n if (e.key === \"Escape\") {\n if (currentView === \"screenshot-preview\") {\n setCurrentView(\"comment\");\n } else if (currentView === \"comment\") {\n setCurrentView(\"menu\");\n setSelectedType(null);\n setPendingComment(undefined);\n } else if (currentView === \"quick-chat\") {\n if (!isQuickChatPinned) {\n setCurrentView(\"menu\");\n }\n } else if (submenuStack.length > 0) {\n setSubmenuStack((prev) => prev.slice(0, -1));\n } else {\n onClose();\n }\n return;\n }\n\n // Type-to-chat: when in menu view and quickChat is enabled,\n // start typing to open chat\n if (\n quickChatConfig &&\n currentView === \"menu\" &&\n !isQuickChatPinned &&\n !e.ctrlKey &&\n !e.metaKey &&\n !e.altKey\n ) {\n // Check if it's a printable character (single character keys)\n if (e.key.length === 1 && e.key.match(/[a-zA-Z0-9\\s.,!?'\"]/)) {\n e.preventDefault();\n setInitialChatInput(e.key);\n setCurrentView(\"quick-chat\");\n }\n }\n };\n\n if (visible) {\n document.addEventListener(\"keydown\", handleKeyDown);\n return () => document.removeEventListener(\"keydown\", handleKeyDown);\n }\n }, [\n currentView,\n isQuickChatPinned,\n onClose,\n quickChatConfig,\n submenuStack.length,\n visible,\n ]);\n\n // Prevent touch default behaviors on menu container\n useEffect(() => {\n const menuElement = menuRef.current;\n if (!visible || !menuElement) return;\n\n const preventTouchDefault = (e: TouchEvent) => {\n const target = e.target as HTMLElement;\n if (\n target.tagName === \"TEXTAREA\" ||\n target.tagName === \"INPUT\" ||\n target.isContentEditable\n ) {\n return;\n }\n e.preventDefault();\n };\n\n menuElement.addEventListener(\"touchmove\", preventTouchDefault, {\n passive: false,\n });\n\n return () => {\n menuElement.removeEventListener(\"touchmove\", preventTouchDefault);\n };\n }, [visible]);\n\n const handleItemClick = (item: ContextMenuItem) => {\n if (item.status === \"comingSoon\") {\n return;\n }\n\n if (item.children && item.children.length > 0) {\n setSubmenuStack((prev) => [...prev, item.children!]);\n return;\n }\n\n if (item.onClick) {\n try {\n return item.onClick({\n closeMenu: onClose,\n containerElement,\n targetElement,\n });\n } catch (error) {\n console.error(\"Anyclick menu onClick error:\", error);\n return;\n }\n }\n\n if (item.showComment) {\n setSelectedType(item.type);\n setCurrentView(\"comment\");\n } else {\n if (showPreview) {\n setSelectedType(item.type);\n setCurrentView(\"screenshot-preview\");\n captureScreenshots();\n } else {\n onSelect(item.type);\n }\n }\n };\n\n const handleBack = () => {\n setSubmenuStack((prev) => prev.slice(0, -1));\n };\n\n const handleCommentSubmit = (comment: string) => {\n if (!selectedType) return;\n\n if (showPreview) {\n setPendingComment(comment || undefined);\n setCurrentView(\"screenshot-preview\");\n captureScreenshots();\n } else {\n onSelect(selectedType, comment || undefined);\n }\n };\n\n const handleCommentCancel = () => {\n setCurrentView(\"menu\");\n setSelectedType(null);\n setPendingComment(undefined);\n };\n\n const handleScreenshotConfirm = (confirmedScreenshots: ScreenshotData) => {\n if (selectedType) {\n onSelect(selectedType, pendingComment, confirmedScreenshots);\n }\n };\n\n const handleScreenshotCancel = () => {\n if (pendingComment !== undefined) {\n setCurrentView(\"comment\");\n } else {\n setCurrentView(\"menu\");\n setSelectedType(null);\n }\n setScreenshots(null);\n };\n\n const handleRetakeScreenshots = () => {\n captureScreenshots();\n };\n\n const handleQuickChatToggle = () => {\n if (currentView === \"quick-chat\" && !isQuickChatPinned) {\n setCurrentView(\"menu\");\n } else {\n setCurrentView(\"quick-chat\");\n }\n };\n\n const handleQuickChatPin = (pinned: boolean) => {\n setIsQuickChatPinned(pinned);\n // Sync to session storage\n try {\n if (pinned) {\n sessionStorage.setItem(\"anyclick-quick-chat-pinned\", \"true\");\n } else {\n sessionStorage.removeItem(\"anyclick-quick-chat-pinned\");\n }\n } catch {\n // Ignore storage errors\n }\n // When pinning, go back to menu view so context menu keeps working\n if (pinned) {\n setCurrentView(\"menu\");\n }\n };\n\n const handleQuickChatClose = () => {\n setIsQuickChatPinned(false);\n try {\n sessionStorage.removeItem(\"anyclick-quick-chat-pinned\");\n } catch {\n // Ignore storage errors\n }\n setCurrentView(\"menu\");\n };\n\n const containerWidth =\n currentView === \"screenshot-preview\"\n ? 360\n : currentView === \"quick-chat\" && !isQuickChatPinned\n ? 320\n : undefined;\n\n // Show pinned QuickChat drawer (separate from menu)\n const showPinnedDrawer = isQuickChatPinned && quickChatConfig;\n const showMenu = visible && targetElement;\n\n return (\n <>\n {/* Pinned QuickChat drawer - anchored to right side, independent of menu */}\n {showPinnedDrawer && (\n <QuickChat\n visible={true}\n targetElement={targetElement}\n containerElement={containerElement}\n onClose={handleQuickChatClose}\n onPin={handleQuickChatPin}\n isPinned={true}\n config={quickChatConfig}\n />\n )}\n\n {/* Context menu - only visible when menu is open */}\n {showMenu && (\n <div\n ref={menuRef}\n aria-label=\"Feedback options\"\n className={className}\n role=\"menu\"\n style={{\n ...menuStyles.container,\n left: adjustedPosition.x,\n top: adjustedPosition.y,\n ...(containerWidth\n ? { minWidth: containerWidth, width: containerWidth }\n : {}),\n touchAction: \"none\",\n userSelect: \"none\",\n WebkitTouchCallout: \"none\",\n WebkitUserSelect: \"none\",\n ...(isDragging ? { cursor: \"grabbing\" } : {}),\n ...style,\n }}\n >\n {!header &&\n currentView !== \"screenshot-preview\" &&\n currentView !== \"quick-chat\" && (\n <DefaultHeader styles={menuStyles.header} title=\"Send Feedback\">\n {positionMode === \"dynamic\" && (\n <div\n data-drag-handle\n onMouseEnter={(e) => {\n (e.currentTarget as HTMLElement).style.opacity = \"1\";\n }}\n onMouseLeave={(e) => {\n (e.currentTarget as HTMLElement).style.opacity = \"0.5\";\n }}\n onPointerDown={handleDragStart}\n style={{\n ...menuStyles.dragHandle,\n cursor: isDragging ? \"grabbing\" : \"grab\",\n }}\n title=\"Drag to move\"\n >\n <GripVertical className=\"w-4 h-4\" />\n </div>\n )}\n {showPreview && (\n <div style={menuStyles.screenshotIndicator}>\n <CameraIcon className=\"w-3 h-3\" />\n </div>\n )}\n {quickChatConfig && (\n <button\n type=\"button\"\n onClick={handleQuickChatToggle}\n style={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n width: \"24px\",\n height: \"24px\",\n border: \"none\",\n borderRadius: \"4px\",\n backgroundColor: isQuickChatPinned\n ? \"var(--anyclick-menu-accent, #0066cc)\"\n : \"transparent\",\n color: isQuickChatPinned\n ? \"#fff\"\n : \"var(--anyclick-menu-accent, #0066cc)\",\n cursor: \"pointer\",\n transition: \"all 0.15s ease\",\n }}\n title={\n isQuickChatPinned ? \"Quick Chat (pinned)\" : \"Quick Ask AI\"\n }\n >\n <Sparkles className=\"w-3.5 h-3.5\" />\n </button>\n )}\n </DefaultHeader>\n )}\n {!!header && header}\n\n {currentView === \"menu\" && (\n <div style={menuStyles.itemList}>\n {submenuStack.length > 0 && <BackButton onClick={handleBack} />}\n {currentItems.map((item) => (\n <MenuItem\n key={item.type}\n disabled={isSubmitting}\n hasChildren={item.children && item.children.length > 0}\n item={item}\n onClick={() => handleItemClick(item)}\n />\n ))}\n </div>\n )}\n\n {currentView === \"comment\" && (\n <CommentForm\n isSubmitting={isSubmitting}\n onCancel={handleCommentCancel}\n onSubmit={handleCommentSubmit}\n />\n )}\n\n {currentView === \"screenshot-preview\" && (\n <ScreenshotPreview\n isLoading={isCapturing}\n isSubmitting={isSubmitting}\n onCancel={handleScreenshotCancel}\n onConfirm={handleScreenshotConfirm}\n onRetake={handleRetakeScreenshots}\n screenshots={screenshots}\n />\n )}\n\n {/* Inline QuickChat - inside menu when not pinned */}\n {currentView === \"quick-chat\" &&\n quickChatConfig &&\n !isQuickChatPinned && (\n <QuickChat\n visible={true}\n targetElement={targetElement}\n containerElement={containerElement}\n onClose={handleQuickChatClose}\n onPin={handleQuickChatPin}\n isPinned={false}\n config={quickChatConfig}\n initialInput={initialChatInput}\n onInitialInputConsumed={() => setInitialChatInput(\"\")}\n />\n )}\n </div>\n )}\n </>\n );\n}\n","/**\n * QuickChat component - Lightweight AI chat in the context menu.\n *\n * Provides a minimal chat interface that auto-focuses when opened,\n * streams AI responses using ai-sdk-ui, and offers quick actions.\n * Chat history persists for 24h via zustand store.\n *\n * @module QuickChat/QuickChat\n * @since 3.1.0\n */\n\"use client\";\n\nimport React, {\n useCallback,\n useEffect,\n useMemo,\n useRef,\n useState,\n} from \"react\";\nimport { buildAnyclickPayload } from \"@ewjdev/anyclick-core\";\nimport {\n AlertCircle,\n ChevronDown,\n ChevronLeft,\n ChevronUp,\n Copy,\n ExternalLink,\n Pin,\n PinOff,\n RefreshCw,\n Send,\n X,\n} from \"lucide-react\";\nimport { quickChatKeyframes, quickChatStyles } from \"./styles\";\nimport type { QuickChatProps } from \"./types\";\nimport { useQuickChat } from \"./useQuickChat\";\n\n/**\n * Injects keyframe animations into the document.\n */\nlet stylesInjected = false;\nfunction injectStyles() {\n if (stylesInjected || typeof document === \"undefined\") return;\n const style = document.createElement(\"style\");\n style.textContent = quickChatKeyframes;\n document.head.appendChild(style);\n stylesInjected = true;\n}\n\n/**\n * Loading dots component.\n */\nconst LoadingDots = React.memo(function LoadingDots() {\n return (\n <div style={quickChatStyles.loadingDots}>\n {[0, 1, 2].map((i) => (\n <div\n key={i}\n style={{\n ...quickChatStyles.loadingDot,\n animationDelay: `${i * 0.16}s`,\n }}\n />\n ))}\n </div>\n );\n});\n\n/**\n * QuickChat component.\n */\nexport function QuickChat({\n visible,\n targetElement,\n containerElement,\n onClose,\n onPin,\n isPinned: isPinnedProp = false,\n config,\n style,\n className,\n initialInput,\n onInitialInputConsumed,\n}: QuickChatProps) {\n const inputRef = useRef<HTMLTextAreaElement>(null);\n const messagesEndRef = useRef<HTMLDivElement>(null);\n const [inputFocused, setInputFocused] = useState(false);\n const [showContext, setShowContext] = useState(false);\n const [hoveredSuggestion, setHoveredSuggestion] = useState<string | null>(\n null,\n );\n\n const {\n input,\n messages,\n isLoadingSuggestions,\n isSending,\n isStreaming,\n debugInfo,\n rateLimitNotice,\n suggestedPrompts,\n contextChunks,\n error,\n isPinned: storePinned,\n setInput,\n toggleChunk,\n toggleAllChunks,\n selectSuggestion,\n sendMessage,\n clearMessages,\n setIsPinned,\n clearRateLimitNotice,\n config: mergedConfig,\n } = useQuickChat(targetElement, containerElement, config);\n\n // Use prop or store pinned state\n const isPinned = isPinnedProp || storePinned;\n\n // Sync pinned state with store\n const handlePinToggle = useCallback(() => {\n const newPinned = !isPinned;\n setIsPinned(newPinned);\n onPin?.(newPinned);\n }, [isPinned, setIsPinned, onPin]);\n\n // Handle close - if pinned, just unpin; otherwise close\n const handleClose = useCallback(() => {\n if (isPinned) {\n setIsPinned(false);\n onPin?.(false);\n }\n onClose();\n }, [isPinned, setIsPinned, onPin, onClose]);\n\n // Inject styles on mount\n useEffect(() => {\n injectStyles();\n }, []);\n\n // Auto-focus input when visible\n useEffect(() => {\n if (visible && inputRef.current) {\n const timer = setTimeout(() => {\n inputRef.current?.focus();\n }, 100);\n return () => clearTimeout(timer);\n }\n }, [visible]);\n\n // Handle initial input from type-to-chat\n useEffect(() => {\n if (initialInput && visible) {\n setInput(initialInput);\n onInitialInputConsumed?.();\n // Focus and place cursor at end\n if (inputRef.current) {\n inputRef.current.focus();\n inputRef.current.setSelectionRange(\n initialInput.length,\n initialInput.length,\n );\n }\n }\n }, [initialInput, visible, setInput, onInitialInputConsumed]);\n\n // Scroll to bottom when messages change\n useEffect(() => {\n if (messagesEndRef.current) {\n messagesEndRef.current.scrollIntoView({ behavior: \"smooth\" });\n }\n }, [messages]);\n\n // Handle input change\n const handleInputChange = useCallback(\n (e: React.ChangeEvent<HTMLTextAreaElement>) => {\n setInput(e.target.value);\n // Auto-resize textarea\n const target = e.target;\n target.style.height = \"auto\";\n target.style.height = `${Math.min(target.scrollHeight, 80)}px`;\n },\n [setInput],\n );\n\n // Handle key down\n const handleKeyDown = useCallback(\n (e: React.KeyboardEvent) => {\n if (e.key === \"Enter\" && !e.shiftKey) {\n e.preventDefault();\n sendMessage();\n } else if (e.key === \"Escape\") {\n onClose();\n }\n },\n [sendMessage, onClose],\n );\n\n // Handle send click\n const handleSend = useCallback(() => {\n sendMessage();\n }, [sendMessage]);\n\n // Handle send to t3.chat\n const handleSendToT3Chat = useCallback(() => {\n if (typeof window === \"undefined\") return;\n const query = input.trim();\n const baseUrl = mergedConfig.t3chat?.baseUrl ?? \"https://t3.chat\";\n const url = query ? `${baseUrl}/?q=${encodeURIComponent(query)}` : baseUrl;\n window.open(url, \"_blank\", \"noopener,noreferrer\");\n }, [input, mergedConfig.t3chat?.baseUrl]);\n\n // Handle copy to clipboard\n const handleCopy = useCallback((text: string) => {\n navigator.clipboard.writeText(text);\n }, []);\n\n // Compute included context count\n const includedCount = useMemo(\n () => contextChunks.filter((c) => c.included).length,\n [contextChunks],\n );\n\n const [rateLimitExpanded, setRateLimitExpanded] = useState(false);\n const [reportStatus, setReportStatus] = useState<\n \"idle\" | \"sending\" | \"sent\" | \"error\"\n >(\"idle\");\n const [reportUrl, setReportUrl] = useState<string | null>(null);\n const [reportError, setReportError] = useState<string | null>(null);\n\n // If a new rate-limit notice appears, reset report UI\n useEffect(() => {\n if (rateLimitNotice) {\n setReportStatus(\"idle\");\n setReportUrl(null);\n setReportError(null);\n setRateLimitExpanded(false);\n }\n }, [rateLimitNotice]);\n\n const handleReportIssue = useCallback(async () => {\n if (!rateLimitNotice) return;\n if (!targetElement) {\n setReportStatus(\"error\");\n setReportError(\"No target element available to report.\");\n return;\n }\n\n setReportStatus(\"sending\");\n setReportError(null);\n\n try {\n const payload = buildAnyclickPayload(targetElement, \"issue\", {\n comment: `QuickChat: ${rateLimitNotice.message}`,\n metadata: {\n source: \"quickchat\",\n kind: \"rate_limit\",\n endpoint: rateLimitNotice.endpoint ?? mergedConfig.endpoint,\n retryAt: rateLimitNotice.retryAt,\n retryAfterSeconds: rateLimitNotice.retryAfterSeconds,\n requestId: rateLimitNotice.requestId,\n debugInfo: debugInfo ?? undefined,\n raw: rateLimitNotice.raw ?? undefined,\n },\n });\n\n const res = await fetch(\"/api/feedback\", {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify(payload),\n });\n\n const json = (await res.json().catch(() => null)) as {\n success?: boolean;\n results?: Array<{ adapter: string; url?: string }>;\n partialFailures?: Array<{ adapter: string; error?: string }>;\n error?: string;\n } | null;\n\n if (!res.ok || !json?.success) {\n const msg =\n json?.error ||\n (res.status\n ? `Failed to create issue (${res.status}).`\n : \"Failed to create issue.\");\n throw new Error(msg);\n }\n\n const firstUrl = json.results?.find(\n (r) => typeof r.url === \"string\",\n )?.url;\n setReportUrl(firstUrl ?? null);\n setReportStatus(\"sent\");\n } catch (e) {\n setReportStatus(\"error\");\n setReportError(e instanceof Error ? e.message : String(e));\n }\n }, [rateLimitNotice, targetElement, mergedConfig.endpoint, debugInfo]);\n\n if (!visible) return null;\n\n // Use different styles based on pinned state\n const containerStyles = isPinned\n ? {\n ...quickChatStyles.pinnedContainer,\n animation: \"slideInFromRight 0.25s ease-out\",\n ...style,\n }\n : {\n ...quickChatStyles.container,\n animation: \"fadeIn 0.15s ease-out\",\n ...style,\n };\n\n return (\n <div className={className} style={containerStyles}>\n {/* Header with context badge */}\n <div\n style={{\n ...quickChatStyles.header,\n padding: isPinned ? \"12px 12px 8px 12px\" : \"6px 8px\",\n }}\n >\n <div style={{ display: \"flex\", alignItems: \"center\", gap: \"4px\" }}>\n {!isPinned && (\n <button\n type=\"button\"\n onClick={onClose}\n style={{\n ...quickChatStyles.iconButton,\n marginLeft: \"-4px\",\n }}\n title=\"Back to menu\"\n >\n <ChevronLeft size={16} />\n </button>\n )}\n {/* Context badge */}\n {mergedConfig.showRedactionUI && contextChunks.length > 0 && (\n <>\n <button\n type=\"button\"\n onClick={() => setShowContext(!showContext)}\n style={{\n ...quickChatStyles.contextBadge,\n ...(showContext ? quickChatStyles.contextBadgeActive : {}),\n }}\n title=\"Edit context\"\n >\n <span>\n {includedCount}/{contextChunks.length}\n </span>\n {showContext ? (\n <ChevronUp size={10} />\n ) : (\n <ChevronDown size={10} />\n )}\n </button>\n {/* All/None toggles when dropdown is open */}\n {showContext && (\n <div style={{ display: \"flex\", gap: \"2px\" }}>\n <button\n type=\"button\"\n onClick={() => toggleAllChunks(true)}\n style={quickChatStyles.contextToggleSmall}\n title=\"Include all\"\n >\n All\n </button>\n <button\n type=\"button\"\n onClick={() => toggleAllChunks(false)}\n style={quickChatStyles.contextToggleSmall}\n title=\"Exclude all\"\n >\n None\n </button>\n </div>\n )}\n </>\n )}\n </div>\n <div style={quickChatStyles.headerActions}>\n {messages.length > 0 && (\n <button\n type=\"button\"\n onClick={clearMessages}\n style={quickChatStyles.iconButton}\n title=\"Clear chat\"\n >\n <RefreshCw size={14} />\n </button>\n )}\n <button\n type=\"button\"\n onClick={handlePinToggle}\n style={{\n ...quickChatStyles.iconButton,\n ...(isPinned ? quickChatStyles.iconButtonActive : {}),\n }}\n title={isPinned ? \"Unpin (closes with menu)\" : \"Pin (stays open)\"}\n >\n {isPinned ? <PinOff size={14} /> : <Pin size={14} />}\n </button>\n <button\n type=\"button\"\n onClick={handleClose}\n style={quickChatStyles.iconButton}\n title=\"Close\"\n >\n <X size={14} />\n </button>\n </div>\n </div>\n\n {/* Context dropdown - compact list */}\n {showContext && contextChunks.length > 0 && (\n <div style={quickChatStyles.contextDropdown}>\n {contextChunks.map((chunk) => (\n <label\n key={chunk.id}\n style={{\n ...quickChatStyles.contextChunkCompact,\n ...(chunk.included ? {} : quickChatStyles.contextChunkExcluded),\n }}\n >\n <input\n type=\"checkbox\"\n checked={chunk.included}\n onChange={() => toggleChunk(chunk.id)}\n style={quickChatStyles.contextCheckbox}\n />\n <span style={quickChatStyles.contextLabel}>{chunk.label}</span>\n </label>\n ))}\n </div>\n )}\n\n {/* Suggested prompts */}\n {mergedConfig.showSuggestions &&\n messages.length === 0 &&\n suggestedPrompts.length > 0 && (\n <div style={quickChatStyles.suggestionsContainer}>\n {isLoadingSuggestions ? (\n <LoadingDots />\n ) : (\n suggestedPrompts.map((prompt) => (\n <button\n key={prompt.id}\n type=\"button\"\n onClick={() => selectSuggestion(prompt)}\n onMouseEnter={() => setHoveredSuggestion(prompt.id)}\n onMouseLeave={() => setHoveredSuggestion(null)}\n style={{\n ...quickChatStyles.suggestionChip,\n ...(hoveredSuggestion === prompt.id\n ? quickChatStyles.suggestionChipHover\n : {}),\n }}\n >\n {prompt.text}\n </button>\n ))\n )}\n </div>\n )}\n\n {/* Messages area */}\n <div\n style={\n isPinned\n ? quickChatStyles.pinnedMessagesArea\n : quickChatStyles.messagesArea\n }\n >\n {/* Keep generic errors visible, but rate-limit uses a sticky banner below */}\n {error && !rateLimitNotice && (\n <div style={quickChatStyles.errorContainer}>\n <AlertCircle size={20} style={quickChatStyles.errorIcon} />\n <span style={quickChatStyles.errorText}>{error}</span>\n <button\n type=\"button\"\n onClick={() => sendMessage()}\n style={quickChatStyles.errorRetry}\n >\n <RefreshCw size={10} />\n Retry\n </button>\n </div>\n )}\n {debugInfo && (\n <div\n style={{\n backgroundColor: \"#0f172a\",\n color: \"#e2e8f0\",\n border: \"1px solid #334155\",\n borderRadius: \"8px\",\n padding: \"8px\",\n margin: \"0 0 8px\",\n fontSize: \"12px\",\n lineHeight: 1.4,\n wordBreak: \"break-word\",\n }}\n >\n <div\n style={{\n display: \"flex\",\n justifyContent: \"space-between\",\n gap: \"8px\",\n }}\n >\n <span>\n Last request: {debugInfo.status}{\" \"}\n {debugInfo.ok ? \"(ok)\" : \"(error)\"}\n </span>\n <span style={{ opacity: 0.7 }}>\n {new Date(debugInfo.timestamp).toLocaleTimeString()}\n </span>\n </div>\n {debugInfo.error && (\n <div style={{ color: \"#f87171\", marginTop: \"4px\" }}>\n Error: {debugInfo.error}\n </div>\n )}\n {debugInfo.contentPreview && (\n <div style={{ marginTop: \"4px\" }}>\n Content: {debugInfo.contentPreview}\n </div>\n )}\n <div style={{ marginTop: \"4px\", opacity: 0.8 }}>\n Raw: {debugInfo.rawTextPreview || \"(empty)\"}\n </div>\n </div>\n )}\n {messages.length > 0 &&\n messages.map((message) => (\n <div\n key={message.id}\n style={{\n ...quickChatStyles.message,\n animation: \"fadeIn 0.2s ease-out\",\n }}\n >\n <div\n style={\n message.role === \"user\"\n ? quickChatStyles.messageUser\n : quickChatStyles.messageAssistant\n }\n >\n {message.content}\n {message.isStreaming && (\n <span style={quickChatStyles.streamingIndicator} />\n )}\n {message.role === \"assistant\" &&\n !message.isStreaming &&\n message.content.endsWith(\"...\") && (\n <span style={quickChatStyles.truncated}>(truncated)</span>\n )}\n </div>\n {message.role === \"assistant\" &&\n !message.isStreaming &&\n message.content && (\n <div style={quickChatStyles.messageActions}>\n <button\n type=\"button\"\n onClick={() => handleCopy(message.content)}\n style={quickChatStyles.actionButton}\n >\n <Copy size={10} />\n Copy\n </button>\n {message.actions?.map((action) => (\n <button\n key={action.id}\n type=\"button\"\n onClick={action.onClick}\n style={quickChatStyles.actionButton}\n >\n {action.icon}\n {action.label}\n </button>\n ))}\n </div>\n )}\n </div>\n ))}\n <div ref={messagesEndRef} />\n </div>\n\n {/* Sticky bottom notice for rate limiting */}\n {rateLimitNotice && (\n <div\n style={{\n borderTop: \"1px solid rgba(148, 163, 184, 0.25)\",\n background:\n \"linear-gradient(180deg, rgba(15, 23, 42, 0.92), rgba(15, 23, 42, 0.96))\",\n color: \"#e2e8f0\",\n padding: \"8px 10px\",\n }}\n >\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"space-between\",\n gap: \"8px\",\n }}\n >\n <div style={{ display: \"flex\", alignItems: \"center\", gap: \"8px\" }}>\n <AlertCircle size={16} style={{ color: \"#fbbf24\" }} />\n <span style={{ fontSize: \"13px\", lineHeight: 1.2 }}>\n {rateLimitNotice.message}\n </span>\n </div>\n\n <div style={{ display: \"flex\", alignItems: \"center\", gap: \"6px\" }}>\n <button\n type=\"button\"\n onClick={() => setRateLimitExpanded((v) => !v)}\n style={{\n border: \"1px solid rgba(148, 163, 184, 0.25)\",\n background: \"rgba(30, 41, 59, 0.6)\",\n color: \"#e2e8f0\",\n borderRadius: \"6px\",\n padding: \"4px 8px\",\n fontSize: \"12px\",\n cursor: \"pointer\",\n }}\n >\n {rateLimitExpanded ? \"Hide\" : \"Details\"}\n </button>\n\n <button\n type=\"button\"\n onClick={handleReportIssue}\n disabled={reportStatus === \"sending\" || reportStatus === \"sent\"}\n style={{\n border: \"1px solid rgba(148, 163, 184, 0.25)\",\n background:\n reportStatus === \"sent\"\n ? \"rgba(34, 197, 94, 0.22)\"\n : \"rgba(30, 41, 59, 0.6)\",\n color: \"#e2e8f0\",\n borderRadius: \"6px\",\n padding: \"4px 8px\",\n fontSize: \"12px\",\n cursor:\n reportStatus === \"sending\" || reportStatus === \"sent\"\n ? \"not-allowed\"\n : \"pointer\",\n opacity: reportStatus === \"sending\" ? 0.7 : 1,\n }}\n title=\"Create a GitHub issue via /api/feedback\"\n >\n {reportStatus === \"sending\"\n ? \"Reporting...\"\n : reportStatus === \"sent\"\n ? \"Reported\"\n : \"Report\"}\n </button>\n\n <button\n type=\"button\"\n onClick={() => {\n clearRateLimitNotice();\n setRateLimitExpanded(false);\n }}\n style={{\n border: \"none\",\n background: \"transparent\",\n color: \"rgba(226, 232, 240, 0.8)\",\n padding: \"4px\",\n cursor: \"pointer\",\n }}\n title=\"Dismiss\"\n >\n <X size={14} />\n </button>\n </div>\n </div>\n\n {reportUrl && (\n <div style={{ marginTop: \"6px\", fontSize: \"12px\" }}>\n Created:{\" \"}\n <a\n href={reportUrl}\n target=\"_blank\"\n rel=\"noopener noreferrer\"\n style={{ color: \"#93c5fd\" }}\n >\n Open issue\n </a>\n </div>\n )}\n {reportError && (\n <div\n style={{ marginTop: \"6px\", fontSize: \"12px\", color: \"#fca5a5\" }}\n >\n {reportError}\n </div>\n )}\n\n {rateLimitExpanded && (\n <div\n style={{\n marginTop: \"8px\",\n fontSize: \"12px\",\n lineHeight: 1.4,\n backgroundColor: \"rgba(2, 6, 23, 0.55)\",\n border: \"1px solid rgba(148, 163, 184, 0.25)\",\n borderRadius: \"8px\",\n padding: \"8px\",\n wordBreak: \"break-word\",\n }}\n >\n <div style={{ opacity: 0.85 }}>\n Status: {rateLimitNotice.status}\n {rateLimitNotice.requestId\n ? ` • Request: ${rateLimitNotice.requestId}`\n : \"\"}\n </div>\n {rateLimitNotice.endpoint && (\n <div style={{ opacity: 0.75, marginTop: \"4px\" }}>\n Endpoint: {rateLimitNotice.endpoint}\n </div>\n )}\n {rateLimitNotice.retryAt && (\n <div style={{ opacity: 0.75, marginTop: \"4px\" }}>\n RetryAt: {new Date(rateLimitNotice.retryAt).toLocaleString()}\n </div>\n )}\n {rateLimitNotice.raw && (\n <div style={{ marginTop: \"6px\", opacity: 0.85 }}>\n Raw: {rateLimitNotice.raw}\n </div>\n )}\n {debugInfo && (\n <div style={{ marginTop: \"6px\", opacity: 0.85 }}>\n Debug: {debugInfo.rawTextPreview || \"(empty)\"}\n </div>\n )}\n </div>\n )}\n </div>\n )}\n\n {/* Input area */}\n <div style={quickChatStyles.inputContainer}>\n <textarea\n ref={inputRef}\n value={input}\n onChange={handleInputChange}\n onKeyDown={handleKeyDown}\n onFocus={() => setInputFocused(true)}\n onBlur={() => setInputFocused(false)}\n placeholder={mergedConfig.placeholder}\n disabled={isSending}\n rows={1}\n style={{\n ...quickChatStyles.input,\n ...(inputFocused ? quickChatStyles.inputFocused : {}),\n }}\n />\n <div style={{ display: \"flex\", gap: \"4px\" }}>\n {/* t3.chat button */}\n {mergedConfig.t3chat?.enabled !== false && (\n <button\n type=\"button\"\n onClick={handleSendToT3Chat}\n disabled={!input.trim()}\n title={mergedConfig.t3chat?.label ?? \"Ask t3.chat\"}\n style={{\n ...quickChatStyles.sendButton,\n backgroundColor: \"#7c3aed\",\n ...(!input.trim() ? quickChatStyles.sendButtonDisabled : {}),\n }}\n >\n <ExternalLink size={14} />\n </button>\n )}\n <button\n type=\"button\"\n onClick={handleSend}\n disabled={isSending || !input.trim()}\n style={{\n ...quickChatStyles.sendButton,\n ...(isSending || !input.trim()\n ? quickChatStyles.sendButtonDisabled\n : {}),\n }}\n >\n {isSending ? (\n <div\n style={{\n width: \"14px\",\n height: \"14px\",\n border: \"2px solid transparent\",\n borderTopColor: \"#fff\",\n borderRadius: \"50%\",\n animation: \"spin 0.8s linear infinite\",\n }}\n />\n ) : (\n <Send size={14} />\n )}\n </button>\n </div>\n </div>\n </div>\n );\n}\n","/**\n * Style definitions for QuickChat component.\n *\n * @module QuickChat/styles\n * @since 2.0.0\n */\nimport type { CSSProperties } from \"react\";\n\n/**\n * QuickChat component styles.\n */\nexport const quickChatStyles: Record<string, CSSProperties> = {\n // Inline container - inside the context menu\n container: {\n display: \"flex\",\n flexDirection: \"column\",\n width: \"100%\",\n maxHeight: \"320px\",\n overflow: \"hidden\",\n },\n\n // Pinned drawer - anchored to right side of screen\n pinnedContainer: {\n position: \"fixed\",\n top: 0,\n right: 0,\n bottom: 0,\n width: \"340px\",\n display: \"flex\",\n flexDirection: \"column\",\n backgroundColor: \"var(--anyclick-menu-bg, #ffffff)\",\n borderLeft: \"1px solid var(--anyclick-menu-border, #e5e5e5)\",\n boxShadow: \"-4px 0 24px rgba(0, 0, 0, 0.15)\",\n fontFamily:\n '-apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, sans-serif',\n fontSize: \"14px\",\n overflow: \"hidden\",\n zIndex: 9998,\n },\n\n // Pinned messages area (taller)\n pinnedMessagesArea: {\n flex: 1,\n overflowY: \"auto\",\n padding: \"12px\",\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"8px\",\n minHeight: \"200px\",\n },\n\n // Header - minimal design\n header: {\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"space-between\",\n padding: \"6px 8px\",\n gap: \"8px\",\n },\n headerTitle: {\n fontSize: \"11px\",\n fontWeight: 600,\n textTransform: \"uppercase\" as const,\n letterSpacing: \"0.5px\",\n color: \"var(--anyclick-menu-text-muted, #666)\",\n },\n headerActions: {\n display: \"flex\",\n alignItems: \"center\",\n gap: \"2px\",\n },\n iconButton: {\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n width: \"24px\",\n height: \"24px\",\n border: \"none\",\n borderRadius: \"4px\",\n backgroundColor: \"transparent\",\n color: \"var(--anyclick-menu-text-muted, #666)\",\n cursor: \"pointer\",\n transition: \"all 0.15s ease\",\n },\n iconButtonActive: {\n backgroundColor: \"var(--anyclick-menu-accent, #0066cc)\",\n color: \"#fff\",\n },\n\n // Context badge in header\n contextBadge: {\n display: \"inline-flex\",\n alignItems: \"center\",\n gap: \"4px\",\n padding: \"3px 8px\",\n fontSize: \"10px\",\n fontWeight: 500,\n border: \"1px solid var(--anyclick-menu-border, #e5e5e5)\",\n borderRadius: \"10px\",\n backgroundColor: \"transparent\",\n color: \"var(--anyclick-menu-text-muted, #666)\",\n cursor: \"pointer\",\n transition: \"all 0.15s ease\",\n },\n contextBadgeActive: {\n borderColor: \"var(--anyclick-menu-accent, #0066cc)\",\n backgroundColor: \"rgba(0, 102, 204, 0.08)\",\n },\n\n // Context dropdown (in normal flow, not absolute)\n contextDropdown: {\n display: \"flex\",\n flexDirection: \"column\" as const,\n gap: \"2px\",\n padding: \"6px 8px\",\n margin: \"0 8px 6px 8px\",\n backgroundColor: \"var(--anyclick-menu-hover, #f5f5f5)\",\n borderRadius: \"6px\",\n maxHeight: \"80px\",\n overflowY: \"auto\" as const,\n },\n\n // Messages area\n messagesArea: {\n flex: 1,\n overflowY: \"auto\",\n padding: \"8px 12px\",\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"8px\",\n minHeight: \"40px\",\n maxHeight: \"140px\",\n },\n emptyState: {\n display: \"none\", // Hide empty state, placeholder in input is enough\n },\n\n // Message bubble\n message: {\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"4px\",\n maxWidth: \"100%\",\n },\n messageUser: {\n alignSelf: \"flex-end\",\n backgroundColor: \"var(--anyclick-menu-accent, #0066cc)\",\n color: \"#fff\",\n padding: \"6px 10px\",\n borderRadius: \"12px 12px 4px 12px\",\n fontSize: \"13px\",\n maxWidth: \"85%\",\n wordBreak: \"break-word\" as const,\n },\n messageAssistant: {\n alignSelf: \"flex-start\",\n backgroundColor: \"var(--anyclick-menu-hover, #f5f5f5)\",\n color: \"var(--anyclick-menu-text, #333)\",\n padding: \"8px 10px\",\n borderRadius: \"12px 12px 12px 4px\",\n fontSize: \"13px\",\n maxWidth: \"100%\",\n wordBreak: \"break-word\" as const,\n lineHeight: 1.4,\n },\n messageActions: {\n display: \"flex\",\n gap: \"4px\",\n marginTop: \"4px\",\n flexWrap: \"wrap\" as const,\n },\n actionButton: {\n display: \"inline-flex\",\n alignItems: \"center\",\n gap: \"4px\",\n padding: \"3px 8px\",\n fontSize: \"11px\",\n fontWeight: 500,\n border: \"1px solid var(--anyclick-menu-border, #e5e5e5)\",\n borderRadius: \"4px\",\n backgroundColor: \"transparent\",\n color: \"var(--anyclick-menu-text-muted, #666)\",\n cursor: \"pointer\",\n transition: \"all 0.15s ease\",\n },\n streamingIndicator: {\n display: \"inline-block\",\n width: \"4px\",\n height: \"14px\",\n backgroundColor: \"var(--anyclick-menu-accent, #0066cc)\",\n borderRadius: \"1px\",\n animation: \"blink 1s infinite\",\n },\n\n // Suggestions - compact horizontal scroll\n suggestionsContainer: {\n display: \"flex\",\n flexDirection: \"column\" as const,\n gap: \"6px\",\n padding: \"6px 8px\",\n overflowX: \"auto\" as const,\n overflowY: \"hidden\",\n scrollbarWidth: \"none\" as const,\n msOverflowStyle: \"none\" as const,\n },\n suggestionChip: {\n display: \"inline-flex\",\n alignItems: \"center\",\n padding: \"4px 10px\",\n fontSize: \"11px\",\n border: \"1px solid var(--anyclick-menu-border, #e5e5e5)\",\n borderRadius: \"12px\",\n backgroundColor: \"var(--anyclick-menu-hover, #f5f5f5)\",\n color: \"var(--anyclick-menu-text, #333)\",\n cursor: \"pointer\",\n transition: \"all 0.15s ease\",\n whiteSpace: \"nowrap\" as const,\n flexShrink: 0,\n },\n suggestionChipHover: {\n backgroundColor: \"var(--anyclick-menu-bg, #fff)\",\n borderColor: \"var(--anyclick-menu-accent, #0066cc)\",\n },\n\n // Context redaction - now in dropdown\n contextContainer: {\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"4px\",\n },\n contextHeader: {\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"space-between\",\n marginBottom: \"4px\",\n },\n contextTitle: {\n fontSize: \"10px\",\n fontWeight: 600,\n textTransform: \"uppercase\" as const,\n letterSpacing: \"0.5px\",\n color: \"var(--anyclick-menu-text-muted, #666)\",\n },\n contextToggle: {\n fontSize: \"10px\",\n color: \"var(--anyclick-menu-accent, #0066cc)\",\n background: \"none\",\n border: \"none\",\n cursor: \"pointer\",\n padding: 0,\n },\n contextToggleSmall: {\n fontSize: \"9px\",\n fontWeight: 500,\n color: \"var(--anyclick-menu-text-muted, #666)\",\n background: \"none\",\n border: \"none\",\n cursor: \"pointer\",\n padding: \"2px 4px\",\n borderRadius: \"3px\",\n transition: \"all 0.15s ease\",\n },\n contextChunks: {\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"4px\",\n },\n contextChunk: {\n display: \"flex\",\n alignItems: \"center\",\n gap: \"6px\",\n padding: \"4px 6px\",\n borderRadius: \"4px\",\n fontSize: \"11px\",\n backgroundColor: \"var(--anyclick-menu-hover, #f5f5f5)\",\n cursor: \"pointer\",\n transition: \"opacity 0.15s ease\",\n },\n contextChunkCompact: {\n display: \"flex\",\n alignItems: \"center\",\n gap: \"6px\",\n padding: \"2px 4px\",\n borderRadius: \"3px\",\n fontSize: \"10px\",\n cursor: \"pointer\",\n transition: \"opacity 0.15s ease\",\n },\n contextChunkExcluded: {\n opacity: 0.5,\n textDecoration: \"line-through\" as const,\n },\n contextCheckbox: {\n width: \"12px\",\n height: \"12px\",\n accentColor: \"var(--anyclick-menu-accent, #0066cc)\",\n },\n contextLabel: {\n flex: 1,\n overflow: \"hidden\",\n textOverflow: \"ellipsis\",\n whiteSpace: \"nowrap\" as const,\n color: \"var(--anyclick-menu-text, #333)\",\n },\n contextSize: {\n fontSize: \"10px\",\n color: \"var(--anyclick-menu-text-muted, #666)\",\n },\n\n // Input area\n inputContainer: {\n display: \"flex\",\n alignItems: \"flex-end\",\n gap: \"8px\",\n padding: \"8px\",\n },\n input: {\n flex: 1,\n padding: \"8px 12px\",\n fontSize: \"13px\",\n border: \"1px solid var(--anyclick-menu-input-border, #ddd)\",\n borderRadius: \"18px\",\n backgroundColor: \"var(--anyclick-menu-input-bg, #fff)\",\n color: \"var(--anyclick-menu-text, #333)\",\n outline: \"none\",\n resize: \"none\" as const,\n fontFamily: \"inherit\",\n lineHeight: 1.4,\n maxHeight: \"80px\",\n minHeight: \"36px\",\n },\n inputFocused: {\n borderColor: \"var(--anyclick-menu-accent, #0066cc)\",\n boxShadow: \"0 0 0 2px rgba(0, 102, 204, 0.1)\",\n },\n sendButton: {\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n width: \"32px\",\n height: \"32px\",\n border: \"none\",\n borderRadius: \"50%\",\n backgroundColor: \"var(--anyclick-menu-accent, #0066cc)\",\n color: \"#fff\",\n cursor: \"pointer\",\n transition: \"all 0.15s ease\",\n flexShrink: 0,\n },\n sendButtonDisabled: {\n backgroundColor: \"var(--anyclick-menu-border, #e5e5e5)\",\n cursor: \"not-allowed\",\n },\n\n // Loading states\n loadingDots: {\n display: \"flex\",\n gap: \"4px\",\n padding: \"8px\",\n },\n loadingDot: {\n width: \"6px\",\n height: \"6px\",\n borderRadius: \"50%\",\n backgroundColor: \"var(--anyclick-menu-text-muted, #666)\",\n animation: \"bounce 1.4s infinite ease-in-out both\",\n },\n\n // Error states\n errorContainer: {\n display: \"flex\",\n flexDirection: \"column\",\n alignItems: \"center\",\n gap: \"8px\",\n padding: \"16px\",\n textAlign: \"center\" as const,\n },\n errorIcon: {\n color: \"#ef4444\",\n },\n errorText: {\n fontSize: \"12px\",\n color: \"#ef4444\",\n maxWidth: \"200px\",\n },\n errorRetry: {\n display: \"inline-flex\",\n alignItems: \"center\",\n gap: \"4px\",\n padding: \"4px 10px\",\n fontSize: \"11px\",\n fontWeight: 500,\n border: \"1px solid #ef4444\",\n borderRadius: \"4px\",\n backgroundColor: \"transparent\",\n color: \"#ef4444\",\n cursor: \"pointer\",\n transition: \"all 0.15s ease\",\n },\n\n // Truncation indicator\n truncated: {\n fontSize: \"10px\",\n color: \"var(--anyclick-menu-text-muted, #666)\",\n fontStyle: \"italic\" as const,\n marginTop: \"4px\",\n },\n};\n\n/**\n * CSS keyframes for animations (to be injected).\n */\nexport const quickChatKeyframes = `\n@keyframes blink {\n 0%, 50% { opacity: 1; }\n 51%, 100% { opacity: 0; }\n}\n\n@keyframes bounce {\n 0%, 80%, 100% { transform: scale(0); }\n 40% { transform: scale(1); }\n}\n\n@keyframes slideIn {\n from {\n opacity: 0;\n transform: translateY(-8px);\n }\n to {\n opacity: 1;\n transform: translateY(0);\n }\n}\n\n@keyframes slideInFromRight {\n from {\n transform: translateX(100%);\n }\n to {\n transform: translateX(0);\n }\n}\n\n@keyframes slideOutToRight {\n from {\n transform: translateX(0);\n }\n to {\n transform: translateX(100%);\n }\n}\n\n@keyframes fadeIn {\n from { opacity: 0; }\n to { opacity: 1; }\n}\n\n@keyframes spin {\n from { transform: rotate(0deg); }\n to { transform: rotate(360deg); }\n}\n\n@keyframes pulse {\n 0%, 100% { opacity: 1; }\n 50% { opacity: 0.5; }\n}\n`;\n","/**\n * Hook for managing QuickChat state and logic using ai-sdk-ui and zustand.\n *\n * @module QuickChat/useQuickChat\n * @since 3.1.0\n */\n\"use client\";\n\nimport { useCallback, useEffect, useMemo, useRef, useState } from \"react\";\nimport { useChat } from \"@ai-sdk/react\";\nimport { DefaultChatTransport } from \"ai\";\nimport { useActiveMessages, useQuickChatStore } from \"./store\";\nimport type { ChatMessage, QuickChatConfig, SuggestedPrompt } from \"./types\";\nimport { DEFAULT_QUICK_CHAT_CONFIG } from \"./types\";\nimport {\n buildContextString,\n extractContextChunks,\n} from \"./useQuickChat.context\";\nimport type { DebugInfo } from \"./useQuickChat.debug\";\nimport { createDebugInfo } from \"./useQuickChat.debug\";\nimport {\n chatMessagesToUiMessages,\n getUIMessageText,\n uiMessagesToChatMessages,\n} from \"./useQuickChat.messages\";\nimport type { RateLimitNotice } from \"./useQuickChat.rateLimit\";\nimport {\n rateLimitNoticeFromError,\n rateLimitNoticeFromResponse,\n} from \"./useQuickChat.rateLimit\";\n\nexport type { RateLimitNotice } from \"./useQuickChat.rateLimit\";\n\n/**\n * Hook for managing QuickChat state and interactions.\n * Uses ai-sdk-ui for streaming and zustand for persistence.\n */\nexport function useQuickChat(\n targetElement: Element | null,\n containerElement: Element | null,\n config: QuickChatConfig = {},\n) {\n console.count(\"useQuickChat\");\n const mergedConfig = { ...DEFAULT_QUICK_CHAT_CONFIG, ...config };\n\n const initializedRef = useRef(false);\n const syncTimeoutRef = useRef<ReturnType<typeof setTimeout> | null>(null);\n\n const [manualSending, setManualSending] = useState(false);\n const [debugInfo, setDebugInfo] = useState<DebugInfo | null>(null);\n const [rateLimitNotice, setRateLimitNotice] =\n useState<RateLimitNotice | null>(null);\n\n // Zustand store\n const {\n input,\n setInput,\n isPinned,\n setIsPinned,\n contextChunks,\n setContextChunks,\n toggleChunk,\n toggleAllChunks,\n suggestedPrompts,\n setSuggestedPrompts,\n isLoadingSuggestions,\n setIsLoadingSuggestions,\n error,\n setError,\n addMessage,\n clearMessages: storeClearMessages,\n setLastSyncedAt,\n lastSyncedAt,\n setIsSending: setStoreIsSending,\n setIsStreaming: setStoreIsStreaming,\n } = useQuickChatStore();\n\n // Active (non-expired) messages persisted for 24h\n const storedMessages = useActiveMessages();\n\n const contextString = useMemo(\n () => buildContextString(contextChunks),\n [contextChunks],\n );\n\n const chatBody = useMemo(\n () => ({\n action: \"chat\",\n context: contextString,\n model: mergedConfig.model,\n systemPrompt: mergedConfig.systemPrompt,\n maxLength: mergedConfig.maxResponseLength,\n }),\n [\n contextString,\n mergedConfig.model,\n mergedConfig.systemPrompt,\n mergedConfig.maxResponseLength,\n ],\n );\n\n // Memoize transport to prevent re-creation (and avoid re-initializing useChat)\n const transport = useMemo(\n () =>\n new DefaultChatTransport({\n api: mergedConfig.endpoint,\n body: chatBody,\n }),\n [mergedConfig.endpoint, chatBody],\n );\n\n const handleRateLimitResponse = useCallback(\n async (res: Response, endpoint: string) => {\n const notice = await rateLimitNoticeFromResponse(res, endpoint);\n if (!notice) return false;\n setRateLimitNotice(notice);\n setError(null);\n return true;\n },\n [setError],\n );\n\n /**\n * Schedule a backend sync after a short delay to batch updates.\n */\n const scheduleBackendSync = useCallback(() => {\n if (syncTimeoutRef.current) clearTimeout(syncTimeoutRef.current);\n\n syncTimeoutRef.current = setTimeout(async () => {\n try {\n const currentMessages = useQuickChatStore\n .getState()\n .getActiveMessages();\n if (currentMessages.length === 0) return;\n\n const endpoint = `${mergedConfig.endpoint}/history`;\n const res = await fetch(endpoint, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({\n action: \"save\",\n messages: currentMessages,\n }),\n });\n\n if (await handleRateLimitResponse(res, endpoint)) return;\n if (res.ok) setLastSyncedAt(Date.now());\n } catch (err) {\n console.error(\"[useQuickChat] Failed to sync chat history:\", err);\n }\n }, 1000);\n }, [handleRateLimitResponse, mergedConfig.endpoint, setLastSyncedAt]);\n\n const {\n messages: aiMessages,\n sendMessage: aiSendMessage,\n status,\n stop,\n setMessages: setAiMessages,\n } = useChat({\n transport,\n onError: (err) => {\n const response =\n (err as unknown as { response?: Response }).response ?? undefined;\n const statusCode =\n (err as unknown as { status?: number }).status ??\n (response ? response.status : undefined) ??\n -1;\n\n const responseText =\n (err as unknown as { responseText?: string }).responseText ??\n (err as unknown as { message?: string }).message ??\n \"\";\n\n setDebugInfo(\n createDebugInfo({\n status: statusCode,\n ok: false,\n contentType: response?.headers?.get?.(\"content-type\") ?? null,\n rawText: responseText,\n error: err.message,\n }),\n );\n\n setStoreIsStreaming(false);\n setStoreIsSending(false);\n\n const notice = rateLimitNoticeFromError({\n statusCode,\n response,\n responseText,\n endpoint: mergedConfig.endpoint,\n });\n\n if (notice) {\n setRateLimitNotice(notice);\n setError(null);\n return;\n }\n\n setRateLimitNotice(null);\n setError(err.message);\n },\n onFinish: ({ message }) => {\n const messageText = getUIMessageText(message);\n\n // Persist assistant message to store for 24h history + backend sync.\n // Store IDs are generated, so we dedupe using the trailing message.\n const current = useQuickChatStore.getState().getActiveMessages();\n const last = current[current.length - 1];\n const alreadyHaveSameTail =\n last?.role === \"assistant\" && last.content === messageText;\n\n if (!alreadyHaveSameTail && messageText) {\n addMessage({\n role: message.role as \"user\" | \"assistant\" | \"system\",\n content: messageText,\n isStreaming: false,\n });\n }\n\n scheduleBackendSync();\n setStoreIsStreaming(false);\n setStoreIsSending(false);\n },\n });\n\n const loadFromBackend = useCallback(async () => {\n try {\n const endpoint = `${mergedConfig.endpoint}/history`;\n const response = await fetch(endpoint, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({ action: \"load\" }),\n });\n\n if (await handleRateLimitResponse(response, endpoint)) return;\n if (!response.ok) return;\n\n const data = (await response.json().catch(() => null)) as {\n messages?: ChatMessage[];\n } | null;\n\n if (!data?.messages || !Array.isArray(data.messages)) return;\n if (data.messages.length === 0) return;\n\n useQuickChatStore.getState().hydrate(data.messages);\n setAiMessages(chatMessagesToUiMessages(data.messages));\n } catch (err) {\n console.error(\"[useQuickChat] Failed to load chat history:\", err);\n }\n }, [handleRateLimitResponse, mergedConfig.endpoint, setAiMessages]);\n\n // Convert ai-sdk messages to our ChatMessage format for display\n const messages: ChatMessage[] = useMemo(\n () =>\n uiMessagesToChatMessages({\n uiMessages: aiMessages,\n status,\n setInput,\n }),\n [aiMessages, setInput, status],\n );\n\n const isStreaming = status === \"streaming\";\n const isSending =\n status === \"submitted\" || status === \"streaming\" || manualSending;\n\n // Initialize: load from backend if store is empty, or restore from store\n useEffect(() => {\n if (initializedRef.current) return;\n initializedRef.current = true;\n\n if (storedMessages.length > 0) {\n setAiMessages(chatMessagesToUiMessages(storedMessages));\n } else {\n void loadFromBackend();\n }\n }, [loadFromBackend, setAiMessages, storedMessages]);\n\n // Extract context when target element changes\n useEffect(() => {\n if (!targetElement) return;\n const chunks = extractContextChunks(targetElement, containerElement);\n setContextChunks(chunks);\n }, [targetElement, containerElement, setContextChunks]);\n\n // Fetch suggested prompts when context is available\n useEffect(() => {\n if (!mergedConfig.showSuggestions) return;\n if (!contextString) return;\n if (suggestedPrompts.length > 0) return;\n\n let cancelled = false;\n\n const fetchSuggestions = async () => {\n setIsLoadingSuggestions(true);\n\n try {\n const response = await fetch(mergedConfig.endpoint, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({\n action: \"suggest\",\n context: contextString,\n model: mergedConfig.prePassModel,\n }),\n });\n\n if (await handleRateLimitResponse(response, mergedConfig.endpoint)) {\n return;\n }\n\n if (response.ok) {\n const data = (await response.json().catch(() => null)) as {\n suggestions?: string[];\n } | null;\n\n if (data?.suggestions && Array.isArray(data.suggestions)) {\n if (!cancelled) {\n setSuggestedPrompts(\n data.suggestions.map((text: string, i: number) => ({\n id: `suggestion-${i}`,\n text,\n })),\n );\n setIsLoadingSuggestions(false);\n }\n return;\n }\n }\n } catch (err) {\n console.error(\"[useQuickChat] Failed to fetch suggestions:\", err);\n }\n\n if (!cancelled) {\n setSuggestedPrompts([\n { id: \"s1\", text: \"What is this element?\" },\n { id: \"s2\", text: \"How can I style this?\" },\n { id: \"s3\", text: \"Is this accessible?\" },\n ]);\n setIsLoadingSuggestions(false);\n }\n };\n\n void fetchSuggestions();\n\n return () => {\n cancelled = true;\n };\n }, [\n contextString,\n handleRateLimitResponse,\n mergedConfig.endpoint,\n mergedConfig.prePassModel,\n mergedConfig.showSuggestions,\n setIsLoadingSuggestions,\n setSuggestedPrompts,\n suggestedPrompts.length,\n ]);\n\n // Select a suggested prompt\n const selectSuggestion = useCallback(\n (prompt: SuggestedPrompt) => {\n setInput(prompt.text);\n },\n [setInput],\n );\n\n // Send a message using streaming (ai-sdk useChat)\n const sendMessage = useCallback(\n async (messageText?: string) => {\n const text = (messageText || input).trim();\n if (!text) return;\n\n setInput(\"\");\n setError(null);\n setManualSending(true);\n setStoreIsSending(true);\n setStoreIsStreaming(true);\n setDebugInfo(null);\n\n try {\n addMessage({\n role: \"user\",\n content: text,\n });\n\n await aiSendMessage({ text });\n } catch (err) {\n const msg = err instanceof Error ? err.message : String(err);\n setError(msg);\n } finally {\n setManualSending(false);\n setStoreIsSending(false);\n setStoreIsStreaming(false);\n }\n },\n [\n addMessage,\n aiSendMessage,\n input,\n setError,\n setInput,\n setStoreIsSending,\n setStoreIsStreaming,\n ],\n );\n\n // Clear messages\n const clearMessages = useCallback(() => {\n stop();\n storeClearMessages();\n setAiMessages([]);\n\n const endpoint = `${mergedConfig.endpoint}/history`;\n fetch(endpoint, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({ action: \"clear\" }),\n })\n .then((res) => handleRateLimitResponse(res, endpoint))\n .catch((err) =>\n console.error(\"[useQuickChat] Failed to clear backend history:\", err),\n );\n }, [\n handleRateLimitResponse,\n mergedConfig.endpoint,\n setAiMessages,\n stop,\n storeClearMessages,\n ]);\n\n // Cleanup on unmount\n useEffect(() => {\n return () => {\n if (syncTimeoutRef.current) clearTimeout(syncTimeoutRef.current);\n };\n }, []);\n\n return {\n input,\n messages,\n isLoadingSuggestions,\n isSending,\n isStreaming,\n suggestedPrompts,\n contextChunks,\n error,\n debugInfo,\n rateLimitNotice,\n isPinned,\n lastSyncedAt,\n config: mergedConfig,\n setInput,\n toggleChunk,\n toggleAllChunks,\n selectSuggestion,\n sendMessage,\n clearMessages,\n setIsPinned,\n clearRateLimitNotice: () => setRateLimitNotice(null),\n };\n}\n","/**\n * Zustand store for QuickChat with 24h localStorage persistence.\n *\n * @module QuickChat/store\n * @since 3.1.0\n */\n\"use client\";\n\nimport { create } from \"zustand\";\nimport { createJSONStorage, persist } from \"zustand/middleware\";\nimport type { ChatMessage, ContextChunk, SuggestedPrompt } from \"./types\";\n\nconst STORE_NAME = \"anyclick-quick-chat-store\";\nconst TWENTY_FOUR_HOURS_MS = 24 * 60 * 60 * 1000;\n\n/**\n * Generate a unique message ID.\n */\nexport function generateMessageId(): string {\n return `${Date.now()}-${Math.random().toString(36).slice(2, 9)}`;\n}\n\n/**\n * Stored message with expiry timestamp.\n */\ninterface StoredMessage extends ChatMessage {\n /** Unix timestamp when this message expires */\n expiresAt: number;\n}\n\n/**\n * Chat store state.\n */\nexport interface QuickChatStore {\n /** Chat messages with 24h expiry */\n messages: StoredMessage[];\n /** Whether the chat is pinned */\n isPinned: boolean;\n /** Current input value */\n input: string;\n /** Context chunks for current session */\n contextChunks: ContextChunk[];\n /** Suggested prompts */\n suggestedPrompts: SuggestedPrompt[];\n /** Loading state for suggestions */\n isLoadingSuggestions: boolean;\n /** Sending state */\n isSending: boolean;\n /** Streaming state */\n isStreaming: boolean;\n /** Error message */\n error: string | null;\n /** Last sync timestamp with backend */\n lastSyncedAt: number | null;\n\n // Actions\n setInput: (input: string) => void;\n addMessage: (message: Omit<ChatMessage, \"id\" | \"timestamp\">) => string;\n updateMessage: (id: string, updates: Partial<ChatMessage>) => void;\n clearMessages: () => void;\n setIsPinned: (pinned: boolean) => void;\n setContextChunks: (chunks: ContextChunk[]) => void;\n toggleChunk: (chunkId: string) => void;\n toggleAllChunks: (included: boolean) => void;\n setSuggestedPrompts: (prompts: SuggestedPrompt[]) => void;\n setIsLoadingSuggestions: (loading: boolean) => void;\n setIsSending: (sending: boolean) => void;\n setIsStreaming: (streaming: boolean) => void;\n setError: (error: string | null) => void;\n setLastSyncedAt: (timestamp: number | null) => void;\n pruneExpiredMessages: () => void;\n getActiveMessages: () => ChatMessage[];\n hydrate: (messages: ChatMessage[]) => void;\n}\n\n/**\n * Custom storage that handles 24h expiry on rehydration.\n */\ntype PersistedQuickChatState = Pick<\n QuickChatStore,\n \"messages\" | \"isPinned\" | \"lastSyncedAt\"\n>;\n\nconst storage = createJSONStorage<PersistedQuickChatState>(() => localStorage);\n\n/**\n * Filter out expired messages.\n */\nfunction filterExpiredMessages(messages: StoredMessage[]): StoredMessage[] {\n const now = Date.now();\n return messages.filter((msg) => msg.expiresAt > now);\n}\n\n/**\n * Create the QuickChat store with persistence.\n */\nexport const useQuickChatStore = create<QuickChatStore>()(\n persist<QuickChatStore, [], [], PersistedQuickChatState>(\n (set, get) => ({\n messages: [],\n isPinned: false,\n input: \"\",\n contextChunks: [],\n suggestedPrompts: [],\n isLoadingSuggestions: false,\n isSending: false,\n isStreaming: false,\n error: null,\n lastSyncedAt: null,\n\n setInput: (input) => set({ input }),\n\n addMessage: (message) => {\n const id = generateMessageId();\n const now = Date.now();\n const storedMessage: StoredMessage = {\n ...message,\n id,\n timestamp: now,\n expiresAt: now + TWENTY_FOUR_HOURS_MS,\n };\n set((state) => {\n const newMessages = [...state.messages, storedMessage];\n return {\n messages: newMessages,\n };\n });\n return id;\n },\n\n updateMessage: (id, updates) => {\n set((state) => ({\n messages: state.messages.map((msg) =>\n msg.id === id ? { ...msg, ...updates } : msg,\n ),\n }));\n },\n\n clearMessages: () => set({ messages: [], error: null }),\n\n setIsPinned: (pinned) => set({ isPinned: pinned }),\n\n setContextChunks: (chunks) => set({ contextChunks: chunks }),\n\n toggleChunk: (chunkId) => {\n set((state) => ({\n contextChunks: state.contextChunks.map((chunk) =>\n chunk.id === chunkId\n ? { ...chunk, included: !chunk.included }\n : chunk,\n ),\n }));\n },\n\n toggleAllChunks: (included) => {\n set((state) => ({\n contextChunks: state.contextChunks.map((chunk) => ({\n ...chunk,\n included,\n })),\n }));\n },\n\n setSuggestedPrompts: (prompts) => set({ suggestedPrompts: prompts }),\n\n setIsLoadingSuggestions: (loading) =>\n set({ isLoadingSuggestions: loading }),\n\n setIsSending: (sending) => set({ isSending: sending }),\n\n setIsStreaming: (streaming) => set({ isStreaming: streaming }),\n\n setError: (error) => set({ error }),\n\n setLastSyncedAt: (timestamp) => set({ lastSyncedAt: timestamp }),\n\n pruneExpiredMessages: () => {\n set((state) => ({\n messages: filterExpiredMessages(state.messages),\n }));\n },\n\n getActiveMessages: () => {\n const state = get();\n const now = Date.now();\n const active = state.messages\n .filter((msg) => msg.expiresAt > now)\n .map(({ expiresAt, ...msg }) => msg);\n console.log(\"[store] getActiveMessages\", {\n totalMessages: state.messages.length,\n activeMessages: active.length,\n activeIds: active.map((m) => m.id),\n });\n return active;\n },\n\n hydrate: (messages) => {\n const now = Date.now();\n const storedMessages: StoredMessage[] = messages.map((msg) => ({\n ...msg,\n expiresAt: now + TWENTY_FOUR_HOURS_MS,\n }));\n set({ messages: storedMessages, lastSyncedAt: now });\n },\n }),\n {\n name: STORE_NAME,\n storage,\n partialize: (state) => ({\n messages: state.messages,\n isPinned: state.isPinned,\n lastSyncedAt: state.lastSyncedAt,\n }),\n onRehydrateStorage: () => (state) => {\n // Prune expired messages on rehydration\n if (state) {\n state.pruneExpiredMessages();\n }\n },\n },\n ),\n);\n\n/**\n * Hook to get only active (non-expired) messages as ChatMessage[].\n */\nexport function useActiveMessages(): ChatMessage[] {\n const messages = useQuickChatStore((state) => state.messages);\n const now = Date.now();\n return messages\n .filter((msg) => msg.expiresAt > now)\n .map(({ expiresAt, ...msg }) => msg);\n}\n\n/**\n * Selector for messages count (for display purposes).\n */\nexport function useMessagesCount(): number {\n const messages = useQuickChatStore((state) => state.messages);\n const now = Date.now();\n return messages.filter((msg) => msg.expiresAt > now).length;\n}\n","/**\n * Type definitions for QuickChat component.\n *\n * @module QuickChat/types\n * @since 2.0.0\n */\nimport type { CSSProperties, ReactNode } from \"react\";\n\n/**\n * Context payload chunk that can be included or excluded by the user.\n */\nexport interface ContextChunk {\n /** Unique identifier for the chunk */\n id: string;\n /** Human-readable label for the chunk */\n label: string;\n /** The actual content/data */\n content: string;\n /** Type of context (element, text, error, etc.) */\n type: \"element\" | \"text\" | \"error\" | \"navigation\" | \"custom\";\n /** Whether this chunk is included in the payload (default: true) */\n included: boolean;\n /** Size in characters */\n size: number;\n}\n\n/**\n * A suggested prompt from the AI pre-pass.\n */\nexport interface SuggestedPrompt {\n /** Unique identifier */\n id: string;\n /** The prompt text */\n text: string;\n /** Optional category */\n category?: string;\n}\n\n/**\n * Quick action available for AI responses.\n */\nexport interface QuickAction {\n /** Unique identifier */\n id: string;\n /** Label to display */\n label: string;\n /** Icon to display */\n icon?: ReactNode;\n /** Action handler */\n onClick: () => void;\n}\n\n/**\n * A single chat message.\n */\nexport interface ChatMessage {\n /** Unique identifier */\n id: string;\n /** Role of the sender */\n role: \"user\" | \"assistant\" | \"system\";\n /** Message content */\n content: string;\n /** Timestamp */\n timestamp: number;\n /** Whether the message is currently streaming */\n isStreaming?: boolean;\n /** Quick actions available for this message */\n actions?: QuickAction[];\n}\n\n/**\n * Configuration for t3.chat integration.\n */\nexport interface T3ChatIntegrationConfig {\n /** Whether to show the \"Send to t3.chat\" button */\n enabled?: boolean;\n /** Base URL for t3.chat (default: https://t3.chat) */\n baseUrl?: string;\n /** Label for the button (default: \"Ask t3.chat\") */\n label?: string;\n}\n\n/**\n * Configuration for the QuickChat component.\n */\nexport interface QuickChatConfig {\n /** API endpoint for chat requests */\n endpoint?: string;\n /** Model to use for the main chat (default: auto) */\n model?: string;\n /** Model to use for pre-pass suggestions (default: gpt-5-nano) */\n prePassModel?: string;\n /** Maximum response length in characters */\n maxResponseLength?: number;\n /** Whether to show context redaction UI */\n showRedactionUI?: boolean;\n /** Whether to show suggested prompts */\n showSuggestions?: boolean;\n /** Custom system prompt */\n systemPrompt?: string;\n /** Placeholder text for input */\n placeholder?: string;\n /** Header title */\n title?: string;\n /** t3.chat integration settings */\n t3chat?: T3ChatIntegrationConfig;\n}\n\n/**\n * Props for the QuickChat component.\n */\nexport interface QuickChatProps {\n /** Whether the chat is visible */\n visible: boolean;\n /** Target element that was right-clicked */\n targetElement: Element | null;\n /** Container element */\n containerElement: Element | null;\n /** Callback when chat is closed */\n onClose: () => void;\n /** Callback when user wants to pin the chat */\n onPin?: (pinned: boolean) => void;\n /** Whether the chat is pinned */\n isPinned?: boolean;\n /** Configuration options */\n config?: QuickChatConfig;\n /** Custom styles */\n style?: CSSProperties;\n /** Custom class name */\n className?: string;\n /** Initial input value (for type-to-chat feature) */\n initialInput?: string;\n /** Callback when initial input has been consumed */\n onInitialInputConsumed?: () => void;\n}\n\n/**\n * State for the QuickChat hook.\n */\nexport interface QuickChatState {\n /** Current input value */\n input: string;\n /** Chat messages */\n messages: ChatMessage[];\n /** Whether we're loading suggestions */\n isLoadingSuggestions: boolean;\n /** Whether we're sending a message */\n isSending: boolean;\n /** Whether we're streaming a response */\n isStreaming: boolean;\n /** Suggested prompts from pre-pass */\n suggestedPrompts: SuggestedPrompt[];\n /** Context chunks with redaction state */\n contextChunks: ContextChunk[];\n /** Error message if any */\n error: string | null;\n}\n\n/**\n * Default t3.chat configuration values.\n */\nexport const DEFAULT_T3CHAT_CONFIG: Required<T3ChatIntegrationConfig> = {\n enabled: true,\n baseUrl: \"https://t3.chat\",\n label: \"Ask t3.chat\",\n};\n\n/**\n * Default configuration values.\n */\nexport const DEFAULT_QUICK_CHAT_CONFIG: Required<QuickChatConfig> = {\n endpoint: \"/api/anyclick/chat\",\n model: \"gpt-5-nano\",\n prePassModel: \"gpt-5-nano\",\n maxResponseLength: 10000,\n showRedactionUI: true,\n showSuggestions: true,\n systemPrompt:\n \"You are a helpful assistant that provides quick, concise answers about web elements and UI. Keep responses brief and actionable.\",\n placeholder: \"Ask about this element...\",\n title: \"Quick Ask\",\n t3chat: DEFAULT_T3CHAT_CONFIG,\n};\n","import { getElementInspectInfo } from \"@ewjdev/anyclick-core\";\nimport type { ContextChunk } from \"./types\";\n\n/**\n * Extracts context chunks from the target element.\n *\n * Note: `containerElement` is currently unused, but kept in the signature to\n * allow future enhancements (e.g. walking a scoped subtree) without changing\n * the hook API.\n */\nexport function extractContextChunks(\n targetElement: Element | null,\n _containerElement: Element | null,\n): ContextChunk[] {\n const chunks: ContextChunk[] = [];\n if (!targetElement) return chunks;\n\n try {\n const info = getElementInspectInfo(targetElement);\n\n const tagContent = `<${info.tagName.toLowerCase()}${\n info.id ? ` id=\"${info.id}\"` : \"\"\n }${\n info.classNames.length > 0 ? ` class=\"${info.classNames.join(\" \")}\"` : \"\"\n }>`;\n chunks.push({\n id: \"element-tag\",\n label: \"Element Tag\",\n content: tagContent,\n type: \"element\",\n included: true,\n size: tagContent.length,\n });\n\n if (info.innerText && info.innerText.length > 0) {\n const textContent = info.innerText.slice(0, 200);\n chunks.push({\n id: \"element-text\",\n label: \"Text Content\",\n content: textContent,\n type: \"text\",\n included: true,\n size: textContent.length,\n });\n }\n\n if (info.computedStyles) {\n const styleEntries: string[] = [];\n for (const [, styles] of Object.entries(info.computedStyles)) {\n if (styles && typeof styles === \"object\") {\n const entries = Object.entries(styles).slice(0, 2);\n for (const [k, v] of entries) {\n if (v) styleEntries.push(`${k}: ${v}`);\n }\n }\n if (styleEntries.length >= 8) break;\n }\n const stylesContent = styleEntries.join(\"; \");\n if (stylesContent) {\n chunks.push({\n id: \"element-styles\",\n label: \"Key Styles\",\n content: stylesContent,\n type: \"element\",\n included: true,\n size: stylesContent.length,\n });\n }\n }\n\n if (info.accessibility) {\n const a11yContent = [\n info.accessibility.role && `role=\"${info.accessibility.role}\"`,\n info.accessibility.accessibleName &&\n `aria-label=\"${info.accessibility.accessibleName}\"`,\n ]\n .filter(Boolean)\n .join(\", \");\n\n if (a11yContent) {\n chunks.push({\n id: \"element-a11y\",\n label: \"Accessibility\",\n content: a11yContent,\n type: \"element\",\n included: true,\n size: a11yContent.length,\n });\n }\n }\n\n if (info.boxModel) {\n const boxContent = `${Math.round(info.boxModel.content.width)}x${Math.round(\n info.boxModel.content.height,\n )}px`;\n chunks.push({\n id: \"element-dimensions\",\n label: \"Dimensions\",\n content: boxContent,\n type: \"element\",\n included: true,\n size: boxContent.length,\n });\n }\n } catch (error) {\n console.error(\"[useQuickChat] Failed to extract context:\", error);\n }\n\n return chunks;\n}\n\n/**\n * Builds the context string from included chunks.\n */\nexport function buildContextString(chunks: ContextChunk[]): string {\n const included = chunks.filter((c) => c.included);\n if (included.length === 0) return \"\";\n return included.map((c) => `[${c.label}]: ${c.content}`).join(\"\\n\");\n}\n","export type DebugInfo = {\n status: number;\n ok: boolean;\n contentType: string | null;\n rawTextPreview: string;\n parsedKeys?: string[];\n contentPreview?: string;\n payloadPreview?: string;\n timestamp: number;\n error?: string;\n};\n\nexport function createDebugInfo(args: {\n status: number;\n ok: boolean;\n contentType?: string | null;\n rawText?: string;\n error?: string;\n}): DebugInfo {\n return {\n status: args.status,\n ok: args.ok,\n contentType: args.contentType ?? null,\n rawTextPreview: args.rawText ?? \"\",\n timestamp: Date.now(),\n error: args.error,\n };\n}\n","import type { UIMessage } from \"@ai-sdk/react\";\nimport type { ChatMessage, QuickAction } from \"./types\";\n\ntype TextPartLike = {\n text?: unknown;\n content?: unknown;\n};\n\n/**\n * Extract text content from a UIMessage.\n *\n * The ai-sdk \"parts\" format can vary between versions (e.g. \"text\",\n * \"output_text\"). We treat any part with a string `text` or string `content`\n * field as displayable text.\n */\nexport function getUIMessageText(msg: UIMessage): string {\n const partsText =\n msg.parts\n ?.map((p) => {\n const part = p as unknown as TextPartLike;\n if (typeof part.text === \"string\") return part.text;\n if (typeof part.content === \"string\") return part.content;\n return \"\";\n })\n .join(\"\") ?? \"\";\n\n if (partsText) return partsText;\n\n const maybeContent = (msg as unknown as { content?: unknown }).content;\n return typeof maybeContent === \"string\" ? maybeContent : \"\";\n}\n\nexport function chatMessagesToUiMessages(messages: ChatMessage[]): UIMessage[] {\n return messages.map((msg) => ({\n id: msg.id,\n role: msg.role,\n parts: [{ type: \"text\" as const, text: msg.content }],\n }));\n}\n\nfunction safeCopyToClipboard(text: string) {\n try {\n if (typeof navigator === \"undefined\") return;\n void navigator.clipboard.writeText(text);\n } catch {\n // ignore\n }\n}\n\nexport function buildAssistantActions(\n messageText: string,\n setInput: (value: string) => void,\n): QuickAction[] {\n return [\n {\n id: \"copy\",\n label: \"Copy\",\n onClick: () => safeCopyToClipboard(messageText),\n },\n {\n id: \"research\",\n label: \"Research more\",\n onClick: () =>\n setInput(`Tell me more about: ${messageText.slice(0, 50)}`),\n },\n ];\n}\n\nexport function uiMessagesToChatMessages(args: {\n uiMessages: UIMessage[];\n status: string;\n setInput: (value: string) => void;\n}): ChatMessage[] {\n const { uiMessages, status, setInput } = args;\n const last = uiMessages[uiMessages.length - 1];\n\n return uiMessages.map((msg) => {\n const text = getUIMessageText(msg);\n const isStreaming =\n status === \"streaming\" && msg.role === \"assistant\" && msg === last;\n\n const actions =\n msg.role === \"assistant\" && status === \"ready\"\n ? buildAssistantActions(text, setInput)\n : undefined;\n\n return {\n id: msg.id,\n role: msg.role as \"user\" | \"assistant\" | \"system\",\n content: text,\n timestamp: Date.now(),\n isStreaming,\n actions,\n };\n });\n}\n","export type RateLimitNotice = {\n status: 429;\n message: string;\n retryAt?: number;\n retryAfterSeconds?: number;\n requestId?: string;\n endpoint?: string;\n raw?: string;\n};\n\ntype RateLimitPayload = {\n error?: string;\n message?: string;\n retryAfterSeconds?: number;\n retryAt?: number;\n requestId?: string;\n};\n\nfunction safeJsonParse(text: string): unknown {\n try {\n return JSON.parse(text);\n } catch {\n return null;\n }\n}\n\nexport function formatRetryAt(retryAtMs: number): string {\n try {\n const d = new Date(retryAtMs);\n return new Intl.DateTimeFormat(undefined, {\n hour: \"numeric\",\n minute: \"2-digit\",\n }).format(d);\n } catch {\n return new Date(retryAtMs).toLocaleTimeString();\n }\n}\n\nfunction getRequestIdFromHeaders(\n res: Response | undefined,\n): string | undefined {\n return (\n res?.headers?.get?.(\"X-Anyclick-Request-Id\") ??\n res?.headers?.get?.(\"x-anyclick-request-id\") ??\n undefined\n );\n}\n\nfunction parseRetryAfterSeconds(args: {\n payload: RateLimitPayload | null;\n res?: Response;\n}): number | undefined {\n const { payload, res } = args;\n if (typeof payload?.retryAfterSeconds === \"number\")\n return payload.retryAfterSeconds;\n const headerRetryAfter = res?.headers?.get?.(\"Retry-After\");\n if (!headerRetryAfter) return undefined;\n const n = Number(headerRetryAfter);\n return Number.isFinite(n) ? n : undefined;\n}\n\nfunction parseRetryAt(args: {\n payload: RateLimitPayload | null;\n retryAfterSeconds?: number;\n nowMs: number;\n}): number | undefined {\n const { payload, retryAfterSeconds, nowMs } = args;\n if (\n typeof payload?.retryAt === \"number\" &&\n Number.isFinite(payload.retryAt)\n ) {\n return payload.retryAt;\n }\n if (\n typeof retryAfterSeconds === \"number\" &&\n Number.isFinite(retryAfterSeconds)\n ) {\n return nowMs + Math.max(0, retryAfterSeconds) * 1000;\n }\n return undefined;\n}\n\nfunction buildNotice(args: {\n rawText: string;\n endpoint?: string;\n res?: Response;\n nowMs: number;\n}): RateLimitNotice {\n const { rawText, endpoint, res, nowMs } = args;\n\n const parsed = safeJsonParse(rawText);\n const payload =\n parsed && typeof parsed === \"object\" ? (parsed as RateLimitPayload) : null;\n\n const retryAfterSeconds = parseRetryAfterSeconds({ payload, res });\n const retryAt = parseRetryAt({ payload, retryAfterSeconds, nowMs });\n\n const timePart = retryAt ? `Try again at ${formatRetryAt(retryAt)}.` : \"\";\n const message = timePart ? `Rate limited. ${timePart}` : \"Rate limited.\";\n\n const requestId = payload?.requestId ?? getRequestIdFromHeaders(res);\n\n return {\n status: 429,\n message,\n retryAt,\n retryAfterSeconds,\n requestId,\n endpoint,\n raw: rawText,\n };\n}\n\n/**\n * Create a rate-limit notice from a 429 Response. This will consume the body.\n */\nexport async function rateLimitNoticeFromResponse(\n res: Response,\n endpoint?: string,\n): Promise<RateLimitNotice | null> {\n if (res.status !== 429) return null;\n const raw = await res.text().catch(() => \"\");\n return buildNotice({ rawText: raw, endpoint, res, nowMs: Date.now() });\n}\n\n/**\n * Create a rate-limit notice from an error object surfaced by ai-sdk.\n */\nexport function rateLimitNoticeFromError(args: {\n statusCode: number;\n response?: Response;\n responseText?: string;\n endpoint?: string;\n}): RateLimitNotice | null {\n const { statusCode, response, responseText, endpoint } = args;\n if (statusCode !== 429) return null;\n const raw = responseText ?? \"\";\n return buildNotice({\n rawText: raw,\n endpoint,\n res: response,\n nowMs: Date.now(),\n });\n}\n","\"use client\";\n\nimport React, { useMemo, useState } from \"react\";\nimport type { ScreenshotData, ScreenshotError } from \"@ewjdev/anyclick-core\";\nimport { estimateTotalSize, formatBytes } from \"@ewjdev/anyclick-core\";\nimport {\n AlertCircleIcon,\n CheckIcon,\n ExpandIcon,\n ImageIcon,\n Loader2Icon,\n RefreshCwIcon,\n ShrinkIcon,\n XIcon,\n} from \"lucide-react\";\nimport { menuStyles, screenshotPreviewStyles as styles } from \"./styles\";\nimport type { ScreenshotPreviewProps } from \"./types\";\n\n/** Screenshot preview tab types */\ntype TabType = \"container\" | \"element\" | \"viewport\";\n\n/**\n * Screenshot preview component - shows captured screenshots before sending.\n *\n * Displays a preview of captured screenshots with tabs for element, container,\n * and viewport captures. Allows users to review, retake, or proceed without\n * screenshots.\n *\n * @since 1.0.0\n */\nexport const ScreenshotPreview = React.memo(function ScreenshotPreview({\n isLoading,\n isSubmitting,\n onCancel,\n onConfirm,\n onRetake,\n screenshots,\n}: ScreenshotPreviewProps) {\n const [activeTab, setActiveTab] = useState<TabType>(\"element\");\n const [isExpanded, setIsExpanded] = useState(false);\n\n // Get error for a specific tab\n const getError = (key: TabType): ScreenshotError | undefined => {\n return screenshots?.errors?.[key];\n };\n\n // Memoize tabs computation\n const tabs = useMemo(() => {\n if (!screenshots) return [];\n\n const allTabs: {\n data: typeof screenshots.element;\n error?: ScreenshotError;\n key: TabType;\n label: string;\n }[] = [\n {\n data: screenshots.element,\n error: getError(\"element\"),\n key: \"element\" as const,\n label: \"Element\",\n },\n {\n data: screenshots.container,\n error: getError(\"container\"),\n key: \"container\" as const,\n label: \"Container\",\n },\n {\n data: screenshots.viewport,\n error: getError(\"viewport\"),\n key: \"viewport\" as const,\n label: \"Viewport\",\n },\n ];\n\n // Show tabs that have either data or errors\n return allTabs.filter((tab) => tab.data || tab.error);\n }, [screenshots]);\n\n // Memoize total size calculation\n const totalSize = useMemo(\n () => (screenshots ? estimateTotalSize(screenshots) : 0),\n [screenshots],\n );\n\n if (isLoading) {\n return (\n <div style={styles.container}>\n <div style={styles.loadingContainer}>\n <Loader2Icon\n className=\"w-6 h-6 animate-spin\"\n style={{ color: \"#3b82f6\" }}\n />\n <span style={styles.loadingText}>Capturing screenshots...</span>\n </div>\n </div>\n );\n }\n\n if (!screenshots) {\n return (\n <div style={styles.container}>\n <div style={styles.emptyContainer}>\n <ImageIcon className=\"w-8 h-8\" style={{ color: \"#9ca3af\" }} />\n <span style={styles.emptyText}>Screenshots unavailable</span>\n <span style={styles.emptySubtext}>\n Some elements can&apos;t be captured (e.g., gradient text)\n </span>\n <div style={styles.emptyActions}>\n <button\n type=\"button\"\n disabled={isSubmitting}\n onClick={onRetake}\n style={styles.retakeButtonOutline}\n >\n <RefreshCwIcon className=\"w-4 h-4\" />\n Try Again\n </button>\n <button\n type=\"button\"\n disabled={isSubmitting}\n onClick={() =>\n onConfirm({ capturedAt: new Date().toISOString() })\n }\n style={styles.continueButton}\n >\n <CheckIcon className=\"w-4 h-4\" />\n Continue Without\n </button>\n </div>\n </div>\n </div>\n );\n }\n\n const activeScreenshot =\n activeTab === \"element\"\n ? screenshots.element\n : activeTab === \"container\"\n ? screenshots.container\n : screenshots.viewport;\n\n const activeError = getError(activeTab);\n\n return (\n <div\n style={{\n ...styles.container,\n ...(isExpanded ? styles.containerExpanded : {}),\n padding: \"8px\",\n }}\n >\n <div style={styles.header}>\n <span style={styles.headerTitle}>Review Screenshots</span>\n <div style={styles.headerActions}>\n <span style={styles.sizeLabel}>{formatBytes(totalSize)}</span>\n <button\n type=\"button\"\n onClick={() => setIsExpanded(!isExpanded)}\n style={styles.iconButton}\n title={isExpanded ? \"Collapse\" : \"Expand\"}\n >\n {isExpanded ? (\n <ShrinkIcon className=\"w-4 h-4\" />\n ) : (\n <ExpandIcon className=\"w-4 h-4\" />\n )}\n </button>\n </div>\n </div>\n\n {/* Tabs */}\n <div style={styles.tabContainer}>\n {tabs.map((tab) => (\n <button\n key={tab.key}\n type=\"button\"\n onClick={() => setActiveTab(tab.key)}\n style={{\n ...styles.tab,\n ...(activeTab === tab.key ? styles.tabActive : {}),\n ...(tab.error && !tab.data ? styles.tabError : {}),\n }}\n >\n {tab.error && !tab.data && (\n <AlertCircleIcon\n className=\"w-3 h-3\"\n style={{ color: \"#ef4444\" }}\n />\n )}\n {tab.label}\n {tab.data && (\n <span style={styles.tabSize}>\n {formatBytes(tab.data.sizeBytes)}\n </span>\n )}\n </button>\n ))}\n </div>\n\n {/* Preview image */}\n <div\n style={{\n ...styles.previewContainer,\n ...(isExpanded ? styles.previewContainerExpanded : {}),\n }}\n >\n {activeScreenshot ? (\n <img\n alt={`${activeTab} screenshot`}\n src={activeScreenshot.dataUrl}\n style={styles.previewImage}\n />\n ) : activeError ? (\n <div style={styles.errorPreview}>\n <AlertCircleIcon className=\"w-8 h-8\" style={{ color: \"#ef4444\" }} />\n <span style={styles.errorTitle}>Capture Failed</span>\n <span style={styles.errorMessage}>{activeError.message}</span>\n </div>\n ) : (\n <div style={styles.noPreview}>\n <ImageIcon className=\"w-6 h-6\" style={{ color: \"#9ca3af\" }} />\n <span>No {activeTab} screenshot</span>\n </div>\n )}\n </div>\n\n {/* Dimensions info */}\n {activeScreenshot && (\n <div style={styles.dimensionsInfo}>\n {activeScreenshot.width} × {activeScreenshot.height}px\n </div>\n )}\n\n {/* Actions */}\n <div style={styles.actions}>\n <button\n type=\"button\"\n disabled={isSubmitting}\n onClick={onRetake}\n style={styles.retakeButtonSmall}\n >\n <RefreshCwIcon className=\"w-3 h-3\" />\n Retake\n </button>\n <div style={styles.actionsRight}>\n <button\n type=\"button\"\n className=\"flex items-center gap-1\"\n disabled={isSubmitting}\n onClick={onCancel}\n style={{ ...menuStyles.button, ...menuStyles.cancelButton }}\n >\n <XIcon className=\"w-3 h-3\" />\n Cancel\n </button>\n <button\n type=\"button\"\n disabled={isSubmitting}\n onClick={() => onConfirm(screenshots)}\n style={{\n ...menuStyles.button,\n ...menuStyles.submitButton,\n ...(isSubmitting ? menuStyles.submitButtonDisabled : {}),\n }}\n >\n {isSubmitting ? (\n <>\n <Loader2Icon className=\"w-3 h-3 animate-spin\" />\n Sending...\n </>\n ) : (\n <>\n <CheckIcon className=\"w-3 h-3\" />\n Send\n </>\n )}\n </button>\n </div>\n </div>\n </div>\n );\n});\n","/**\n * Style definitions for anyclick-react components.\n *\n * This module provides consolidated styling for all UI components,\n * including CSS custom properties for theming and dark mode support.\n *\n * @module styles\n * @since 1.0.0\n */\nimport type { CSSProperties } from \"react\";\n\n// ============================================================================\n// CSS Custom Properties\n// ============================================================================\n\n/**\n * CSS custom properties for menu theming.\n *\n * These can be overridden via the `style` prop on AnyclickProvider.\n *\n * @example\n * ```tsx\n * <AnyclickProvider\n * theme={{\n * menuStyle: {\n * '--anyclick-menu-bg': 'rgba(0, 0, 0, 0.9)',\n * '--anyclick-menu-text': '#ffffff',\n * '--anyclick-menu-border': 'rgba(255, 255, 255, 0.1)',\n * '--anyclick-menu-hover': 'rgba(255, 255, 255, 0.1)',\n * '--anyclick-menu-accent': '#f59e0b',\n * }\n * }}\n * />\n * ```\n *\n * @since 1.0.0\n */\nexport const menuCSSVariables = {\n \"--anyclick-menu-accent\": \"#0066cc\",\n \"--anyclick-menu-accent-text\": \"#ffffff\",\n \"--anyclick-menu-bg\": \"#ffffff\",\n \"--anyclick-menu-border\": \"#e5e5e5\",\n \"--anyclick-menu-cancel-bg\": \"#f0f0f0\",\n \"--anyclick-menu-cancel-text\": \"#666666\",\n \"--anyclick-menu-hover\": \"#f5f5f5\",\n \"--anyclick-menu-input-bg\": \"#ffffff\",\n \"--anyclick-menu-input-border\": \"#dddddd\",\n \"--anyclick-menu-text\": \"#333333\",\n \"--anyclick-menu-text-muted\": \"#666666\",\n} as const;\n\n// ============================================================================\n// Badge Styles\n// ============================================================================\n\n/**\n * Badge tone color configuration.\n * @internal\n */\nconst badgeToneColors = {\n info: {\n backgroundColor: \"rgba(59, 130, 246, 0.15)\",\n border: \"1px solid rgba(59, 130, 246, 0.3)\",\n color: \"#60a5fa\",\n },\n neutral: {\n backgroundColor: \"rgba(148, 163, 184, 0.15)\",\n border: \"1px solid rgba(148, 163, 184, 0.3)\",\n color: \"#cbd5e1\",\n },\n success: {\n backgroundColor: \"rgba(34, 197, 94, 0.15)\",\n border: \"1px solid rgba(34, 197, 94, 0.3)\",\n color: \"#4ade80\",\n },\n warning: {\n backgroundColor: \"rgba(251, 191, 36, 0.15)\",\n border: \"1px solid rgba(251, 191, 36, 0.3)\",\n color: \"#fbbf24\",\n },\n} as const;\n\n/**\n * Gets badge styles for a specific tone.\n *\n * @param tone - The badge tone (info, neutral, success, warning)\n * @returns CSSProperties for the badge\n *\n * @example\n * ```tsx\n * const style = getBadgeStyle(\"success\");\n * // => { backgroundColor: \"rgba(34, 197, 94, 0.15)\", ... }\n * ```\n *\n * @since 1.2.0\n */\nexport function getBadgeStyle(\n tone: \"info\" | \"neutral\" | \"success\" | \"warning\" = \"neutral\",\n): CSSProperties {\n const toneColors = badgeToneColors[tone];\n return {\n alignItems: \"center\",\n backgroundColor: toneColors.backgroundColor,\n border: toneColors.border,\n borderRadius: \"9999px\",\n color: toneColors.color,\n display: \"inline-flex\",\n fontSize: \"10px\",\n lineHeight: 1.2,\n padding: \"2px 6px\",\n };\n}\n\n// ============================================================================\n// Menu Styles\n// ============================================================================\n\n/**\n * Core menu component styles.\n *\n * @since 1.0.0\n */\nexport const menuStyles: Record<string, CSSProperties> = {\n backButton: {\n borderBottom: \"1px solid var(--anyclick-menu-border, #e5e5e5)\",\n marginBottom: \"4px\",\n minHeight: \"44px\",\n },\n button: {\n border: \"none\",\n borderRadius: \"6px\",\n cursor: \"pointer\",\n fontSize: \"13px\",\n fontWeight: 500,\n padding: \"6px 12px\",\n transition: \"background-color 0.15s, opacity 0.15s\",\n },\n buttonRow: {\n display: \"flex\",\n gap: \"8px\",\n justifyContent: \"flex-end\",\n marginTop: \"8px\",\n },\n cancelButton: {\n alignItems: \"center\",\n backgroundColor: \"var(--anyclick-menu-cancel-bg, #f0f0f0)\",\n color: \"var(--anyclick-menu-cancel-text, #666)\",\n display: \"flex\",\n gap: \"2px\",\n },\n commentInput: {\n backgroundColor: \"var(--anyclick-menu-input-bg, #ffffff)\",\n border: \"1px solid var(--anyclick-menu-input-border, #ddd)\",\n borderRadius: \"6px\",\n boxSizing: \"border-box\" as const,\n color: \"var(--anyclick-menu-text, #333)\",\n fontFamily: \"inherit\",\n fontSize: \"14px\",\n minHeight: \"60px\",\n outline: \"none\",\n padding: \"8px 12px\",\n resize: \"vertical\" as const,\n width: \"100%\",\n },\n commentSection: {\n borderTop: \"1px solid var(--anyclick-menu-border, #e5e5e5)\",\n padding: \"12px 16px\",\n },\n container: {\n backgroundColor: \"var(--anyclick-menu-bg, #ffffff)\",\n borderRadius: \"8px\",\n boxShadow: \"0 4px 12px rgba(0, 0, 0, 0.15), 0 0 0 1px rgba(0, 0, 0, 0.05)\",\n fontFamily:\n '-apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, sans-serif',\n fontSize: \"14px\",\n minWidth: \"200px\",\n overflow: \"hidden\",\n position: \"fixed\",\n zIndex: 9999,\n ...menuCSSVariables,\n },\n dragHandle: {\n alignItems: \"center\",\n borderRadius: \"4px\",\n display: \"flex\",\n marginRight: \"-4px\",\n opacity: 0.5,\n padding: \"4px\",\n transition: \"opacity 0.15s\",\n },\n header: {\n alignItems: \"center\",\n borderBottom: \"1px solid var(--anyclick-menu-border, #e5e5e5)\",\n color: \"var(--anyclick-menu-text-muted, #666)\",\n display: \"flex\",\n fontSize: \"12px\",\n fontWeight: 500,\n justifyContent: \"space-between\",\n letterSpacing: \"0.5px\",\n padding: \"8px 12px\",\n textTransform: \"uppercase\" as const,\n },\n item: {\n alignItems: \"center\",\n backgroundColor: \"transparent\",\n border: \"none\",\n color: \"var(--anyclick-menu-text, #333)\",\n cursor: \"pointer\",\n display: \"flex\",\n fontSize: \"14px\",\n gap: \"10px\",\n padding: \"10px 16px\",\n textAlign: \"left\" as const,\n transition: \"background-color 0.15s\",\n width: \"100%\",\n },\n itemDisabled: {\n cursor: \"not-allowed\",\n opacity: 0.5,\n },\n itemHover: {\n backgroundColor: \"var(--anyclick-menu-hover, #f5f5f5)\",\n },\n itemIcon: {\n alignItems: \"center\",\n display: \"flex\",\n fontSize: \"16px\",\n height: \"20px\",\n justifyContent: \"center\",\n width: \"20px\",\n },\n itemLabel: {\n alignItems: \"center\",\n display: \"inline-flex\",\n flex: 1,\n gap: \"8px\",\n },\n itemList: {\n padding: \"0px 0px\",\n },\n overlay: {\n inset: 0,\n position: \"fixed\",\n zIndex: 9998,\n },\n screenshotIndicator: {\n display: \"flex\",\n flex: 1,\n justifyContent: \"flex-end\",\n marginLeft: \"4px\",\n opacity: 0.7,\n },\n submenuIcon: {\n marginLeft: \"auto\",\n opacity: 0.5,\n },\n submitButton: {\n alignItems: \"center\",\n backgroundColor: \"var(--anyclick-menu-accent, #0066cc)\",\n color: \"var(--anyclick-menu-accent-text, #ffffff)\",\n display: \"flex\",\n gap: \"2px\",\n },\n submitButtonDisabled: {\n cursor: \"not-allowed\",\n opacity: 0.6,\n },\n touchFriendly: {\n minHeight: \"38px\",\n userSelect: \"none\",\n WebkitTouchCallout: \"none\",\n WebkitUserSelect: \"none\",\n },\n};\n\n// ============================================================================\n// Dark Mode Styles\n// ============================================================================\n\n/**\n * Dark mode menu styles.\n *\n * Apply these styles for dark theme support.\n *\n * @since 1.0.0\n */\nexport const darkMenuStyles: Record<string, CSSProperties> = {\n cancelButton: {\n ...menuStyles.cancelButton,\n backgroundColor: \"#333\",\n color: \"#ccc\",\n },\n commentInput: {\n ...menuStyles.commentInput,\n backgroundColor: \"#2a2a2a\",\n border: \"1px solid #444\",\n color: \"#e0e0e0\",\n },\n commentSection: {\n ...menuStyles.commentSection,\n borderTop: \"1px solid #333\",\n },\n container: {\n ...menuStyles.container,\n backgroundColor: \"#1a1a1a\",\n boxShadow:\n \"0 4px 12px rgba(0, 0, 0, 0.4), 0 0 0 1px rgba(255, 255, 255, 0.1)\",\n },\n header: {\n ...menuStyles.header,\n borderBottom: \"1px solid #333\",\n color: \"#888\",\n },\n item: {\n ...menuStyles.item,\n color: \"#e0e0e0\",\n },\n itemHover: {\n backgroundColor: \"#2a2a2a\",\n },\n};\n\n// ============================================================================\n// Screenshot Preview Styles\n// ============================================================================\n\n/**\n * Screenshot preview component styles.\n *\n * @since 1.0.0\n */\nexport const screenshotPreviewStyles: Record<string, CSSProperties> = {\n actions: {\n alignItems: \"center\",\n borderTop: \"1px solid #e5e7eb\",\n display: \"flex\",\n justifyContent: \"space-between\",\n paddingTop: \"8px\",\n },\n actionsRight: {\n display: \"flex\",\n gap: \"8px\",\n },\n container: {\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"8px\",\n width: \"100%\",\n },\n containerExpanded: {\n backgroundColor: \"#fff\",\n borderRadius: \"12px\",\n boxShadow: \"0 25px 50px -12px rgba(0, 0, 0, 0.25)\",\n left: \"50%\",\n maxHeight: \"90vh\",\n maxWidth: \"800px\",\n padding: \"16px\",\n position: \"fixed\",\n top: \"50%\",\n transform: \"translate(-50%, -50%)\",\n width: \"90vw\",\n zIndex: 10000,\n },\n continueButton: {\n alignItems: \"center\",\n backgroundColor: \"#3b82f6\",\n border: \"none\",\n borderRadius: \"6px\",\n color: \"#fff\",\n cursor: \"pointer\",\n display: \"flex\",\n fontSize: \"12px\",\n fontWeight: \"500\",\n gap: \"6px\",\n padding: \"8px 12px\",\n },\n dimensionsInfo: {\n color: \"#9ca3af\",\n fontSize: \"11px\",\n textAlign: \"center\" as const,\n },\n emptyActions: {\n display: \"flex\",\n gap: \"8px\",\n marginTop: \"8px\",\n },\n emptyContainer: {\n alignItems: \"center\",\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"8px\",\n justifyContent: \"center\",\n padding: \"24px\",\n },\n emptySubtext: {\n color: \"#9ca3af\",\n fontSize: \"11px\",\n textAlign: \"center\" as const,\n },\n emptyText: {\n color: \"#6b7280\",\n fontSize: \"13px\",\n fontWeight: \"500\",\n },\n errorMessage: {\n color: \"#6b7280\",\n fontSize: \"12px\",\n lineHeight: \"1.4\",\n maxWidth: \"250px\",\n },\n errorPreview: {\n alignItems: \"center\",\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"8px\",\n justifyContent: \"center\",\n padding: \"16px\",\n textAlign: \"center\" as const,\n },\n errorTitle: {\n color: \"#ef4444\",\n fontSize: \"14px\",\n fontWeight: \"600\",\n },\n header: {\n alignItems: \"center\",\n display: \"flex\",\n justifyContent: \"space-between\",\n padding: \"0 4px\",\n },\n headerActions: {\n alignItems: \"center\",\n display: \"flex\",\n gap: \"8px\",\n },\n headerTitle: {\n color: \"#374151\",\n fontSize: \"12px\",\n fontWeight: \"600\",\n letterSpacing: \"0.05em\",\n textTransform: \"uppercase\" as const,\n },\n iconButton: {\n alignItems: \"center\",\n backgroundColor: \"transparent\",\n border: \"none\",\n borderRadius: \"4px\",\n color: \"#6b7280\",\n cursor: \"pointer\",\n display: \"flex\",\n height: \"24px\",\n justifyContent: \"center\",\n width: \"24px\",\n },\n loadingContainer: {\n alignItems: \"center\",\n display: \"flex\",\n flexDirection: \"column\",\n gap: \"12px\",\n justifyContent: \"center\",\n padding: \"24px\",\n },\n loadingText: {\n color: \"#6b7280\",\n fontSize: \"13px\",\n },\n noPreview: {\n alignItems: \"center\",\n color: \"#9ca3af\",\n display: \"flex\",\n flexDirection: \"column\",\n fontSize: \"12px\",\n gap: \"8px\",\n },\n previewContainer: {\n alignItems: \"center\",\n backgroundColor: \"#f9fafb\",\n borderRadius: \"8px\",\n display: \"flex\",\n height: \"150px\",\n justifyContent: \"center\",\n overflow: \"hidden\",\n position: \"relative\",\n width: \"100%\",\n },\n previewContainerExpanded: {\n height: \"60vh\",\n maxHeight: \"500px\",\n },\n previewImage: {\n maxHeight: \"100%\",\n maxWidth: \"100%\",\n objectFit: \"contain\",\n },\n retakeButton: {\n alignItems: \"center\",\n backgroundColor: \"#3b82f6\",\n border: \"none\",\n borderRadius: \"6px\",\n color: \"#fff\",\n cursor: \"pointer\",\n display: \"flex\",\n fontSize: \"13px\",\n fontWeight: \"500\",\n gap: \"6px\",\n padding: \"8px 16px\",\n },\n retakeButtonOutline: {\n alignItems: \"center\",\n backgroundColor: \"transparent\",\n border: \"1px solid #e5e7eb\",\n borderRadius: \"6px\",\n color: \"#6b7280\",\n cursor: \"pointer\",\n display: \"flex\",\n fontSize: \"12px\",\n gap: \"6px\",\n padding: \"8px 12px\",\n },\n retakeButtonSmall: {\n alignItems: \"center\",\n backgroundColor: \"transparent\",\n border: \"1px solid #e5e7eb\",\n borderRadius: \"4px\",\n color: \"#6b7280\",\n cursor: \"pointer\",\n display: \"flex\",\n fontSize: \"11px\",\n gap: \"4px\",\n padding: \"4px 8px\",\n },\n sizeLabel: {\n color: \"#9ca3af\",\n fontSize: \"11px\",\n },\n tab: {\n alignItems: \"center\",\n backgroundColor: \"transparent\",\n border: \"none\",\n borderRadius: \"4px\",\n color: \"#6b7280\",\n cursor: \"pointer\",\n display: \"flex\",\n fontSize: \"12px\",\n gap: \"4px\",\n padding: \"2px 5px\",\n transition: \"all 0.15s ease\",\n },\n tabActive: {\n backgroundColor: \"#eff6ff\",\n color: \"#3b82f6\",\n fontWeight: \"500\",\n },\n tabContainer: {\n borderBottom: \"1px solid #e5e7eb\",\n display: \"flex\",\n gap: \"4px\",\n paddingBottom: \"8px\",\n },\n tabError: {\n color: \"#ef4444\",\n },\n tabSize: {\n color: \"#9ca3af\",\n fontSize: \"10px\",\n },\n};\n","/**\n * Highlight utilities for feedback target elements.\n *\n * Provides functions to visually highlight DOM elements during feedback selection.\n * Highlights are applied using CSS classes and dynamically generated styles.\n *\n * @module highlight\n * @since 1.0.0\n */\nimport type { HighlightColors, HighlightConfig } from \"./types\";\n\n/** CSS class applied to highlighted target elements */\nconst HIGHLIGHT_TARGET_CLASS = \"uifeedback-highlight-target\";\n\n/** CSS class applied to highlighted container elements */\nconst HIGHLIGHT_CONTAINER_CLASS = \"uifeedback-highlight-container\";\n\n/** ID of the dynamically injected style element */\nconst STYLE_ID = \"uifeedback-highlight-styles\";\n\n/**\n * Default highlight colors used when no custom colors are specified.\n *\n * @example\n * ```ts\n * // Override specific colors\n * const customColors = {\n * ...defaultHighlightColors,\n * targetColor: \"#ef4444\", // Red instead of blue\n * };\n * ```\n *\n * @since 1.0.0\n */\nexport const defaultHighlightColors: Required<HighlightColors> = {\n containerColor: \"#8b5cf6\",\n containerShadowOpacity: 0.1,\n targetColor: \"#3b82f6\",\n targetShadowOpacity: 0.25,\n};\n\n/**\n * Default CSS selectors used to identify container elements.\n *\n * These selectors are checked when traversing up the DOM tree to find\n * a suitable container element to highlight alongside the target.\n *\n * @example\n * ```ts\n * // Add custom selectors\n * const customSelectors = [\n * ...defaultContainerSelectors,\n * \"[data-component]\",\n * \".my-custom-container\",\n * ];\n * ```\n *\n * @since 1.0.0\n */\nexport const defaultContainerSelectors: string[] = [\n \".box\",\n \".card\",\n \".container\",\n \".dialog\",\n \".drawer\",\n \".modal\",\n \".panel\",\n \".section\",\n \".wrapper\",\n '[role=\"article\"]',\n '[role=\"dialog\"]',\n '[role=\"main\"]',\n '[role=\"region\"]',\n \"article\",\n \"aside\",\n \"footer\",\n \"header\",\n \"main\",\n \"nav\",\n \"section\",\n];\n\n/**\n * Generates CSS for highlight effects based on color configuration.\n *\n * @param colors - The highlight color configuration\n * @returns CSS string to be injected into the document\n * @internal\n */\nfunction generateHighlightCSS(colors: Required<HighlightColors>): string {\n const {\n containerColor,\n containerShadowOpacity,\n targetColor,\n targetShadowOpacity,\n } = colors;\n\n /**\n * Converts a hex color to rgba format.\n * @param hex - Hex color string (with or without #)\n * @param alpha - Alpha transparency value\n */\n const hexToRgba = (hex: string, alpha: number): string => {\n const result = /^#?([a-f\\d]{2})([a-f\\d]{2})([a-f\\d]{2})$/i.exec(hex);\n if (!result) return `rgba(0, 0, 0, ${alpha})`;\n return `rgba(${parseInt(result[1], 16)}, ${parseInt(result[2], 16)}, ${parseInt(result[3], 16)}, ${alpha})`;\n };\n\n return `\n.${HIGHLIGHT_TARGET_CLASS} {\n border-radius: 4px !important;\n box-shadow: 0 0 0 4px ${hexToRgba(targetColor, targetShadowOpacity)}, 0 4px 12px ${hexToRgba(targetColor, targetShadowOpacity * 0.6)} !important;\n outline: 2px dashed ${targetColor} !important;\n outline-offset: 2px !important;\n position: relative;\n top: 0;\n z-index: 9997;\n}\n\n/* SVG elements need special handling - don't apply styles that break their rendering */\nsvg.${HIGHLIGHT_TARGET_CLASS},\n.${HIGHLIGHT_TARGET_CLASS} > svg {\n border-radius: 0 !important;\n box-shadow: none !important;\n outline: none !important;\n position: static !important;\n z-index: auto !important;\n}\n\n.${HIGHLIGHT_CONTAINER_CLASS} {\n border-radius: 6px !important;\n box-shadow: 0 0 0 6px ${hexToRgba(containerColor, containerShadowOpacity)} !important;\n outline: 2px dashed ${hexToRgba(containerColor, 0.6)} !important;\n outline-offset: 4px !important;\n position: relative;\n z-index: 9996;\n}\n\n/* SVG elements in containers also need protection */\nsvg.${HIGHLIGHT_CONTAINER_CLASS},\n.${HIGHLIGHT_CONTAINER_CLASS} > svg {\n border-radius: 0 !important;\n box-shadow: none !important;\n outline: none !important;\n position: static !important;\n z-index: auto !important;\n}\n`;\n}\n\n/**\n * Injects or updates highlight styles in the document head.\n *\n * @param colors - The highlight color configuration\n * @internal\n */\nfunction injectStyles(colors: Required<HighlightColors>): void {\n if (typeof document === \"undefined\") return;\n\n // Remove existing styles if present\n const existingStyle = document.getElementById(STYLE_ID);\n if (existingStyle) {\n existingStyle.remove();\n }\n\n const style = document.createElement(\"style\");\n style.id = STYLE_ID;\n style.textContent = generateHighlightCSS(colors);\n document.head.appendChild(style);\n}\n\n/**\n * Finds the closest container parent element for a given target element.\n *\n * Traverses up the DOM tree looking for elements that match container selectors\n * or have multiple meaningful child elements.\n *\n * @param element - The target element to find a container for\n * @param config - Optional highlight configuration with custom selectors\n * @returns The found container element, or null if none found\n *\n * @example\n * ```ts\n * const target = document.querySelector(\".my-button\");\n * const container = findContainerParent(target, {\n * containerSelectors: [\".card\", \".panel\"],\n * minChildrenForContainer: 3,\n * });\n * ```\n *\n * @since 1.0.0\n */\nexport function findContainerParent(\n element: Element,\n config?: HighlightConfig,\n): Element | null {\n const containerSelectors =\n config?.containerSelectors ?? defaultContainerSelectors;\n const minChildren = config?.minChildrenForContainer ?? 2;\n\n let current = element.parentElement;\n let fallbackContainer: Element | null = null;\n\n while (current && current !== document.body) {\n // Check if element matches any container selector\n for (const selector of containerSelectors) {\n try {\n if (current.matches(selector)) {\n return current;\n }\n } catch {\n // Invalid selector, skip\n }\n }\n\n // Check if parent has multiple meaningful children (not just text nodes)\n const meaningfulChildren = Array.from(current.children).filter((child) => {\n const tag = child.tagName.toLowerCase();\n // Exclude script, style, and hidden elements\n if (tag === \"script\" || tag === \"style\" || tag === \"noscript\") {\n return false;\n }\n // Check if element is visible\n const style = window.getComputedStyle(child);\n if (style.display === \"none\" || style.visibility === \"hidden\") {\n return false;\n }\n return true;\n });\n\n // If this parent has enough children, it's likely a container\n if (meaningfulChildren.length >= minChildren && !fallbackContainer) {\n fallbackContainer = current;\n }\n\n // If parent has 3+ children, strongly consider it a container\n if (meaningfulChildren.length >= 3) {\n return current;\n }\n\n current = current.parentElement;\n }\n\n return fallbackContainer;\n}\n\n/**\n * Applies highlight styling to a target element.\n *\n * Injects the necessary CSS styles and adds the highlight class to the element.\n *\n * @param element - The element to highlight\n * @param colors - Optional custom highlight colors\n *\n * @example\n * ```ts\n * const target = document.querySelector(\".my-button\");\n * highlightTarget(target, { targetColor: \"#ef4444\" });\n * ```\n *\n * @since 1.0.0\n */\nexport function highlightTarget(\n element: Element,\n colors?: HighlightColors,\n): void {\n const mergedColors = { ...defaultHighlightColors, ...colors };\n injectStyles(mergedColors);\n element.classList.add(HIGHLIGHT_TARGET_CLASS);\n}\n\n/**\n * Applies highlight styling to a container element.\n *\n * Container highlights are visually distinct from target highlights,\n * typically with a larger outline offset and different color.\n *\n * @param element - The container element to highlight\n * @param colors - Optional custom highlight colors\n *\n * @example\n * ```ts\n * const container = document.querySelector(\".card\");\n * highlightContainer(container, { containerColor: \"#22c55e\" });\n * ```\n *\n * @since 1.0.0\n */\nexport function highlightContainer(\n element: Element,\n colors?: HighlightColors,\n): void {\n const mergedColors = { ...defaultHighlightColors, ...colors };\n injectStyles(mergedColors);\n element.classList.add(HIGHLIGHT_CONTAINER_CLASS);\n}\n\n/**\n * Removes all highlight styling from the document.\n *\n * Clears both target and container highlights from all elements.\n *\n * @example\n * ```ts\n * // Remove highlights when closing the context menu\n * clearHighlights();\n * ```\n *\n * @since 1.0.0\n */\nexport function clearHighlights(): void {\n if (typeof document === \"undefined\") return;\n\n document.querySelectorAll(`.${HIGHLIGHT_TARGET_CLASS}`).forEach((el) => {\n el.classList.remove(HIGHLIGHT_TARGET_CLASS);\n });\n\n document.querySelectorAll(`.${HIGHLIGHT_CONTAINER_CLASS}`).forEach((el) => {\n el.classList.remove(HIGHLIGHT_CONTAINER_CLASS);\n });\n}\n\n/**\n * Applies highlights to both a target element and its container parent.\n *\n * This is the main function for applying highlights during feedback selection.\n * It automatically finds the container parent and applies appropriate styling.\n *\n * @param targetElement - The element to highlight as the target\n * @param config - Optional highlight configuration\n * @returns Object containing the target and container elements\n *\n * @example\n * ```ts\n * const result = applyHighlights(clickedElement, {\n * enabled: true,\n * colors: { targetColor: \"#3b82f6\", containerColor: \"#8b5cf6\" },\n * containerSelectors: [\".card\", \".modal\"],\n * });\n *\n * console.log(result.target); // The highlighted target\n * console.log(result.container); // The highlighted container (or null)\n * ```\n *\n * @since 1.0.0\n */\nexport function applyHighlights(\n targetElement: Element,\n config?: HighlightConfig,\n): {\n container: Element | null;\n target: Element;\n} {\n // If highlights are disabled, don't apply anything\n if (config?.enabled === false) {\n return { container: null, target: targetElement };\n }\n\n clearHighlights();\n\n const colors = { ...defaultHighlightColors, ...config?.colors };\n\n highlightTarget(targetElement, colors);\n\n const container = findContainerParent(targetElement, config);\n if (container && container !== targetElement) {\n highlightContainer(container, colors);\n }\n\n return { container, target: targetElement };\n}\n","\"use client\";\n\nimport { createContext, useContext } from \"react\";\nimport type { AnyclickContextValue } from \"./types\";\n\n/**\n * React context for anyclick functionality.\n *\n * Provides access to anyclick state and methods throughout the component tree.\n * Use the {@link useAnyclick} hook for type-safe access.\n *\n * @example\n * ```tsx\n * // Using the context directly (advanced)\n * const context = useContext(AnyclickContext);\n * if (context) {\n * context.openMenu(element, { x: 100, y: 100 });\n * }\n * ```\n *\n * @see {@link useAnyclick} for the recommended way to access this context\n * @since 1.0.0\n */\nexport const AnyclickContext = createContext<AnyclickContextValue | null>(null);\n\n/**\n * @deprecated Use {@link AnyclickContext} instead. Will be removed in v2.0.0.\n * @see {@link AnyclickContext}\n */\nexport const FeedbackContext = AnyclickContext;\n\n/**\n * Hook to access anyclick context values and methods.\n *\n * Provides access to:\n * - `isEnabled` - Whether anyclick is currently enabled\n * - `isSubmitting` - Whether a submission is in progress\n * - `submitAnyclick` - Function to submit feedback programmatically\n * - `openMenu` - Function to open the context menu programmatically\n * - `closeMenu` - Function to close the context menu\n * - `theme` - The current merged theme configuration\n * - `scoped` - Whether the current provider is scoped\n * - `providerId` - The unique ID of the current provider\n *\n * @returns {AnyclickContextValue} The anyclick context value\n * @throws {Error} When used outside of an AnyclickProvider\n *\n * @example\n * ```tsx\n * function FeedbackButton() {\n * const { openMenu, isSubmitting, isEnabled } = useAnyclick();\n *\n * const handleClick = (event: React.MouseEvent) => {\n * if (isEnabled && !isSubmitting) {\n * openMenu(event.currentTarget, {\n * x: event.clientX,\n * y: event.clientY,\n * });\n * }\n * };\n *\n * return (\n * <button onClick={handleClick} disabled={!isEnabled || isSubmitting}>\n * Send Feedback\n * </button>\n * );\n * }\n * ```\n *\n * @since 1.0.0\n */\nexport function useAnyclick(): AnyclickContextValue {\n const context = useContext(AnyclickContext);\n if (!context) {\n throw new Error(\"useAnyclick must be used within an AnyclickProvider\");\n }\n return context;\n}\n\n/**\n * @deprecated Use {@link useAnyclick} instead. Will be removed in v2.0.0.\n * @see {@link useAnyclick}\n */\nexport function useFeedback(): AnyclickContextValue {\n const context = useContext(AnyclickContext);\n if (!context) {\n throw new Error(\"useFeedback must be used within a FeedbackProvider\");\n }\n return context;\n}\n","/**\n * Provider registry store for managing anyclick provider instances.\n *\n * Uses Zustand to maintain a global registry of all AnyclickProvider instances,\n * enabling features like nested providers, theme inheritance, and scoped contexts.\n *\n * @module store\n * @since 1.0.0\n */\n\"use client\";\n\nimport type { AnyclickMenuEvent } from \"@ewjdev/anyclick-core\";\nimport { create } from \"zustand\";\nimport type { AnyclickTheme } from \"./types\";\n\n/**\n * Registered provider instance in the provider registry.\n *\n * Each AnyclickProvider creates an instance of this type when mounted,\n * enabling the store to track and manage provider hierarchies.\n *\n * @since 1.0.0\n */\nexport interface ProviderInstance {\n /** Reference to the provider's container element (null if not scoped) */\n containerRef: React.RefObject<Element | null>;\n /** Depth in the provider hierarchy (0 = root) */\n depth: number;\n /** Whether this provider is disabled */\n disabled: boolean;\n /** Unique identifier for this provider instance */\n id: string;\n /** Handler to call when an event occurs in this provider's scope */\n onContextMenu?: (\n event: AnyclickMenuEvent,\n element: Element,\n ) => boolean | void;\n /** Parent provider ID (if nested) */\n parentId: string | null;\n /** Whether this provider is scoped to its container */\n scoped: boolean;\n /** The provider's theme configuration */\n theme: AnyclickTheme | null;\n}\n\n/**\n * Provider registry store state and actions.\n * @internal\n */\ninterface ProviderStore {\n /** Map of provider ID to provider instance */\n providers: Map<string, ProviderInstance>;\n\n /**\n * Finds all providers that contain a given element, sorted by depth (nearest first).\n * @param element - The DOM element to find providers for\n * @returns Array of matching providers, sorted by depth (deepest first)\n */\n findProvidersForElement: (element: Element) => ProviderInstance[];\n\n /**\n * Finds the nearest parent provider for a given container.\n * @param container - The container element to find a parent for\n * @param excludeId - Optional provider ID to exclude from search\n * @returns The nearest parent provider, or null if none found\n */\n findParentProvider: (\n container: Element | null,\n excludeId?: string,\n ) => ProviderInstance | null;\n\n /**\n * Gets the merged theme for a provider (includes inherited parent themes).\n * @param providerId - The ID of the provider to get the merged theme for\n * @returns The merged theme configuration\n */\n getMergedTheme: (providerId: string) => AnyclickTheme;\n\n /**\n * Checks if any ancestor provider has disabled anyclick.\n * @param providerId - The ID of the provider to check\n * @returns True if any ancestor is disabled\n */\n isDisabledByAncestor: (providerId: string) => boolean;\n\n /**\n * Checks if an element is inside any scoped provider's container.\n * Used to prevent the global provider from handling touch events.\n * @param element - The element to check\n * @returns True if element is inside any scoped provider\n */\n isElementInAnyScopedProvider: (element: Element) => boolean;\n\n /**\n * Checks if an element is inside a disabled scoped provider's container.\n * @param element - The element to check\n * @returns True if element is inside a disabled scope\n */\n isElementInDisabledScope: (element: Element) => boolean;\n\n /**\n * Registers a new provider in the store.\n * @param provider - The provider instance to register\n */\n registerProvider: (provider: ProviderInstance) => void;\n\n /**\n * Unregisters a provider from the store.\n * @param id - The ID of the provider to unregister\n */\n unregisterProvider: (id: string) => void;\n\n /**\n * Updates a provider's configuration.\n * @param id - The ID of the provider to update\n * @param updates - Partial updates to apply\n */\n updateProvider: (id: string, updates: Partial<ProviderInstance>) => void;\n}\n\n/** Counter for generating unique provider IDs */\nlet providerIdCounter = 0;\n\n/**\n * Generates a unique ID for a provider instance.\n *\n * @returns A unique provider ID string\n *\n * @example\n * ```ts\n * const id = generateProviderId();\n * // => \"anyclick-provider-1\"\n * ```\n *\n * @since 1.0.0\n */\nexport function generateProviderId(): string {\n return `anyclick-provider-${++providerIdCounter}`;\n}\n\n/**\n * Zustand store hook for managing provider instances.\n *\n * This store maintains a global registry of all AnyclickProvider instances,\n * enabling features like:\n * - Nested provider hierarchies\n * - Theme inheritance\n * - Scoped contexts\n * - Event routing\n *\n * @example\n * ```ts\n * // Get providers for an element\n * const providers = useProviderStore.getState().findProvidersForElement(element);\n *\n * // Get merged theme for a provider\n * const { getMergedTheme } = useProviderStore();\n * const theme = getMergedTheme(providerId);\n * ```\n *\n * @since 1.0.0\n */\nexport const useProviderStore = create<ProviderStore>((set, get) => ({\n providers: new Map(),\n\n findProvidersForElement: (element) => {\n const { providers } = get();\n const matching: ProviderInstance[] = [];\n\n for (const provider of providers.values()) {\n // Skip disabled providers\n if (provider.disabled) continue;\n\n const container = provider.containerRef.current;\n\n // For scoped providers, check if element is within container\n if (provider.scoped && container) {\n if (container.contains(element)) {\n matching.push(provider);\n }\n } else if (!provider.scoped) {\n // Non-scoped providers match all elements\n matching.push(provider);\n }\n }\n\n // Sort by depth (nearest/deepest first)\n return matching.sort((a, b) => b.depth - a.depth);\n },\n\n findParentProvider: (container, excludeId) => {\n const { providers } = get();\n\n if (!container) return null;\n\n let nearestParent: ProviderInstance | null = null;\n let nearestDepth = -1;\n\n for (const provider of providers.values()) {\n if (provider.id === excludeId) continue;\n\n const providerContainer = provider.containerRef.current;\n if (!providerContainer) continue;\n\n // Check if this provider's container contains our container\n if (providerContainer.contains(container)) {\n // This is a potential parent - check if it's the nearest one\n if (provider.depth > nearestDepth) {\n nearestParent = provider;\n nearestDepth = provider.depth;\n }\n }\n }\n\n return nearestParent;\n },\n\n getMergedTheme: (providerId) => {\n const { providers } = get();\n const provider = providers.get(providerId);\n\n if (!provider) {\n return {};\n }\n\n // Build ancestor chain\n const ancestors: ProviderInstance[] = [];\n let current: ProviderInstance | undefined = provider;\n\n while (current) {\n ancestors.unshift(current);\n current = current.parentId ? providers.get(current.parentId) : undefined;\n }\n\n // Merge themes from root to current (later themes override earlier)\n const mergedTheme: AnyclickTheme = {};\n\n for (const ancestor of ancestors) {\n if (ancestor.theme) {\n // Deep merge for nested objects\n Object.assign(mergedTheme, ancestor.theme);\n\n // Special handling for highlightConfig and screenshotConfig\n if (ancestor.theme.highlightConfig) {\n mergedTheme.highlightConfig = {\n ...mergedTheme.highlightConfig,\n ...ancestor.theme.highlightConfig,\n colors: {\n ...mergedTheme.highlightConfig?.colors,\n ...ancestor.theme.highlightConfig.colors,\n },\n };\n }\n\n if (ancestor.theme.screenshotConfig) {\n mergedTheme.screenshotConfig = {\n ...mergedTheme.screenshotConfig,\n ...ancestor.theme.screenshotConfig,\n };\n }\n }\n }\n\n return mergedTheme;\n },\n\n isDisabledByAncestor: (providerId) => {\n const { providers } = get();\n const provider = providers.get(providerId);\n\n if (!provider) return false;\n\n // Check this provider and all ancestors\n let current: ProviderInstance | undefined = provider;\n\n while (current) {\n if (current.disabled || current.theme?.disabled) {\n return true;\n }\n current = current.parentId ? providers.get(current.parentId) : undefined;\n }\n\n return false;\n },\n\n isElementInAnyScopedProvider: (element) => {\n const { providers } = get();\n\n // Check all scoped providers (enabled or disabled)\n for (const provider of providers.values()) {\n // Only check scoped providers\n if (!provider.scoped) continue;\n\n const container = provider.containerRef.current;\n if (!container) continue;\n\n // If element is inside this scoped provider's container\n if (container.contains(element)) {\n return true;\n }\n }\n\n return false;\n },\n\n isElementInDisabledScope: (element) => {\n const { providers } = get();\n\n // Check all scoped providers (including disabled ones)\n for (const provider of providers.values()) {\n // Only check scoped providers that are disabled\n if (!provider.scoped) continue;\n if (!provider.disabled && !provider.theme?.disabled) continue;\n\n const container = provider.containerRef.current;\n if (!container) continue;\n\n // If element is inside this disabled scoped provider's container\n if (container.contains(element)) {\n return true;\n }\n }\n\n return false;\n },\n\n registerProvider: (provider) => {\n set((state) => {\n const newProviders = new Map(state.providers);\n newProviders.set(provider.id, provider);\n return { providers: newProviders };\n });\n },\n\n unregisterProvider: (id) => {\n set((state) => {\n const newProviders = new Map(state.providers);\n newProviders.delete(id);\n return { providers: newProviders };\n });\n },\n\n updateProvider: (id, updates) => {\n set((state) => {\n const newProviders = new Map(state.providers);\n const existing = newProviders.get(id);\n if (existing) {\n newProviders.set(id, { ...existing, ...updates });\n }\n return { providers: newProviders };\n });\n },\n}));\n\n/**\n * Dispatches a context menu event to all matching providers.\n *\n * Routes the event through the provider hierarchy, calling handlers\n * from the nearest (deepest) provider first.\n *\n * @param event - The original mouse event\n * @param element - The target element\n *\n * @example\n * ```ts\n * document.addEventListener(\"contextmenu\", (event) => {\n * dispatchContextMenuEvent(event, event.target as Element);\n * });\n * ```\n *\n * @since 1.0.0\n */\nexport function dispatchContextMenuEvent(\n event: MouseEvent,\n element: Element,\n): void {\n const store = useProviderStore.getState();\n const providers = store.findProvidersForElement(element);\n\n // Convert MouseEvent to AnyclickMenuEvent\n const menuEvent: AnyclickMenuEvent = {\n clientX: event.clientX,\n clientY: event.clientY,\n isTouch: false,\n originalEvent: event,\n };\n\n // Call handlers from nearest to outermost\n for (const provider of providers) {\n // Check if disabled by theme or prop\n if (store.isDisabledByAncestor(provider.id)) {\n continue;\n }\n\n if (provider.onContextMenu) {\n provider.onContextMenu(menuEvent, element);\n // After the first handler processes, we don't need to call others\n break;\n }\n }\n}\n","\"use client\";\n\nimport { useEffect, useMemo, useRef } from \"react\";\nimport {\n type FunModeConfig,\n type PointerConfig,\n usePointer,\n} from \"@ewjdev/anyclick-pointer\";\nimport { useProviderStore } from \"./store\";\nimport type { AnyclickTheme, FunModeThemeConfig } from \"./types\";\n\nfunction isFunModeEnabled(\n theme?: AnyclickTheme | null,\n): theme is AnyclickTheme {\n if (!theme) return false;\n if (theme.funMode === undefined) return false;\n if (typeof theme.funMode === \"boolean\") return theme.funMode;\n return theme.funMode.enabled ?? true;\n}\n\nfunction buildFunConfig(\n theme: AnyclickTheme | null | undefined,\n container: Element,\n): FunModeConfig {\n const funTheme =\n typeof theme?.funMode === \"object\"\n ? (theme.funMode as FunModeThemeConfig)\n : {};\n const resolveTrackElement = (): HTMLElement => {\n // Some scoped containers use display: contents and report zero bounds.\n // Walk up to the first ancestor with a real box; fall back to body.\n let el: HTMLElement | null = container as HTMLElement | null;\n while (el) {\n const rect = el.getBoundingClientRect();\n if (rect.width > 0 && rect.height > 0) {\n return el;\n }\n el = el.parentElement;\n }\n return document.body;\n };\n\n const getTrackElement = () => resolveTrackElement();\n return {\n maxSpeed: funTheme.maxSpeed,\n acceleration: funTheme.acceleration,\n getTrackElement,\n getObstacles: () => {\n // Obstacles = siblings + children (lightweight bounding boxes)\n const trackElement = getTrackElement();\n const obstacles: DOMRect[] = [];\n const parent = trackElement.parentElement;\n if (parent) {\n Array.from(parent.children).forEach((sibling) => {\n if (sibling !== trackElement) {\n obstacles.push(sibling.getBoundingClientRect());\n }\n });\n }\n Array.from(trackElement.children).forEach((child) => {\n obstacles.push(child.getBoundingClientRect());\n });\n return obstacles;\n },\n };\n}\n\n/**\n * FunModeBridge watches Anyclick scoped providers and toggles the pointer\n * into fun mode (go-kart) when the cursor is within a provider with funMode enabled.\n * Requires a PointerProvider higher in the tree.\n */\nexport function FunModeBridge() {\n const { setConfig } = usePointer();\n const providerStore = useProviderStore();\n const activeProviderRef = useRef<string | null>(null);\n const cachedConfigs = useRef<Record<string, PointerConfig>>({});\n\n const findActiveFunProvider = useMemo(() => {\n return (el: Element | null) => {\n if (!el) return null;\n const providers = providerStore.findProvidersForElement(el);\n for (const provider of providers) {\n if (\n provider.scoped &&\n !provider.disabled &&\n isFunModeEnabled(provider.theme)\n ) {\n return provider;\n }\n }\n return null;\n };\n }, [providerStore]);\n\n useEffect(() => {\n const handleMove = (event: PointerEvent) => {\n const el = document.elementFromPoint(event.clientX, event.clientY);\n const provider = findActiveFunProvider(el as Element | null);\n\n if (!provider || !provider.containerRef.current) {\n if (activeProviderRef.current !== null) {\n activeProviderRef.current = null;\n setConfig({ mode: \"normal\" });\n }\n return;\n }\n\n if (activeProviderRef.current === provider.id) {\n return;\n }\n\n activeProviderRef.current = provider.id;\n if (!cachedConfigs.current[provider.id]) {\n cachedConfigs.current[provider.id] = {\n mode: \"fun\",\n funConfig: buildFunConfig(\n provider.theme,\n provider.containerRef.current,\n ),\n };\n }\n setConfig(cachedConfigs.current[provider.id]);\n };\n\n window.addEventListener(\"pointermove\", handleMove, { passive: true });\n return () => {\n window.removeEventListener(\"pointermove\", handleMove);\n };\n }, [findActiveFunProvider, setConfig]);\n\n return null;\n}\n\nexport default FunModeBridge;\n","import { ButtonHTMLAttributes, forwardRef } from \"react\";\nimport { cn } from \"../utils/cn\";\n\ntype ButtonProps = ButtonHTMLAttributes<HTMLButtonElement> & {\n variant?: \"default\" | \"ghost\" | \"outline\" | \"destructive\";\n size?: \"sm\" | \"md\" | \"lg\";\n};\n\nconst variantClasses: Record<NonNullable<ButtonProps[\"variant\"]>, string> = {\n default:\n \"ac-bg-accent ac-text-accent-foreground hover:ac-bg-accent-muted ac-border ac-border-border\",\n ghost: \"ac-bg-transparent hover:ac-bg-surface-muted ac-text-text\",\n outline:\n \"ac-bg-transparent ac-text-text ac-border ac-border-border hover:ac-bg-surface-muted\",\n destructive:\n \"ac-bg-destructive ac-text-accent-foreground hover:ac-bg-destructive/80\",\n};\n\nconst sizeClasses: Record<NonNullable<ButtonProps[\"size\"]>, string> = {\n sm: \"ac-h-8 ac-px-3 ac-text-sm\",\n md: \"ac-h-10 ac-px-4 ac-text-sm\",\n lg: \"ac-h-11 ac-px-5 ac-text-base\",\n};\n\nexport const Button = forwardRef<HTMLButtonElement, ButtonProps>(\n ({ className, variant = \"default\", size = \"md\", ...props }, ref) => {\n return (\n <button\n ref={ref}\n className={cn(\n \"ac-inline-flex ac-items-center ac-justify-center ac-gap-2 ac-rounded-md ac-font-medium ac-transition-colors focus-visible:ac-outline focus-visible:ac-outline-2 focus-visible:ac-outline-offset-2 focus-visible:ac-outline-accent disabled:ac-opacity-50 disabled:ac-cursor-not-allowed\",\n variantClasses[variant],\n sizeClasses[size],\n className,\n )}\n {...props}\n />\n );\n },\n);\n\nButton.displayName = \"Button\";\n","export function cn(...classes: Array<string | false | null | undefined>) {\n return classes.filter(Boolean).join(\" \");\n}\n","import { InputHTMLAttributes, forwardRef } from \"react\";\nimport { cn } from \"../utils/cn\";\n\ntype InputProps = InputHTMLAttributes<HTMLInputElement>;\n\nexport const Input = forwardRef<HTMLInputElement, InputProps>(\n ({ className, ...props }, ref) => {\n return (\n <input\n ref={ref}\n className={cn(\n \"ac-h-10 ac-w-full ac-rounded-md ac-border ac-border-border ac-bg-surface ac-text-text ac-placeholder-text-muted ac-px-3 ac-py-2 ac-text-sm focus-visible:ac-outline focus-visible:ac-outline-2 focus-visible:ac-outline-offset-2 focus-visible:ac-outline-accent disabled:ac-opacity-50 disabled:ac-cursor-not-allowed\",\n className,\n )}\n {...props}\n />\n );\n },\n);\n\nInput.displayName = \"Input\";\n","\"use client\";\n\nimport React, { useCallback, useEffect, useState } from \"react\";\nimport type { IDEConfig } from \"../ide\";\nimport type { HighlightColors } from \"../types\";\nimport {\n type CompactModeConfig,\n InspectSimple,\n type PinnedPosition,\n} from \"./InspectSimple\";\n\n/**\n * Custom event name for triggering the inspect dialog\n */\nexport const INSPECT_DIALOG_EVENT = \"anyclick:inspect\";\n\n/**\n * Custom event detail for the inspect dialog\n */\nexport interface InspectDialogEventDetail {\n targetElement: Element;\n}\n\n/**\n * Dispatch an event to open the inspect dialog for an element\n */\nexport function openInspectDialog(targetElement: Element): void {\n if (typeof window === \"undefined\") return;\n\n const event = new CustomEvent<InspectDialogEventDetail>(\n INSPECT_DIALOG_EVENT,\n {\n detail: { targetElement },\n bubbles: true,\n cancelable: true,\n },\n );\n\n window.dispatchEvent(event);\n}\n\n/**\n * Props for InspectDialogManager\n */\nexport interface InspectDialogManagerProps {\n /** IDE configuration for \"Open in IDE\" feature */\n ideConfig?: Partial<IDEConfig>;\n /** Custom styles for the dialog */\n dialogStyle?: React.CSSProperties;\n /** Custom class name for the dialog */\n dialogClassName?: string;\n /** Custom highlight colors for the element highlight */\n highlightColors?: HighlightColors;\n /** Whether to show box model overlay (padding/margin visualization). Defaults to true. */\n showBoxModelOverlay?: boolean;\n /** Initial pinned position for the dialog. Defaults to \"floating\" (centered) */\n initialPinnedPosition?: PinnedPosition;\n /** Custom compact mode configuration. Partially override DEFAULT_COMPACT_CONFIG */\n compactConfig?: Partial<CompactModeConfig>;\n}\n\n/**\n * InspectDialogManager - A component that listens for inspect events and renders the dialog\n *\n * Place this component once in your app (e.g., alongside AnyclickProvider) to enable\n * the inspect dialog functionality from the chrome preset.\n *\n * @example\n * ```tsx\n * <AnyclickProvider adapter={adapter}>\n * <InspectDialogManager ideConfig={{ protocol: \"cursor\", basePath: \"/Users/me/project\" }} />\n * {children}\n * </AnyclickProvider>\n * ```\n */\nexport function InspectDialogManager({\n ideConfig,\n dialogStyle,\n dialogClassName,\n highlightColors,\n showBoxModelOverlay = true,\n initialPinnedPosition = \"floating\",\n compactConfig,\n}: InspectDialogManagerProps) {\n const [visible, setVisible] = useState(false);\n const [targetElement, setTargetElement] = useState<Element | null>(null);\n\n const handleClose = useCallback(() => {\n setVisible(false);\n setTargetElement(null);\n }, []);\n\n // Handle selecting a different element (e.g., from modified elements list)\n const handleSelectElement = useCallback((element: Element) => {\n setTargetElement(element);\n // Keep dialog visible, just switch the target\n }, []);\n\n useEffect(() => {\n const handleInspectEvent = (event: Event) => {\n const customEvent = event as CustomEvent<InspectDialogEventDetail>;\n if (customEvent.detail?.targetElement) {\n setTargetElement(customEvent.detail.targetElement);\n setVisible(true);\n }\n };\n\n window.addEventListener(INSPECT_DIALOG_EVENT, handleInspectEvent);\n\n return () => {\n window.removeEventListener(INSPECT_DIALOG_EVENT, handleInspectEvent);\n };\n }, []);\n\n return (\n <InspectSimple\n visible={visible}\n targetElement={targetElement}\n onClose={handleClose}\n onSelectElement={handleSelectElement}\n ideConfig={ideConfig}\n style={dialogStyle}\n className={dialogClassName}\n highlightColors={highlightColors}\n showBoxModelOverlay={showBoxModelOverlay}\n initialPinnedPosition={initialPinnedPosition}\n compactConfig={compactConfig}\n />\n );\n}\n\nexport default InspectDialogManager;\n","\"use client\";\n\nimport React, { useEffect, useMemo, useRef, useState } from \"react\";\nimport {\n type ElementInspectInfo,\n captureScreenshot,\n getElementInspectInfo,\n} from \"@ewjdev/anyclick-core\";\nimport { Camera, Code, Copy, ExternalLink, FileText, X } from \"lucide-react\";\nimport {\n clearHighlights,\n findContainerParent,\n highlightContainer,\n highlightTarget,\n} from \"../highlight\";\nimport {\n type IDEConfig,\n type SourceLocation,\n findSourceLocationInAncestors,\n formatSourceLocation,\n openInIDE,\n} from \"../ide\";\nimport type { HighlightColors } from \"../types\";\n\nexport type PinnedPosition = \"left\" | \"right\" | \"top\" | \"bottom\" | \"floating\";\n\nexport interface CompactModeConfig {\n scale: number;\n fonts: {\n base: number;\n title: number;\n tag: number;\n selector: number;\n section: number;\n badge: number;\n property: number;\n styleRow: number;\n button: number;\n };\n spacing: {\n headerPadding: string;\n identityPadding: string;\n sectionHeaderPadding: string;\n sectionContentPadding: string;\n footerPadding: string;\n selectorCodePadding: string;\n buttonPadding: string;\n buttonPrimaryPadding: string;\n buttonDangerPadding: string;\n badgePadding: string;\n propertyRowPadding: string;\n styleRowPadding: string;\n };\n gaps: {\n headerTitle: string;\n pinButtons: string;\n propertyRow: string;\n propertyValue: string;\n button: string;\n footer: string;\n };\n sizes: {\n dialogWidth: number;\n closeButton: number;\n copyButtonSmall: number;\n styleValueMaxWidth: number;\n categoryMarginBottom: number;\n styleCategoryHeaderMarginBottom: number;\n };\n letterSpacing: {\n sectionTitle: string;\n };\n}\n\nexport const DEFAULT_COMPACT_CONFIG: CompactModeConfig = {\n scale: 0.5,\n fonts: {\n base: 12,\n title: 14,\n tag: 12,\n selector: 11,\n section: 12,\n badge: 11,\n property: 12,\n styleRow: 11,\n button: 12,\n },\n spacing: {\n headerPadding: \"8px 12px\",\n identityPadding: \"8px 12px\",\n sectionHeaderPadding: \"6px 12px\",\n sectionContentPadding: \"8px 12px\",\n footerPadding: \"8px 12px\",\n selectorCodePadding: \"6px 10px\",\n buttonPadding: \"6px 10px\",\n buttonPrimaryPadding: \"6px 12px\",\n buttonDangerPadding: \"6px 8px\",\n badgePadding: \"2px 6px\",\n propertyRowPadding: \"4px 6px\",\n styleRowPadding: \"4px 6px\",\n },\n gaps: {\n headerTitle: \"8px\",\n pinButtons: \"4px\",\n propertyRow: \"4px\",\n propertyValue: \"6px\",\n button: \"6px\",\n footer: \"8px\",\n },\n sizes: {\n dialogWidth: 420,\n closeButton: 18,\n copyButtonSmall: 16,\n styleValueMaxWidth: 240,\n categoryMarginBottom: 8,\n styleCategoryHeaderMarginBottom: 6,\n },\n letterSpacing: {\n sectionTitle: \"0.04em\",\n },\n};\n\nexport interface InspectSimpleProps {\n visible: boolean;\n targetElement: Element | null;\n onClose: () => void;\n onSelectElement?: (element: Element) => void;\n ideConfig?: Partial<IDEConfig>;\n style?: React.CSSProperties;\n className?: string;\n highlightColors?: HighlightColors;\n showBoxModelOverlay?: boolean;\n initialPinnedPosition?: PinnedPosition;\n compactConfig?: Partial<CompactModeConfig>;\n}\n\nfunction copy(text: string): Promise<boolean> {\n if (!text) return Promise.resolve(false);\n if (typeof navigator === \"undefined\" || !navigator.clipboard) {\n return Promise.resolve(false);\n }\n return navigator.clipboard\n .writeText(text)\n .then(() => true)\n .catch(() => false);\n}\n\nfunction downloadDataUrl(dataUrl: string, filename: string) {\n const link = document.createElement(\"a\");\n link.href = dataUrl;\n link.download = filename;\n link.click();\n}\n\nfunction useIsMobile() {\n const [isMobile, setIsMobile] = useState(false);\n\n useEffect(() => {\n const mq = window.matchMedia(\"(max-width: 640px)\");\n setIsMobile(mq.matches);\n const handler = (e: MediaQueryListEvent) => setIsMobile(e.matches);\n mq.addEventListener(\"change\", handler);\n return () => mq.removeEventListener(\"change\", handler);\n }, []);\n\n return isMobile;\n}\n\nexport function InspectSimple({\n visible,\n targetElement,\n onClose,\n ideConfig,\n style,\n className,\n highlightColors,\n}: InspectSimpleProps) {\n const [info, setInfo] = useState<ElementInspectInfo | null>(null);\n const [sourceLocation, setSourceLocation] = useState<SourceLocation | null>(\n null,\n );\n const [status, setStatus] = useState<string | null>(null);\n const [saving, setSaving] = useState(false);\n const dialogRef = useRef<HTMLDivElement>(null);\n const isMobile = useIsMobile();\n\n // Auto-dismiss status message after 5 seconds\n useEffect(() => {\n if (!status) return;\n const timer = setTimeout(() => setStatus(null), 5000);\n return () => clearTimeout(timer);\n }, [status]);\n\n useEffect(() => {\n if (!visible || !targetElement) return;\n\n try {\n clearHighlights();\n highlightTarget(targetElement, highlightColors);\n const container = findContainerParent(targetElement);\n if (container) highlightContainer(container, highlightColors);\n } catch {\n // ignore highlight errors\n }\n\n const nextInfo = getElementInspectInfo(targetElement);\n setInfo(nextInfo);\n setSourceLocation(\n findSourceLocationInAncestors(targetElement) ??\n nextInfo.sourceLocation ??\n null,\n );\n\n return () => {\n clearHighlights();\n };\n }, [visible, targetElement, highlightColors]);\n\n // Handle outside click\n useEffect(() => {\n if (!visible) return;\n\n const handleClickOutside = (e: MouseEvent) => {\n if (dialogRef.current && !dialogRef.current.contains(e.target as Node)) {\n onClose();\n }\n };\n\n // Delay adding the listener to avoid immediate close\n const timeoutId = setTimeout(() => {\n document.addEventListener(\"mousedown\", handleClickOutside);\n }, 100);\n\n return () => {\n clearTimeout(timeoutId);\n document.removeEventListener(\"mousedown\", handleClickOutside);\n };\n }, [visible, onClose]);\n\n const identityLabel = useMemo(() => {\n if (!info) return \"Select an element\";\n const classes = info.classNames[0] ? `.${info.classNames[0]}` : \"\";\n const id = info.id ? `#${info.id}` : \"\";\n return `${info.tagName}${id}${classes}`;\n }, [info]);\n\n const handleCopySelector = async () => {\n if (!info?.selector) {\n setStatus(\"No selector available\");\n return;\n }\n const ok = await copy(info.selector);\n setStatus(\n ok ? \"✓ Selector copied to clipboard\" : \"Failed to copy selector\",\n );\n };\n\n const handleCopyText = async () => {\n if (!info?.innerText) {\n setStatus(\"No text content to copy\");\n return;\n }\n const ok = await copy(info.innerText);\n setStatus(\n ok ? \"✓ Text content copied to clipboard\" : \"Failed to copy text\",\n );\n };\n\n const handleSaveScreenshot = async () => {\n if (!targetElement) return;\n setSaving(true);\n setStatus(\"Capturing screenshot…\");\n const result = await captureScreenshot(targetElement, null, \"element\");\n setSaving(false);\n if (result.capture?.dataUrl) {\n downloadDataUrl(result.capture.dataUrl, \"anyclick-inspect.png\");\n setStatus(\"✓ Screenshot saved to downloads\");\n } else {\n setStatus(result.error?.message || \"Screenshot capture failed\");\n }\n };\n\n const handleCopyOuterHTML = async () => {\n if (!info?.outerHTML) {\n setStatus(\"No HTML to copy\");\n return;\n }\n const ok = await copy(info.outerHTML);\n setStatus(ok ? \"✓ HTML markup copied to clipboard\" : \"Failed to copy HTML\");\n };\n\n const handleOpenIDE = () => {\n if (!sourceLocation) return;\n openInIDE(sourceLocation, ideConfig);\n };\n\n if (!visible || !targetElement) return null;\n\n const dialogStyles: React.CSSProperties = isMobile\n ? {\n position: \"fixed\",\n left: 0,\n right: 0,\n bottom: 0,\n zIndex: 9999,\n width: \"100%\",\n maxWidth: \"100%\",\n background: \"#0f172a\",\n color: \"#e2e8f0\",\n borderTop: \"1px solid #1e293b\",\n borderRadius: \"16px 16px 0 0\",\n boxShadow: \"0 -8px 32px rgba(0,0,0,0.4)\",\n fontFamily: \"Inter, system-ui, -apple-system, sans-serif\",\n fontSize: 13,\n overflow: \"hidden\",\n ...style,\n }\n : {\n position: \"fixed\",\n right: 16,\n bottom: 16,\n zIndex: 9999,\n width: 320,\n maxWidth: \"90vw\",\n background: \"#0f172a\",\n color: \"#e2e8f0\",\n border: \"1px solid #1e293b\",\n borderRadius: 12,\n boxShadow: \"0 18px 48px rgba(0,0,0,0.45)\",\n fontFamily: \"Inter, system-ui, -apple-system, sans-serif\",\n fontSize: 13,\n overflow: \"hidden\",\n ...style,\n };\n\n return (\n <>\n {/* Backdrop overlay */}\n <div\n style={{\n position: \"fixed\",\n inset: 0,\n zIndex: 9998,\n background: isMobile ? \"rgba(0,0,0,0.5)\" : \"transparent\",\n pointerEvents: isMobile ? \"auto\" : \"none\",\n }}\n onClick={onClose}\n onKeyDown={(e) => e.key === \"Escape\" && onClose()}\n role=\"presentation\"\n />\n\n <div\n ref={dialogRef}\n className={`anyclick-tiny-inspect ${className ?? \"\"}`}\n style={dialogStyles}\n >\n {/* Header with close button */}\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"space-between\",\n padding: isMobile ? \"12px 16px\" : \"8px 10px\",\n background: \"#0b1220\",\n borderBottom: \"1px solid #1e293b\",\n }}\n >\n {/* Mobile drawer handle */}\n {isMobile && (\n <div\n style={{\n position: \"absolute\",\n top: 6,\n left: \"50%\",\n transform: \"translateX(-50%)\",\n width: 36,\n height: 4,\n borderRadius: 2,\n background: \"#475569\",\n }}\n />\n )}\n\n <div style={{ display: \"flex\", alignItems: \"center\", gap: 6 }}>\n <span\n style={{\n padding: \"3px 8px\",\n borderRadius: 6,\n background: \"#1e293b\",\n color: \"#e2e8f0\",\n fontSize: 12,\n fontWeight: 600,\n fontFamily: \"monospace\",\n }}\n >\n {identityLabel}\n </span>\n {sourceLocation && (\n <button\n type=\"button\"\n onClick={handleOpenIDE}\n title={formatSourceLocation(sourceLocation)}\n style={iconBtnStyle}\n >\n <ExternalLink size={14} />\n </button>\n )}\n </div>\n\n <button\n type=\"button\"\n onClick={onClose}\n style={iconBtnStyle}\n aria-label=\"Close inspector\"\n >\n <X size={16} />\n </button>\n </div>\n\n {/* Compact content */}\n <div\n style={{\n padding: isMobile ? \"12px 16px 20px\" : \"10px\",\n display: \"flex\",\n flexDirection: \"column\",\n gap: 8,\n }}\n >\n {/* Selector row */}\n {info?.selector && (\n <code\n style={{\n fontSize: 11,\n color: \"#94a3b8\",\n background: \"#111827\",\n padding: \"6px 8px\",\n borderRadius: 6,\n wordBreak: \"break-all\",\n display: \"block\",\n }}\n >\n {info.selector}\n </code>\n )}\n\n {/* Status feedback message - above buttons */}\n {status && (\n <div\n style={{\n fontSize: 12,\n color: status.startsWith(\"✓\")\n ? \"#4ade80\"\n : status.toLowerCase().includes(\"failed\") ||\n status.toLowerCase().includes(\"error\")\n ? \"#f87171\"\n : \"#94a3b8\",\n padding: \"4px 0\",\n fontWeight: 500,\n }}\n >\n {status}\n </div>\n )}\n\n {/* Actions - icon-only row */}\n <div\n style={{\n display: \"flex\",\n alignItems: \"center\",\n gap: 6,\n }}\n >\n <button\n type=\"button\"\n onClick={handleCopySelector}\n style={iconActionStyle}\n title=\"Copy CSS selector\"\n aria-label=\"Copy CSS selector\"\n >\n <Copy size={15} />\n </button>\n <button\n type=\"button\"\n onClick={handleCopyText}\n style={iconActionStyle}\n title=\"Copy text content\"\n aria-label=\"Copy text content\"\n >\n <FileText size={15} />\n </button>\n <button\n type=\"button\"\n onClick={handleCopyOuterHTML}\n style={iconActionStyle}\n title=\"Copy HTML markup\"\n aria-label=\"Copy HTML markup\"\n >\n <Code size={15} />\n </button>\n <button\n type=\"button\"\n onClick={handleSaveScreenshot}\n style={{\n ...iconActionStyle,\n ...(saving ? { opacity: 0.5, cursor: \"wait\" } : {}),\n }}\n disabled={saving}\n title=\"Save screenshot\"\n aria-label=\"Save screenshot\"\n >\n <Camera size={15} />\n </button>\n </div>\n </div>\n </div>\n </>\n );\n}\n\nconst iconBtnStyle: React.CSSProperties = {\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n width: 28,\n height: 28,\n borderRadius: 6,\n border: \"1px solid #1e293b\",\n background: \"#0b1220\",\n color: \"#94a3b8\",\n cursor: \"pointer\",\n padding: 0,\n};\n\nconst iconActionStyle: React.CSSProperties = {\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n width: 32,\n height: 32,\n borderRadius: 8,\n border: \"1px solid #1e293b\",\n background: \"#0b1220\",\n color: \"#94a3b8\",\n cursor: \"pointer\",\n padding: 0,\n transition: \"background 0.15s, color 0.15s, border-color 0.15s\",\n};\n","/**\n * IDE protocol handler integration for opening files directly in IDEs.\n * Supports VS Code, Cursor, WebStorm, and other IDEs that support URL protocols.\n */\n\n/**\n * Supported IDE protocol types\n */\nexport type IDEProtocol =\n | \"vscode\"\n | \"cursor\"\n | \"webstorm\"\n | \"intellij\"\n | \"phpstorm\"\n | \"sublime\"\n | \"atom\"\n | \"custom\";\n\n/**\n * Configuration for IDE integration\n */\nexport interface IDEConfig {\n /** The IDE protocol to use */\n protocol: IDEProtocol;\n /** Custom protocol string (only used when protocol is 'custom') */\n customProtocol?: string;\n /** Base path to prepend to file paths (for mapping web paths to file system) */\n basePath?: string;\n /** Path transformations to apply (regex find/replace) */\n pathTransforms?: Array<{\n find: string | RegExp;\n replace: string;\n }>;\n}\n\n/**\n * Source location information\n */\nexport interface SourceLocation {\n /** File path */\n file: string;\n /** Line number (1-indexed) */\n line: number;\n /** Column number (1-indexed, optional) */\n column?: number;\n}\n\n/**\n * Default IDE configuration\n */\nconst DEFAULT_IDE_CONFIG: IDEConfig = {\n protocol: \"cursor\",\n};\n\n/**\n * Protocol URL templates for different IDEs\n * {file} = file path, {line} = line number, {column} = column number\n */\nconst PROTOCOL_TEMPLATES: Record<IDEProtocol, string> = {\n vscode: \"vscode://file/{file}:{line}:{column}\",\n cursor: \"cursor://file/{file}:{line}:{column}\",\n webstorm: \"webstorm://open?file={file}&line={line}&column={column}\",\n intellij: \"idea://open?file={file}&line={line}&column={column}\",\n phpstorm: \"phpstorm://open?file={file}&line={line}&column={column}\",\n sublime: \"subl://open?url=file://{file}&line={line}&column={column}\",\n atom: \"atom://open?url=file://{file}&line={line}&column={column}\",\n custom: \"\", // Placeholder, will use customProtocol\n};\n\n/**\n * Build the URL for opening a file in an IDE\n */\nexport function buildIDEUrl(\n location: SourceLocation,\n config: Partial<IDEConfig> = {},\n): string {\n const mergedConfig: IDEConfig = { ...DEFAULT_IDE_CONFIG, ...config };\n let filePath = location.file;\n\n // Apply base path if provided\n if (mergedConfig.basePath) {\n // Remove leading slash from file path if base path doesn't end with one\n if (!mergedConfig.basePath.endsWith(\"/\") && filePath.startsWith(\"/\")) {\n filePath = filePath.slice(1);\n }\n filePath = `${mergedConfig.basePath}/${filePath}`.replace(/\\/+/g, \"/\");\n }\n\n // Apply path transformations\n if (mergedConfig.pathTransforms) {\n for (const transform of mergedConfig.pathTransforms) {\n filePath = filePath.replace(transform.find, transform.replace);\n }\n }\n\n // Get the template\n let template =\n mergedConfig.protocol === \"custom\"\n ? mergedConfig.customProtocol || \"\"\n : PROTOCOL_TEMPLATES[mergedConfig.protocol];\n\n // Replace placeholders\n const url = template\n .replace(\"{file}\", encodeURIComponent(filePath))\n .replace(\"{line}\", String(location.line))\n .replace(\"{column}\", String(location.column || 1));\n\n return url;\n}\n\n/**\n * Open a file in the IDE using the protocol handler\n */\nexport function openInIDE(\n location: SourceLocation,\n config: Partial<IDEConfig> = {},\n): boolean {\n if (typeof window === \"undefined\") {\n console.warn(\"openInIDE: Cannot open IDE in non-browser environment\");\n return false;\n }\n\n try {\n const url = buildIDEUrl(location, config);\n\n // Use window.open with a short timeout to avoid popup blockers\n // The protocol handler should intercept this\n window.location.href = url;\n\n return true;\n } catch (error) {\n console.error(\"Failed to open file in IDE:\", error);\n return false;\n }\n}\n\n/**\n * Check if the current environment likely supports IDE protocol handlers\n * Note: This is a heuristic and may not be 100% accurate\n */\nexport function isIDEProtocolSupported(): boolean {\n if (typeof window === \"undefined\") return false;\n\n // Protocol handlers are generally supported on desktop browsers\n // but not on mobile or in some restricted environments\n const userAgent = navigator.userAgent.toLowerCase();\n\n // Mobile browsers generally don't support custom protocol handlers well\n if (/mobile|android|iphone|ipad/i.test(userAgent)) {\n return false;\n }\n\n return true;\n}\n\n/**\n * Detect the most likely IDE based on environment\n * This is a heuristic based on common development setups\n */\nexport function detectPreferredIDE(): IDEProtocol {\n if (typeof window === \"undefined\") return \"vscode\";\n\n // Check for Cursor-specific indicators\n // Cursor sets some specific user agent or environment hints\n const userAgent = navigator.userAgent;\n\n // For now, default to Cursor since this is the anyclick project\n // In production, this could be enhanced with better detection\n return \"cursor\";\n}\n\n/**\n * Try to extract source location from element data attributes\n */\nexport function getSourceLocationFromElement(\n element: Element,\n): SourceLocation | null {\n const htmlElement = element as HTMLElement;\n const dataset = htmlElement.dataset || {};\n\n // Try different data attribute conventions\n const file =\n dataset.sourceFile ||\n dataset[\"source-file\"] ||\n element.getAttribute(\"data-source-file\") ||\n dataset.file ||\n element.getAttribute(\"data-file\");\n\n const line =\n dataset.sourceLine ||\n dataset[\"source-line\"] ||\n element.getAttribute(\"data-source-line\") ||\n dataset.line ||\n element.getAttribute(\"data-line\");\n\n if (!file || !line) {\n return null;\n }\n\n const column =\n dataset.sourceColumn ||\n dataset[\"source-column\"] ||\n element.getAttribute(\"data-source-column\") ||\n dataset.column ||\n element.getAttribute(\"data-column\");\n\n return {\n file,\n line: parseInt(line, 10),\n column: column ? parseInt(column, 10) : undefined,\n };\n}\n\n/**\n * Walk up the DOM tree to find source location from any ancestor\n */\nexport function findSourceLocationInAncestors(\n element: Element,\n maxDepth: number = 10,\n): SourceLocation | null {\n let current: Element | null = element;\n let depth = 0;\n\n while (current && depth < maxDepth) {\n const location = getSourceLocationFromElement(current);\n if (location) {\n return location;\n }\n current = current.parentElement;\n depth++;\n }\n\n return null;\n}\n\n/**\n * Create a configured IDE opener function\n */\nexport function createIDEOpener(\n config: Partial<IDEConfig> = {},\n): (location: SourceLocation) => boolean {\n return (location: SourceLocation) => openInIDE(location, config);\n}\n\n/**\n * Format a source location as a readable string\n */\nexport function formatSourceLocation(location: SourceLocation): string {\n const { file, line, column } = location;\n if (column !== undefined) {\n return `${file}:${line}:${column}`;\n }\n return `${file}:${line}`;\n}\n","/**\n * Role-based preset configurations for common user types.\n *\n * Provides pre-configured menu items, screenshot settings, and themes\n * tailored for specific roles like QA, PM, Designer, and Developer.\n *\n * @module presets\n * @since 1.2.0\n *\n * @example\n * ```tsx\n * import { AnyclickProvider, createPresetMenu } from \"@ewjdev/anyclick-react\";\n *\n * const qaPreset = createPresetMenu(\"qa\");\n *\n * function App() {\n * return (\n * <AnyclickProvider\n * adapter={adapter}\n * menuItems={qaPreset.menuItems}\n * screenshotConfig={qaPreset.screenshotConfig}\n * theme={qaPreset.theme}\n * >\n * <YourApp />\n * </AnyclickProvider>\n * );\n * }\n * ```\n */\nimport { CSSProperties } from \"react\";\nimport type { ScreenshotConfig } from \"@ewjdev/anyclick-core\";\nimport { openInspectDialog } from \"./InspectDialog/InspectDialogManager\";\nimport type { AnyclickTheme, ContextMenuItem, HighlightConfig } from \"./types\";\n\n/**\n * Available preset role identifiers.\n *\n * - `qa` - QA/Testing focused menu with bug reporting and repro steps\n * - `pm` - Product Manager focused menu with feature ideas and impact sizing\n * - `designer` - Designer focused menu with visual QA and accessibility\n * - `developer` - Developer focused menu with diagnostics and debugging\n * - `chrome` - Chrome-like context menu with browser actions\n *\n * @since 1.2.0\n */\nexport type PresetRole = \"chrome\" | \"designer\" | \"developer\" | \"pm\" | \"qa\";\n\n/**\n * Complete preset configuration for a role.\n *\n * Contains all the settings needed to configure an AnyclickProvider\n * for a specific user role.\n *\n * @since 1.2.0\n */\nexport interface PresetConfig {\n /** Human-readable description of the preset */\n description: string;\n /** Optional highlight configuration */\n highlightConfig?: HighlightConfig;\n /** Human-readable label for the preset */\n label: string;\n /** Context menu items for this preset */\n menuItems: ContextMenuItem[];\n /** Additional metadata to include with submissions */\n metadata?: Record<string, unknown>;\n /** The preset role identifier */\n role: PresetRole;\n /** Screenshot capture configuration */\n screenshotConfig?: Partial<ScreenshotConfig>;\n /** Theme configuration including styles and highlighting */\n theme?: AnyclickTheme;\n}\n\n/**\n * Options for customizing preset menu creation.\n *\n * @since 1.2.0\n */\nexport interface CreatePresetMenuOptions {\n /**\n * Whether to include coming-soon items in the menu.\n * Coming-soon items are shown but disabled.\n * @default true\n */\n includeComingSoon?: boolean;\n /**\n * Optional overrides for menu items, screenshot config, metadata, or theme.\n * Useful when you want to tweak a preset without rebuilding it manually.\n *\n * @example\n * ```ts\n * const qaPreset = createPresetMenu(\"qa\", {\n * overrides: {\n * screenshotConfig: { quality: 0.9 },\n * theme: { highlightConfig: { colors: { targetColor: \"#ef4444\" } } },\n * },\n * });\n * ```\n */\n overrides?: Partial<Omit<PresetConfig, \"description\" | \"label\" | \"role\">>;\n}\n\n/**\n * Default preset configurations for each role.\n *\n * These are the base configurations that {@link createPresetMenu} uses.\n * You can use them directly if you don't need any customization.\n *\n * @since 1.2.0\n */\nconst presetDefaults: Record<PresetRole, PresetConfig> = {\n chrome: {\n description:\n \"Chrome-like context menu with core browser actions and native styling.\",\n label: \"Chrome\",\n menuItems: [\n {\n label: \"Reload page\",\n onClick: ({ closeMenu }) => {\n closeMenu();\n if (typeof window !== \"undefined\") {\n window.location.reload();\n }\n return false;\n },\n showComment: false,\n type: \"reload_page\",\n },\n {\n label: \"Print…\",\n onClick: ({ closeMenu }) => {\n closeMenu();\n if (typeof window !== \"undefined\") {\n window.print();\n }\n return false;\n },\n showComment: false,\n type: \"print_page\",\n },\n {\n label: 'Search \"Google\"',\n onClick: ({ closeMenu }) => {\n closeMenu();\n if (typeof window === \"undefined\") return false;\n const selection = window.getSelection()?.toString().trim();\n const query = selection && selection.length > 0 ? selection : \"\";\n const url = query\n ? `https://www.google.com/search?q=${encodeURIComponent(query)}`\n : \"https://www.google.com\";\n window.open(url, \"_blank\", \"noopener,noreferrer\");\n return false;\n },\n showComment: false,\n type: \"search_google\",\n },\n {\n label: \"Ask t3.chat\",\n onClick: ({ closeMenu }) => {\n closeMenu();\n if (typeof window === \"undefined\") return false;\n const selection = window.getSelection()?.toString().trim();\n const query = selection && selection.length > 0 ? selection : \"\";\n const url = query\n ? `https://t3.chat/?q=${encodeURIComponent(query)}`\n : \"https://t3.chat\";\n window.open(url, \"_blank\", \"noopener,noreferrer\");\n return false;\n },\n showComment: false,\n type: \"ask_t3chat\",\n },\n {\n label: \"Share…\",\n onClick: async ({ closeMenu }) => {\n closeMenu();\n if (typeof window === \"undefined\") return false;\n const shareData = {\n text: document.title,\n title: document.title,\n url: window.location.href,\n };\n try {\n if (navigator.share) {\n await navigator.share(shareData);\n } else if (navigator.clipboard?.writeText) {\n await navigator.clipboard.writeText(window.location.href);\n }\n } catch {\n // Silently ignore share/clipboard errors to match native feel\n }\n return false;\n },\n showComment: false,\n type: \"share_page\",\n },\n {\n label: \"Inspect\",\n onClick: ({ closeMenu, targetElement }) => {\n closeMenu();\n if (targetElement) {\n openInspectDialog(targetElement);\n }\n return false;\n },\n showComment: false,\n type: \"inspect\",\n },\n ],\n role: \"chrome\",\n screenshotConfig: {\n enabled: false,\n },\n theme: {\n highlightConfig: {\n enabled: false,\n },\n menuStyle: {\n \"--anyclick-menu-accent\": \"#8ab4f8\",\n \"--anyclick-menu-accent-text\": \"#0b1117\",\n \"--anyclick-menu-bg\": \"#202124\",\n \"--anyclick-menu-border\": \"#3c4043\",\n \"--anyclick-menu-cancel-bg\": \"#2f3135\",\n \"--anyclick-menu-cancel-text\": \"#9aa0a6\",\n \"--anyclick-menu-hover\": \"#2f3135\",\n \"--anyclick-menu-input-bg\": \"#2f3135\",\n \"--anyclick-menu-input-border\": \"#3c4043\",\n \"--anyclick-menu-text\": \"#e8eaed\",\n \"--anyclick-menu-text-muted\": \"#9aa0a6\",\n backgroundColor: \"#202124\",\n border: \"1px solid #3c4043\",\n borderRadius: 6,\n boxShadow: \"0 8px 18px rgba(0, 0, 0, 0.4)\",\n color: \"#e8eaed\",\n fontFamily:\n 'Roboto, \"Segoe UI\", -apple-system, BlinkMacSystemFont, sans-serif',\n fontSize: 14,\n letterSpacing: 0,\n minWidth: 240,\n padding: 0,\n } as CSSProperties,\n },\n },\n designer: {\n description: \"Visual QA with contrast and motion cues.\",\n label: \"Designer\",\n menuItems: [\n { label: \"Visual bug\", showComment: true, type: \"visual_bug\" },\n { label: \"Accessibility\", showComment: true, type: \"accessibility\" },\n { label: \"Copy / tone\", showComment: true, type: \"copy_tone\" },\n {\n badge: { label: \"Coming soon\", tone: \"info\" },\n label: \"Motion glitch\",\n showComment: true,\n status: \"comingSoon\",\n type: \"motion_glitch\",\n },\n ],\n metadata: {\n capture: {\n colorContrast: true,\n prefersReducedMotion: true,\n },\n },\n role: \"designer\",\n screenshotConfig: {\n enabled: true,\n padding: 32,\n quality: 0.75,\n showPreview: true,\n },\n theme: {\n highlightConfig: {\n colors: {\n containerColor: \"#22d3ee\",\n targetColor: \"#a855f7\",\n },\n },\n },\n },\n developer: {\n description: \"Debug-ready menu with diagnostics placeholders.\",\n label: \"Developer\",\n menuItems: [\n { label: \"Bug\", showComment: true, type: \"bug\" },\n { label: \"Refactor request\", showComment: true, type: \"refactor\" },\n {\n children: [\n {\n badge: { label: \"Coming soon\", tone: \"info\" },\n label: \"Console snapshot\",\n showComment: false,\n status: \"comingSoon\",\n type: \"console_snapshot\",\n },\n {\n badge: { label: \"Coming soon\", tone: \"info\" },\n label: \"Network trace\",\n showComment: false,\n status: \"comingSoon\",\n type: \"network_trace\",\n },\n {\n label: \"Copy CSS selector\",\n showComment: false,\n type: \"copy_selector\",\n },\n ],\n label: \"Diagnostics\",\n type: \"diagnostics\",\n },\n ],\n metadata: {\n capture: {\n console: \"errors\",\n network: \"errors\",\n reduxState: \"opt-in\",\n },\n },\n role: \"developer\",\n screenshotConfig: {\n enabled: true,\n padding: 20,\n quality: 0.7,\n showPreview: true,\n },\n theme: {\n highlightConfig: {\n colors: {\n containerColor: \"#0ea5e9\",\n targetColor: \"#22c55e\",\n },\n },\n },\n },\n pm: {\n description: \"Idea-first menu with quick impact sizing.\",\n label: \"PM\",\n menuItems: [\n { label: \"Feature idea\", showComment: true, type: \"feature\" },\n { label: \"UX papercut\", showComment: true, type: \"ux_papercut\" },\n { label: \"Customer quote\", showComment: true, type: \"success_story\" },\n {\n badge: { label: \"Coming soon\", tone: \"neutral\" },\n label: \"Impact / priority\",\n showComment: true,\n status: \"comingSoon\",\n type: \"impact_sizing\",\n },\n ],\n metadata: {\n capture: {\n audience: \"pm\",\n sentiment: true,\n },\n },\n role: \"pm\",\n screenshotConfig: {\n enabled: true,\n padding: 16,\n quality: 0.65,\n showPreview: true,\n },\n },\n qa: {\n description: \"Defect-first menu tuned for repros and logs.\",\n label: \"QA\",\n menuItems: [\n { label: \"Bug / defect\", showComment: true, type: \"bug\" },\n { label: \"UX papercut\", showComment: true, type: \"ux_papercut\" },\n { label: \"Repro steps\", showComment: true, type: \"repro_steps\" },\n {\n badge: { label: \"Coming soon\", tone: \"info\" },\n label: \"Performance trace\",\n showComment: true,\n status: \"comingSoon\",\n type: \"perf_trace\",\n },\n {\n badge: { label: \"Coming soon\", tone: \"info\" },\n label: \"Video capture\",\n showComment: false,\n status: \"comingSoon\",\n type: \"video_capture\",\n },\n ],\n metadata: {\n capture: {\n console: \"errors\",\n domSnapshot: true,\n network: \"errors\",\n },\n },\n role: \"qa\",\n screenshotConfig: {\n enabled: true,\n padding: 24,\n quality: 0.7,\n showPreview: true,\n },\n },\n};\n\n/**\n * Creates a preset menu configuration for a specific role.\n *\n * Returns a complete configuration that can be spread into AnyclickProvider props.\n * Coming-soon items are included by default but shown as disabled.\n *\n * @param role - The preset role to create a menu for\n * @param options - Optional customization options\n * @returns A complete preset configuration\n * @throws {Error} If an unknown role is specified\n *\n * @example\n * ```tsx\n * // Basic usage\n * const qaPreset = createPresetMenu(\"qa\");\n *\n * // With customization\n * const devPreset = createPresetMenu(\"developer\", {\n * includeComingSoon: false,\n * overrides: {\n * screenshotConfig: { quality: 0.9 },\n * },\n * });\n *\n * <AnyclickProvider\n * adapter={adapter}\n * menuItems={qaPreset.menuItems}\n * screenshotConfig={qaPreset.screenshotConfig}\n * theme={qaPreset.theme}\n * >\n * <App />\n * </AnyclickProvider>\n * ```\n *\n * @since 1.2.0\n */\nexport function createPresetMenu(\n role: PresetRole,\n options: CreatePresetMenuOptions = {},\n): PresetConfig {\n const preset = presetDefaults[role];\n if (!preset) {\n throw new Error(`Unknown preset role: ${role}`);\n }\n\n const includeComingSoon = options.includeComingSoon ?? true;\n const menuItems = (options.overrides?.menuItems ?? preset.menuItems).filter(\n (item) => (includeComingSoon ? true : item.status !== \"comingSoon\"),\n );\n\n // Shallow-clone menu items so consumers can mutate safely\n const clonedMenuItems: ContextMenuItem[] = menuItems.map((item) => ({\n ...item,\n children: item.children\n ? item.children.map((child) => ({ ...child }))\n : undefined,\n }));\n\n return {\n description: preset.description,\n label: preset.label,\n menuItems: clonedMenuItems,\n metadata: {\n ...preset.metadata,\n ...options.overrides?.metadata,\n },\n role: preset.role,\n screenshotConfig: {\n ...preset.screenshotConfig,\n ...options.overrides?.screenshotConfig,\n },\n theme: {\n ...preset.theme,\n ...options.overrides?.theme,\n },\n };\n}\n\n/**\n * Lists all available preset configurations.\n *\n * Returns cloned copies of all presets so they can be safely modified.\n * Useful for displaying available options or building custom preset selectors.\n *\n * @returns Array of all preset configurations\n *\n * @example\n * ```tsx\n * const presets = listPresets();\n *\n * function PresetSelector({ onSelect }) {\n * return (\n * <select onChange={(e) => onSelect(e.target.value)}>\n * {presets.map((preset) => (\n * <option key={preset.role} value={preset.role}>\n * {preset.label} - {preset.description}\n * </option>\n * ))}\n * </select>\n * );\n * }\n * ```\n *\n * @since 1.2.0\n */\nexport function listPresets(): PresetConfig[] {\n return Object.values(presetDefaults).map((preset) => ({\n ...preset,\n menuItems: preset.menuItems.map((item) => ({\n ...item,\n children: item.children\n ? item.children.map((child) => ({ ...child }))\n : undefined,\n })),\n }));\n}\n\nexport { presetDefaults };\n\n/**\n * Creates a menu item for sending selected text or a query to t3.chat.\n *\n * Can be added to any custom menu configuration. Uses the current text\n * selection if available, otherwise opens t3.chat without a pre-filled query.\n *\n * @param options - Optional customization for the menu item\n * @returns A ContextMenuItem configured for t3.chat\n *\n * @example\n * ```tsx\n * import { createT3ChatMenuItem } from \"@ewjdev/anyclick-react\";\n *\n * const menuItems = [\n * { label: \"Bug\", type: \"bug\", showComment: true },\n * createT3ChatMenuItem(),\n * ];\n * ```\n *\n * @since 1.5.0\n */\nexport function createT3ChatMenuItem(\n options: {\n /** Custom label for the menu item */\n label?: string;\n /** Base URL for t3.chat */\n baseUrl?: string;\n } = {},\n): ContextMenuItem {\n const { label = \"Ask t3.chat\", baseUrl = \"https://t3.chat\" } = options;\n\n return {\n label,\n onClick: ({ closeMenu }) => {\n closeMenu();\n if (typeof window === \"undefined\") return false;\n const selection = window.getSelection()?.toString().trim();\n const query = selection && selection.length > 0 ? selection : \"\";\n const url = query\n ? `${baseUrl}/?q=${encodeURIComponent(query)}`\n : baseUrl;\n window.open(url, \"_blank\", \"noopener,noreferrer\");\n return false;\n },\n showComment: false,\n type: \"ask_t3chat\",\n };\n}\n\n/**\n * Gets the currently selected text on the page.\n *\n * Useful for checking if text is selected before showing certain menu items.\n *\n * @returns The selected text, or empty string if nothing is selected\n *\n * @example\n * ```tsx\n * const selection = getSelectedText();\n * if (selection) {\n * console.log(\"Selected:\", selection);\n * }\n * ```\n *\n * @since 1.5.0\n */\nexport function getSelectedText(): string {\n if (typeof window === \"undefined\") return \"\";\n return window.getSelection()?.toString().trim() ?? \"\";\n}\n\n/**\n * Checks if there is currently any text selected on the page.\n *\n * @returns true if text is selected\n *\n * @since 1.5.0\n */\nexport function hasTextSelection(): boolean {\n return getSelectedText().length > 0;\n}\n\n/**\n * Detects if an element is or contains an image that can be uploaded.\n *\n * Checks for:\n * - `<img>` elements\n * - `<picture>` elements\n * - `<canvas>` elements\n * - `<svg>` elements\n * - CSS background images\n *\n * @param element - The element to check\n * @returns Object with isImage flag and optional image source\n *\n * @since 1.5.0\n */\nexport function detectImageElement(element: Element | null): {\n isImage: boolean;\n src?: string;\n type?: \"img\" | \"picture\" | \"svg\" | \"canvas\" | \"background\";\n} {\n if (!element) return { isImage: false };\n\n // Check if element itself is an image\n if (element.tagName === \"IMG\") {\n const img = element as HTMLImageElement;\n return {\n isImage: true,\n src: img.src || img.currentSrc,\n type: \"img\",\n };\n }\n\n // Check if element is a picture element\n if (element.tagName === \"PICTURE\") {\n const img = element.querySelector(\"img\");\n return {\n isImage: true,\n src: img?.src || img?.currentSrc,\n type: \"picture\",\n };\n }\n\n // Check if element is an SVG\n if (element.tagName === \"SVG\" || element.tagName === \"svg\") {\n return {\n isImage: true,\n type: \"svg\",\n };\n }\n\n // Check if element is a canvas\n if (element.tagName === \"CANVAS\") {\n return {\n isImage: true,\n type: \"canvas\",\n };\n }\n\n // Check for CSS background image\n if (typeof window !== \"undefined\") {\n const computedStyle = window.getComputedStyle(element);\n const backgroundImage = computedStyle.backgroundImage;\n\n if (backgroundImage && backgroundImage !== \"none\") {\n const urlMatch = backgroundImage.match(/url\\([\"']?(.+?)[\"']?\\)/);\n if (urlMatch) {\n return {\n isImage: true,\n src: urlMatch[1],\n type: \"background\",\n };\n }\n }\n }\n\n // Check if any child is an image\n const imgChild = element.querySelector(\"img\");\n if (imgChild) {\n return {\n isImage: true,\n src: imgChild.src || imgChild.currentSrc,\n type: \"img\",\n };\n }\n\n return { isImage: false };\n}\n\n/**\n * Creates a menu item for uploading images to UploadThing.\n *\n * The menu item will upload the target element if it's an image,\n * or a screenshot of the element otherwise.\n *\n * Requires an UploadThing adapter to be configured. The onClick handler\n * receives the target element and can use detectImageElement to determine\n * if it's an image.\n *\n * @param options - Configuration options\n * @returns A ContextMenuItem configured for UploadThing\n *\n * @example\n * ```tsx\n * import { createUploadThingMenuItem } from \"@ewjdev/anyclick-react\";\n *\n * const menuItems = [\n * createUploadThingMenuItem({\n * endpoint: \"/api/uploadthing\",\n * onUploadComplete: (result) => {\n * console.log(\"Uploaded:\", result.url);\n * },\n * }),\n * ];\n * ```\n *\n * @since 1.5.0\n */\nexport function createUploadThingMenuItem(\n options: {\n /** Custom label for the menu item */\n label?: string;\n /** API endpoint for uploading */\n endpoint?: string;\n /** Callback when upload completes */\n onUploadComplete?: (result: { url?: string; error?: string }) => void;\n /** Callback when upload fails */\n onUploadError?: (error: Error) => void;\n } = {},\n): ContextMenuItem {\n const {\n label = \"Upload to UploadThing\",\n endpoint = \"/api/uploadthing\",\n onUploadComplete,\n onUploadError,\n } = options;\n\n return {\n label,\n onClick: async ({ closeMenu, targetElement }) => {\n if (!targetElement) {\n onUploadError?.(new Error(\"No target element\"));\n return false;\n }\n\n try {\n const imageInfo = detectImageElement(targetElement);\n\n // If it's an image with a source, fetch and upload it\n if (imageInfo.isImage && imageInfo.src) {\n const response = await fetch(imageInfo.src);\n const blob = await response.blob();\n\n const formData = new FormData();\n const filename = `image-${Date.now()}.${blob.type.split(\"/\")[1] || \"png\"}`;\n formData.append(\"file\", blob, filename);\n\n const uploadResponse = await fetch(endpoint, {\n method: \"POST\",\n body: formData,\n });\n\n if (!uploadResponse.ok) {\n throw new Error(`Upload failed: ${uploadResponse.status}`);\n }\n\n const result = await uploadResponse.json();\n onUploadComplete?.(result);\n } else if (imageInfo.isImage && imageInfo.type === \"canvas\") {\n // Handle canvas elements\n const canvas = targetElement as HTMLCanvasElement;\n const dataUrl = canvas.toDataURL(\"image/png\");\n const response = await fetch(dataUrl);\n const blob = await response.blob();\n\n const formData = new FormData();\n formData.append(\"file\", blob, `canvas-${Date.now()}.png`);\n\n const uploadResponse = await fetch(endpoint, {\n method: \"POST\",\n body: formData,\n });\n\n if (!uploadResponse.ok) {\n throw new Error(`Upload failed: ${uploadResponse.status}`);\n }\n\n const result = await uploadResponse.json();\n onUploadComplete?.(result);\n } else {\n // For non-image elements, you would need to capture a screenshot\n // This requires the screenshot capture functionality\n onUploadError?.(\n new Error(\n \"Element is not an image. Screenshot upload requires anyclick-core.\",\n ),\n );\n }\n } catch (error) {\n onUploadError?.(\n error instanceof Error ? error : new Error(String(error)),\n );\n }\n\n closeMenu();\n return false;\n },\n showComment: false,\n type: \"upload_image\",\n };\n}\n\n/**\n * Creates a menu item for uploading screenshots to UploadThing.\n *\n * This captures a screenshot of the target element and uploads it.\n * Requires the screenshot preview to be enabled for best results.\n *\n * @param options - Configuration options\n * @returns A ContextMenuItem configured for screenshot uploads\n *\n * @example\n * ```tsx\n * import { createUploadScreenshotMenuItem } from \"@ewjdev/anyclick-react\";\n *\n * const menuItems = [\n * createUploadScreenshotMenuItem({\n * endpoint: \"/api/uploadthing\",\n * onUploadComplete: (result) => {\n * navigator.clipboard.writeText(result.url);\n * },\n * }),\n * ];\n * ```\n *\n * @since 1.5.0\n */\nexport function createUploadScreenshotMenuItem(\n options: {\n /** Custom label for the menu item */\n label?: string;\n /** API endpoint for uploading */\n endpoint?: string;\n /** Callback when upload completes */\n onUploadComplete?: (result: { url?: string; error?: string }) => void;\n /** Callback when upload fails */\n onUploadError?: (error: Error) => void;\n } = {},\n): ContextMenuItem {\n const {\n label = \"Upload Screenshot\",\n endpoint = \"/api/uploadthing\",\n onUploadComplete,\n onUploadError,\n } = options;\n\n return {\n label,\n badge: { label: \"Coming soon\", tone: \"info\" },\n status: \"comingSoon\",\n onClick: async ({ closeMenu }) => {\n // This would integrate with the screenshot capture flow\n // For now, show as coming soon since it requires deep integration\n // with the screenshot preview component\n onUploadError?.(\n new Error(\"Screenshot upload will be available in a future release\"),\n );\n closeMenu();\n return false;\n },\n showComment: false,\n type: \"upload_screenshot\",\n };\n}\n","/**\n * Type definitions for @ewjdev/anyclick-react.\n *\n * Contains all public interfaces, types, and utility functions\n * for configuring anyclick providers, menus, and themes.\n *\n * @module types\n * @since 1.0.0\n */\nimport type { CSSProperties, ReactNode } from \"react\";\nimport type {\n AnyclickAdapter,\n AnyclickPayload,\n AnyclickTriggerEvent,\n AnyclickType,\n ScreenshotConfig,\n ScreenshotData,\n} from \"@ewjdev/anyclick-core\";\nimport { CompactModeConfig } from \"./InspectDialog/InspectSimple\";\nimport type { QuickChatConfig } from \"./QuickChat/types\";\n\n// ============================================================================\n// Theme Configuration\n// ============================================================================\n\n/**\n * Theme configuration for AnyclickProvider.\n *\n * Supports nested theming with inheritance - child providers automatically\n * inherit and can override parent theme settings.\n *\n * @example\n * ```tsx\n * const theme: AnyclickTheme = {\n * menuStyle: { backgroundColor: \"#1a1a1a\" },\n * highlightConfig: {\n * colors: { targetColor: \"#ef4444\" },\n * },\n * };\n *\n * <AnyclickProvider adapter={adapter} theme={theme}>\n * <App />\n * </AnyclickProvider>\n * ```\n *\n * @since 1.0.0\n */\nexport interface AnyclickTheme {\n /** Whether anyclick functionality is disabled in this theme */\n disabled?: boolean;\n /**\n * Enable fun mode (go-kart cursor) within this scoped provider.\n * When true/configured, a FunModeBridge can hand off the track to the pointer.\n */\n funMode?: boolean | FunModeThemeConfig;\n /** Configuration for element highlighting */\n highlightConfig?: HighlightConfig;\n /** Custom class name for the context menu */\n menuClassName?: string;\n /** Custom styles for the context menu */\n menuStyle?: CSSProperties;\n /** Configuration for screenshot capture */\n screenshotConfig?: ScreenshotConfig;\n}\n\n/**\n * Optional fun mode configuration (forwarded to pointer fun mode).\n *\n * @since 1.3.0\n */\nexport interface FunModeThemeConfig {\n /** Optional acceleration override */\n acceleration?: number;\n /** Whether fun mode is enabled (default: true) */\n enabled?: boolean;\n /** Optional max speed override for this provider */\n maxSpeed?: number;\n}\n\n// ============================================================================\n// Menu Configuration\n// ============================================================================\n\n/**\n * Menu positioning modes for the context menu.\n *\n * - `static` - Menu stays at exact click position (may go off-screen)\n * - `inView` - Menu adjusts position to stay fully visible in viewport\n * - `dynamic` - User can drag the menu to reposition it\n *\n * @since 1.1.0\n */\nexport type MenuPositionMode = \"dynamic\" | \"inView\" | \"static\";\n\n/**\n * Menu item displayed in the Anyclick context menu.\n *\n * @example\n * ```tsx\n * const menuItems: ContextMenuItem[] = [\n * {\n * type: \"bug\",\n * label: \"Report Bug\",\n * icon: <BugIcon />,\n * showComment: true,\n * },\n * {\n * type: \"feature\",\n * label: \"Request Feature\",\n * showComment: true,\n * requiredRoles: [\"admin\", \"developer\"],\n * },\n * ];\n * ```\n *\n * @since 1.0.0\n */\nexport interface ContextMenuItem {\n /** Optional badge to render next to the label */\n badge?: FeedbackMenuBadge;\n /** Child menu items (creates a submenu) */\n children?: ContextMenuItem[];\n /** Optional icon */\n icon?: ReactNode;\n /** Display label */\n label: string;\n /**\n * Optional click handler for custom behavior.\n * Return `false` (or a Promise resolving to false) to skip the default submission flow.\n */\n onClick?: (context: {\n closeMenu: () => void;\n containerElement: Element | null;\n targetElement: Element | null;\n }) => boolean | Promise<boolean | void> | void;\n /** Optional role(s) required to see this menu item */\n requiredRoles?: string[];\n /** Whether to show a comment input for this type */\n showComment?: boolean;\n /** Optional status to signal availability (e.g., coming soon) */\n status?: FeedbackMenuStatus;\n /** Feedback type for this option (use unique identifier for parent items with children) */\n type: AnyclickType;\n}\n\n/**\n * Visual badge for menu items.\n *\n * @example\n * ```tsx\n * const badge: FeedbackMenuBadge = {\n * label: \"New\",\n * tone: \"success\",\n * };\n * ```\n *\n * @since 1.2.0\n */\nexport interface FeedbackMenuBadge {\n /** Text shown inside the badge */\n label: string;\n /** Optional tone to drive styling */\n tone?: \"info\" | \"neutral\" | \"success\" | \"warning\";\n}\n\n/**\n * Status of a menu item used for presets.\n *\n * - `available` - Item is fully functional\n * - `comingSoon` - Item is visible but disabled\n *\n * @since 1.2.0\n */\nexport type FeedbackMenuStatus = \"available\" | \"comingSoon\";\n\n// ============================================================================\n// Highlight Configuration\n// ============================================================================\n\n/**\n * Configuration for highlight colors.\n *\n * @example\n * ```tsx\n * const colors: HighlightColors = {\n * targetColor: \"#ef4444\", // Red for target\n * containerColor: \"#3b82f6\", // Blue for container\n * targetShadowOpacity: 0.3,\n * containerShadowOpacity: 0.15,\n * };\n * ```\n *\n * @since 1.0.0\n */\nexport interface HighlightColors {\n /** Color for the container element highlight (default: #8b5cf6 - purple) */\n containerColor?: string;\n /** Opacity for the container shadow (default: 0.1) */\n containerShadowOpacity?: number;\n /** Color for the target element highlight (default: #3b82f6 - blue) */\n targetColor?: string;\n /** Opacity for the target shadow (default: 0.25) */\n targetShadowOpacity?: number;\n}\n\n/**\n * Configuration for highlight behavior.\n *\n * @example\n * ```tsx\n * const highlightConfig: HighlightConfig = {\n * enabled: true,\n * colors: { targetColor: \"#ef4444\" },\n * containerSelectors: [\".card\", \".modal\", \"[data-container]\"],\n * minChildrenForContainer: 3,\n * };\n * ```\n *\n * @since 1.0.0\n */\nexport interface HighlightConfig {\n /** Custom colors for highlights */\n colors?: HighlightColors;\n /** CSS selectors to identify container elements */\n containerSelectors?: string[];\n /** Whether to show highlights (default: true) */\n enabled?: boolean;\n /** Minimum number of children for an element to be considered a container (default: 2) */\n minChildrenForContainer?: number;\n}\n\n// ============================================================================\n// User Context\n// ============================================================================\n\n/**\n * User context for role-based menu filtering.\n *\n * @example\n * ```tsx\n * const userContext: AnyclickUserContext = {\n * id: \"user-123\",\n * email: \"user@example.com\",\n * roles: [\"admin\", \"developer\"],\n * };\n *\n * const visibleItems = filterMenuItemsByRole(allMenuItems, userContext);\n * ```\n *\n * @since 1.2.0\n */\nexport interface AnyclickUserContext {\n /** User email */\n email?: string;\n /** User ID */\n id?: string;\n /** User's role(s) */\n roles?: string[];\n}\n\n/**\n * Filters menu items based on user context and required roles.\n *\n * Items without required roles are shown to everyone.\n * Items with required roles are only shown to users who have at least one matching role.\n *\n * @param items - Menu items to filter\n * @param userContext - Optional user context with roles\n * @returns Filtered menu items visible to the user\n *\n * @example\n * ```tsx\n * const allItems: ContextMenuItem[] = [\n * { type: \"bug\", label: \"Report Bug\" },\n * { type: \"admin\", label: \"Admin Panel\", requiredRoles: [\"admin\"] },\n * ];\n *\n * const userContext = { roles: [\"user\"] };\n * const visibleItems = filterMenuItemsByRole(allItems, userContext);\n * // => [{ type: \"bug\", label: \"Report Bug\" }]\n * ```\n *\n * @since 1.2.0\n */\nexport function filterMenuItemsByRole(\n items: ContextMenuItem[],\n userContext?: AnyclickUserContext,\n): ContextMenuItem[] {\n if (!userContext) {\n // If no user context, only show items without required roles\n return items.filter(\n (item) => !item.requiredRoles || item.requiredRoles.length === 0,\n );\n }\n\n const userRoles = userContext.roles ?? [];\n\n return items.filter((item) => {\n // If no required roles, show to everyone\n if (!item.requiredRoles || item.requiredRoles.length === 0) {\n return true;\n }\n // Check if user has any of the required roles\n return item.requiredRoles.some((role) => userRoles.includes(role));\n });\n}\n\n// ============================================================================\n// Provider Props\n// ============================================================================\n\n/**\n * Props for the AnyclickProvider component.\n *\n * @example\n * ```tsx\n * <AnyclickProvider\n * adapter={myAdapter}\n * menuItems={customMenuItems}\n * highlightConfig={{ colors: { targetColor: \"#ef4444\" } }}\n * screenshotConfig={{ enabled: true, showPreview: true }}\n * onSubmitSuccess={(payload) => console.log(\"Submitted:\", payload)}\n * >\n * <App />\n * </AnyclickProvider>\n * ```\n *\n * @since 1.0.0\n */\nexport interface AnyclickProviderProps {\n /** The adapter to use for submitting anyclick */\n adapter: AnyclickAdapter;\n /** Child components */\n children: ReactNode;\n /** Cooldown in milliseconds between submissions (rate limiting) */\n cooldownMs?: number;\n /** Whether the provider is disabled */\n disabled?: boolean;\n /** Header content */\n header?: ReactNode | null;\n /** Configuration for element highlighting */\n highlightConfig?: HighlightConfig;\n /** Maximum number of ancestors to capture */\n maxAncestors?: number;\n /** Maximum length for innerText capture */\n maxInnerTextLength?: number;\n /** Maximum length for outerHTML capture */\n maxOuterHTMLLength?: number;\n /** Custom class name for the context menu */\n menuClassName?: string;\n /** Custom menu items (defaults to Issue, Feature, Like) */\n menuItems?: ContextMenuItem[];\n /** Menu positioning mode (default: 'inView') */\n menuPositionMode?: MenuPositionMode;\n /** Custom styles for the context menu */\n menuStyle?: CSSProperties;\n /** Additional metadata to include with every submission */\n metadata?: Record<string, unknown>;\n /** Callback after failed submission */\n onSubmitError?: (error: Error, payload: AnyclickPayload) => void;\n /** Callback after successful submission */\n onSubmitSuccess?: (payload: AnyclickPayload) => void;\n /**\n * Configuration for QuickChat AI assistant.\n * Set to enable the lightweight AI chat in the context menu.\n */\n quickChatConfig?: QuickChatConfig;\n /**\n * Whether to scope this provider to its children only.\n * When true, events will only be captured for elements within this provider's subtree.\n * When false (default), events are captured for the entire document.\n */\n scoped?: boolean;\n /** Configuration for screenshot capture */\n screenshotConfig?: ScreenshotConfig;\n /** Attributes to strip from outerHTML for privacy */\n stripAttributes?: string[];\n /**\n * Filter function to determine if anyclick should be captured for a target element.\n * Return true to allow anyclick, false to ignore.\n * Accepts both MouseEvent (right-click) and TouchEvent (press-and-hold).\n */\n targetFilter?: (event: AnyclickTriggerEvent, target: Element) => boolean;\n /**\n * Theme configuration for this provider.\n * Themes are inherited from parent providers and merged (child overrides parent).\n * Set to null or { disabled: true } to disable anyclick in this subtree.\n */\n theme?: AnyclickTheme | null;\n /** Duration in ms to hold touch before triggering context menu (default: 500) */\n touchHoldDurationMs?: number;\n /** Maximum movement in px before touch hold is cancelled (default: 10) */\n touchMoveThreshold?: number;\n}\n\n// ============================================================================\n// Context Value\n// ============================================================================\n\n/**\n * Context value exposed by AnyclickProvider.\n *\n * Access via the {@link useAnyclick} hook.\n *\n * @example\n * ```tsx\n * function MyComponent() {\n * const {\n * isEnabled,\n * isSubmitting,\n * openMenu,\n * closeMenu,\n * submitAnyclick,\n * theme,\n * } = useAnyclick();\n *\n * // ...\n * }\n * ```\n *\n * @since 1.0.0\n */\nexport interface AnyclickContextValue {\n /** Close the anyclick menu */\n closeMenu: () => void;\n /** Whether anyclick is currently enabled */\n isEnabled: boolean;\n /** Whether a submission is in progress */\n isSubmitting: boolean;\n /** Open the anyclick menu programmatically */\n openMenu: (element: Element, position: { x: number; y: number }) => void;\n /** The provider's unique ID */\n providerId: string;\n /** Whether this provider is scoped */\n scoped: boolean;\n /** Submit anyclick for a specific element */\n submitAnyclick: (\n element: Element,\n type: AnyclickType,\n comment?: string,\n ) => Promise<void>;\n /** The current merged theme (inherited from ancestors) */\n theme: AnyclickTheme;\n}\n\n// ============================================================================\n// Component Props\n// ============================================================================\n\n/**\n * Props for the ContextMenu component.\n *\n * @since 1.0.0\n */\nexport interface ContextMenuProps {\n /** Custom class name */\n className?: string;\n /** Container element found by highlight logic */\n containerElement: Element | null;\n /** Footer content */\n footer?: ReactNode;\n /** Header content */\n header?: ReactNode;\n /** Configuration for element highlighting */\n highlightConfig?: HighlightConfig;\n /** Whether submission is in progress */\n isSubmitting: boolean;\n /** Menu items to display */\n items: ContextMenuItem[];\n /** Callback when menu is closed */\n onClose: () => void;\n /** Callback when an item is selected */\n onSelect: (\n type: AnyclickType,\n comment?: string,\n screenshots?: ScreenshotData,\n ) => void;\n /** Position of the menu */\n position: { x: number; y: number };\n /** Menu positioning mode (default: 'inView') */\n positionMode?: MenuPositionMode;\n /**\n * Configuration for QuickChat AI assistant.\n * When provided, shows the QuickChat interface in the context menu.\n */\n quickChatConfig?: QuickChatConfig;\n /** Configuration for screenshot capture */\n screenshotConfig?: ScreenshotConfig;\n /** Custom styles */\n style?: CSSProperties;\n /** Target element for anyclick */\n targetElement: Element | null;\n /** Whether the menu is visible */\n visible: boolean;\n}\n\n/**\n * Props for the ScreenshotPreview component.\n *\n * @since 1.0.0\n */\nexport interface ScreenshotPreviewProps {\n /** Whether screenshots are loading */\n isLoading: boolean;\n /** Whether submission is in progress */\n isSubmitting: boolean;\n /** Callback when user cancels */\n onCancel: () => void;\n /** Callback when user confirms screenshots */\n onConfirm: (screenshots: ScreenshotData) => void;\n /** Callback when user wants to retake screenshots */\n onRetake: () => void;\n /** Captured screenshot data */\n screenshots: ScreenshotData | null;\n}\n\n// ============================================================================\n// Utility Functions\n// ============================================================================\n\n/**\n * Generates compact styles from a CompactModeConfig.\n *\n * Used internally by InspectDialog to apply compact mode styling.\n *\n * @param config - The compact mode configuration\n * @returns Record of style objects keyed by component name\n * @internal\n */\nexport function generateCompactStyles(\n config: CompactModeConfig,\n): Record<string, React.CSSProperties> {\n return {\n actionButton: {\n fontSize: `${config.fonts.button}px`,\n gap: config.gaps.button,\n padding: config.spacing.buttonPadding,\n },\n actionButtonDanger: {\n fontSize: `${config.fonts.button}px`,\n padding: config.spacing.buttonDangerPadding,\n },\n actionButtonPrimary: {\n fontSize: `${config.fonts.button}px`,\n gap: config.gaps.button,\n padding: config.spacing.buttonPrimaryPadding,\n },\n badge: {\n fontSize: `${config.fonts.badge}px`,\n padding: config.spacing.badgePadding,\n },\n classes: {\n fontSize: `${config.fonts.tag}px`,\n },\n closeButton: {\n height: `${config.sizes.closeButton}px`,\n width: `${config.sizes.closeButton}px`,\n },\n copyButtonSmall: {\n height: `${config.sizes.copyButtonSmall}px`,\n width: `${config.sizes.copyButtonSmall}px`,\n },\n dialog: {\n fontSize: `${config.fonts.base}px`,\n width: `${config.sizes.dialogWidth}px`,\n },\n footer: {\n gap: config.gaps.footer,\n padding: config.spacing.footerPadding,\n },\n header: {\n padding: config.spacing.headerPadding,\n },\n headerTitle: {\n fontSize: `${config.fonts.title}px`,\n gap: config.gaps.headerTitle,\n },\n id: {\n fontSize: `${config.fonts.tag}px`,\n },\n identity: {\n padding: config.spacing.identityPadding,\n },\n pinButtons: {\n gap: config.gaps.pinButtons,\n padding: \"1px\",\n },\n propertyLabel: {\n fontSize: `${config.fonts.property}px`,\n },\n propertyRow: {\n gap: config.gaps.propertyRow,\n padding: config.spacing.propertyRowPadding,\n },\n propertyValue: {\n fontSize: `${config.fonts.property}px`,\n gap: config.gaps.propertyValue,\n },\n sectionContent: {\n padding: config.spacing.sectionContentPadding,\n },\n sectionHeader: {\n fontSize: `${config.fonts.section}px`,\n padding: config.spacing.sectionHeaderPadding,\n },\n sectionTitle: {\n letterSpacing: config.letterSpacing.sectionTitle,\n },\n selectorCode: {\n fontSize: `${config.fonts.selector}px`,\n padding: config.spacing.selectorCodePadding,\n },\n styleCategory: {\n marginBottom: `${config.sizes.categoryMarginBottom}px`,\n },\n styleCategoryHeader: {\n fontSize: `${config.fonts.property}px`,\n marginBottom: `${config.sizes.styleCategoryHeaderMarginBottom}px`,\n },\n styleRow: {\n fontSize: `${config.fonts.styleRow}px`,\n padding: config.spacing.styleRowPadding,\n },\n styleValue: {\n maxWidth: `${config.sizes.styleValueMaxWidth}px`,\n },\n tag: {\n fontSize: `${config.fonts.tag}px`,\n },\n };\n}\n","/**\n * @ewjdev/anyclick-react\n *\n * React provider and context menu UI for UI feedback capture.\n * Enables right-click context menus for submitting feedback, capturing screenshots,\n * and integrating with various adapters (GitHub, AI agents, etc.)\n *\n * @packageDocumentation\n * @module @ewjdev/anyclick-react\n * @since 1.0.0\n *\n * @example\n * ```tsx\n * import { AnyclickProvider } from \"@ewjdev/anyclick-react\";\n * import { createHttpAdapter } from \"@ewjdev/anyclick-github\";\n *\n * const adapter = createHttpAdapter({ endpoint: \"/api/feedback\" });\n *\n * function App() {\n * return (\n * <AnyclickProvider adapter={adapter}>\n * <YourApp />\n * </AnyclickProvider>\n * );\n * }\n * ```\n */\n\"use client\";\n// Shared styles (prefixed, no preflight) for anyclick react surfaces.\nimport \"./styles/tailwind.css\";\n\n// ============================================================================\n// Core Components\n// ============================================================================\n\n/**\n * Main provider component for anyclick functionality.\n * Wraps your app to enable right-click feedback capture.\n * @see {@link AnyclickProviderProps} for configuration options\n */\nexport { AnyclickProvider } from \"./AnyclickProvider\";\n\n/**\n * Bridge component for enabling fun mode (go-kart cursor) within a scoped provider.\n * @tag {experimental}\n */\nexport { FunModeBridge } from \"./FunModeBridge\";\n\n/**\n * Standalone context menu component for custom implementations.\n * @see {@link ContextMenuProps} for configuration options\n */\nexport { ContextMenu } from \"./ContextMenu\";\n\n/**\n * Screenshot preview component displayed before sending feedback.\n * @see {@link ScreenshotPreviewProps} for configuration options\n */\nexport { ScreenshotPreview } from \"./ScreenshotPreview\";\n\n// ============================================================================\n// Deprecated Exports (Backward Compatibility)\n// ============================================================================\n\n/**\n * @deprecated Use {@link AnyclickProvider} instead. Will be removed in v2.0.0.\n */\nexport { FeedbackProvider } from \"./AnyclickProvider\";\n\n// ============================================================================\n// Context and Hooks\n// ============================================================================\n\n/**\n * React context for anyclick functionality.\n * Use with `useContext` for custom implementations.\n */\nexport { AnyclickContext } from \"./context\";\n\n/**\n * Hook to access anyclick context values.\n * @throws {Error} When used outside of AnyclickProvider\n * @example\n * ```tsx\n * function MyComponent() {\n * const { openMenu, isSubmitting } = useAnyclick();\n * // ...\n * }\n * ```\n */\nexport { useAnyclick } from \"./context\";\n\n/**\n * @deprecated Use {@link AnyclickContext} instead. Will be removed in v2.0.0.\n */\nexport { FeedbackContext } from \"./context\";\n\n/**\n * @deprecated Use {@link useAnyclick} instead. Will be removed in v2.0.0.\n */\nexport { useFeedback } from \"./context\";\n\n// ============================================================================\n// Store (Advanced Use Cases)\n// ============================================================================\n\n/**\n * Zustand store hook for managing provider instances.\n * For advanced use cases like custom provider hierarchies.\n */\nexport { useProviderStore } from \"./store\";\n\n/**\n * Generates a unique ID for a provider instance.\n */\nexport { generateProviderId } from \"./store\";\n\n/**\n * Dispatches a context menu event to matching providers.\n */\nexport { dispatchContextMenuEvent } from \"./store\";\n\n// ============================================================================\n// UI primitives (shadcn-inspired, prefixed Tailwind)\n// ============================================================================\nexport * from \"./ui\";\n\n/**\n * Provider instance type for advanced store management.\n */\nexport type { ProviderInstance } from \"./store\";\n\n// ============================================================================\n// Types\n// ============================================================================\n\nexport type {\n /** Props for AnyclickProvider component */\n AnyclickProviderProps,\n /** Context value exposed by AnyclickProvider */\n AnyclickContextValue,\n /** Theme configuration for AnyclickProvider */\n AnyclickTheme,\n /** Menu item configuration */\n ContextMenuItem,\n /** Fun mode theme configuration */\n FunModeThemeConfig,\n /** Props for ContextMenu component */\n ContextMenuProps,\n /** Highlight color configuration */\n HighlightColors,\n /** Highlight behavior configuration */\n HighlightConfig,\n /** User context for role-based filtering */\n AnyclickUserContext,\n /** Props for ScreenshotPreview component */\n ScreenshotPreviewProps,\n /** Menu positioning modes */\n MenuPositionMode,\n /** Visual badge for menu items */\n FeedbackMenuBadge,\n /** Status of a menu item */\n FeedbackMenuStatus,\n} from \"./types\";\n\n// ============================================================================\n// Presets\n// ============================================================================\n\n/**\n * Creates a preset menu configuration for a specific role.\n * @param role - The preset role (qa, pm, designer, developer, chrome)\n * @param options - Optional configuration overrides\n * @returns A complete preset configuration\n * @example\n * ```tsx\n * const qaPreset = createPresetMenu(\"qa\");\n * <AnyclickProvider\n * adapter={adapter}\n * menuItems={qaPreset.menuItems}\n * screenshotConfig={qaPreset.screenshotConfig}\n * />\n * ```\n */\nexport { createPresetMenu } from \"./presets\";\n\n/**\n * Lists all available preset configurations.\n */\nexport { listPresets } from \"./presets\";\n\n/**\n * Default preset configurations by role.\n */\nexport { presetDefaults } from \"./presets\";\n\n/**\n * Creates a menu item for sending selected text to t3.chat.\n * @param options - Optional customization (label, baseUrl)\n * @returns A ContextMenuItem configured for t3.chat\n * @example\n * ```tsx\n * const menuItems = [\n * { label: \"Bug\", type: \"bug\", showComment: true },\n * createT3ChatMenuItem(),\n * ];\n * ```\n */\nexport { createT3ChatMenuItem } from \"./presets\";\n\n/**\n * Gets the currently selected text on the page.\n * @returns The selected text, or empty string if nothing is selected\n */\nexport { getSelectedText } from \"./presets\";\n\n/**\n * Checks if there is currently any text selected on the page.\n * @returns true if text is selected\n */\nexport { hasTextSelection } from \"./presets\";\n\n/**\n * Detects if an element is or contains an image.\n * @param element - The element to check\n * @returns Object with isImage flag and optional image source\n */\nexport { detectImageElement } from \"./presets\";\n\n/**\n * Creates a menu item for uploading images to UploadThing.\n * @param options - Configuration options\n * @returns A ContextMenuItem configured for image uploads\n */\nexport { createUploadThingMenuItem } from \"./presets\";\n\n/**\n * Creates a menu item for uploading screenshots to UploadThing.\n * @param options - Configuration options\n * @returns A ContextMenuItem configured for screenshot uploads\n */\nexport { createUploadScreenshotMenuItem } from \"./presets\";\n\nexport type {\n /** Available preset roles */\n PresetRole,\n /** Preset configuration structure */\n PresetConfig,\n /** Options for creating preset menus */\n CreatePresetMenuOptions,\n} from \"./presets\";\n\n// ============================================================================\n// Utilities\n// ============================================================================\n\n/**\n * Filters menu items based on user roles.\n * @param items - Menu items to filter\n * @param userContext - User context with roles\n * @returns Filtered menu items visible to the user\n */\nexport { filterMenuItemsByRole } from \"./types\";\n\n// ============================================================================\n// Core Re-exports\n// ============================================================================\n\nexport type {\n /** Feedback type identifier */\n AnyclickType,\n /** Feedback submission payload */\n AnyclickPayload,\n /** Adapter interface for submitting feedback */\n AnyclickAdapter,\n /** DOM element context information */\n ElementContext,\n /** Page-level context information */\n PageContext,\n /** Captured screenshot data */\n ScreenshotData,\n /** Screenshot capture configuration */\n ScreenshotConfig,\n /** Individual screenshot capture */\n ScreenshotCapture,\n /** Screenshot capture mode */\n ScreenshotCaptureMode,\n} from \"@ewjdev/anyclick-core\";\n\nexport {\n /** Captures all configured screenshots */\n captureAllScreenshots,\n /** Captures a single screenshot */\n captureScreenshot,\n /** Checks if screenshot capture is supported */\n isScreenshotSupported,\n /** Formats bytes to human-readable string */\n formatBytes,\n /** Estimates total size of screenshot data */\n estimateTotalSize,\n /** Default screenshot configuration */\n DEFAULT_SCREENSHOT_CONFIG,\n /** Default sensitive element selectors */\n DEFAULT_SENSITIVE_SELECTORS,\n} from \"@ewjdev/anyclick-core\";\n\n// ============================================================================\n// Styles\n// ============================================================================\n\n/**\n * Default menu styles for customization.\n */\nexport { menuStyles } from \"./styles\";\n\n/**\n * Dark mode menu styles.\n */\nexport { darkMenuStyles } from \"./styles\";\n\n/**\n * CSS custom properties for menu theming.\n * Override these via the `style` prop on AnyclickProvider.\n */\nexport { menuCSSVariables } from \"./styles\";\n\n/**\n * Gets badge styles for a specific tone.\n */\nexport { getBadgeStyle } from \"./styles\";\n\n// ============================================================================\n// Highlight Utilities\n// ============================================================================\n\n/**\n * Finds the closest container parent element based on configuration.\n */\nexport { findContainerParent } from \"./highlight\";\n\n/**\n * Applies highlight styling to target element.\n */\nexport { highlightTarget } from \"./highlight\";\n\n/**\n * Applies highlight styling to container element.\n */\nexport { highlightContainer } from \"./highlight\";\n\n/**\n * Removes all highlight styling from the document.\n */\nexport { clearHighlights } from \"./highlight\";\n\n/**\n * Applies highlights to both target and container elements.\n */\nexport { applyHighlights } from \"./highlight\";\n\n/**\n * Default highlight colors.\n */\nexport { defaultHighlightColors } from \"./highlight\";\n\n/**\n * Default CSS selectors for identifying container elements.\n */\nexport { defaultContainerSelectors } from \"./highlight\";\n\n// ============================================================================\n// Inspect Simple (Lightweight Inspector)\n// ============================================================================\n\n/**\n * Lightweight element inspector component for mobile-friendly inspection.\n */\nexport { InspectSimple } from \"./InspectDialog/InspectSimple\";\n\n/**\n * Default compact mode configuration for InspectSimple.\n */\nexport { DEFAULT_COMPACT_CONFIG } from \"./InspectDialog/InspectSimple\";\n\nexport type {\n /** Props for InspectSimple component */\n InspectSimpleProps,\n /** Dialog pinned position options */\n PinnedPosition,\n /** Compact mode configuration */\n CompactModeConfig,\n} from \"./InspectDialog/InspectSimple\";\n\n/**\n * Manager component that listens for inspect events and renders InspectSimple.\n * Place this component once in your app to enable inspect functionality.\n */\nexport { InspectDialogManager } from \"./InspectDialog/InspectDialogManager\";\n\n/**\n * Opens the inspect dialog for a given element.\n */\nexport { openInspectDialog } from \"./InspectDialog/InspectDialogManager\";\n\n/**\n * Event name for inspect dialog events.\n */\nexport { INSPECT_DIALOG_EVENT } from \"./InspectDialog/InspectDialogManager\";\n\nexport type {\n /** Props for InspectDialogManager component */\n InspectDialogManagerProps,\n /** Event detail for inspect dialog events */\n InspectDialogEventDetail,\n} from \"./InspectDialog/InspectDialogManager\";\n\n// ============================================================================\n// Branding\n// ============================================================================\n\n/**\n * Anyclick logo component for branding.\n */\nexport { AnyclickLogo } from \"./AnyclickLogo\";\n\nexport type {\n /** Props for AnyclickLogo component */\n AnyclickLogoProps,\n} from \"./AnyclickLogo\";\n\n// ============================================================================\n// QuickChat\n// ============================================================================\n\n/**\n * Lightweight AI chat component for the context menu.\n * Provides quick answers about elements with streaming responses.\n */\nexport { QuickChat } from \"./QuickChat\";\n\n/**\n * Hook for managing QuickChat state and logic.\n */\nexport { useQuickChat } from \"./QuickChat\";\n\n/**\n * QuickChat component styles.\n */\nexport { quickChatStyles, quickChatKeyframes } from \"./QuickChat\";\n\n/**\n * Default QuickChat configuration.\n */\nexport { DEFAULT_QUICK_CHAT_CONFIG } from \"./QuickChat\";\n\nexport type {\n /** QuickChat component props */\n QuickChatProps,\n /** QuickChat configuration options */\n QuickChatConfig,\n /** Chat message structure */\n ChatMessage,\n /** Context chunk for redaction UI */\n ContextChunk,\n /** Quick action for AI responses */\n QuickAction,\n /** Suggested prompt from pre-pass */\n SuggestedPrompt,\n /** QuickChat hook state */\n QuickChatState,\n /** t3.chat integration configuration */\n T3ChatIntegrationConfig,\n} from \"./QuickChat\";\n\n// ============================================================================\n// IDE Integration\n// ============================================================================\n\n/**\n * Opens a source file in the preferred IDE.\n */\nexport { openInIDE } from \"./ide\";\n\n/**\n * Builds a URL for opening a file in an IDE.\n */\nexport { buildIDEUrl } from \"./ide\";\n\n/**\n * Checks if an IDE protocol is supported.\n */\nexport { isIDEProtocolSupported } from \"./ide\";\n\n/**\n * Detects the user's preferred IDE from environment.\n */\nexport { detectPreferredIDE } from \"./ide\";\n\n/**\n * Extracts source location from element's data attributes.\n */\nexport { getSourceLocationFromElement } from \"./ide\";\n\n/**\n * Finds source location by searching ancestor elements.\n */\nexport { findSourceLocationInAncestors } from \"./ide\";\n\n/**\n * Creates a configured IDE opener function.\n */\nexport { createIDEOpener } from \"./ide\";\n\n/**\n * Formats source location as a readable string.\n */\nexport { formatSourceLocation } from \"./ide\";\n\nexport type {\n /** Supported IDE protocols */\n IDEProtocol,\n /** IDE configuration options */\n IDEConfig,\n /** Source file location information */\n SourceLocation,\n} from \"./ide\";\n\n// ============================================================================\n// Inspect Utilities (Core Re-exports)\n// ============================================================================\n\nexport {\n /** Gets computed styles for an element */\n getComputedStyles,\n /** Gets accessibility information for an element */\n getAccessibilityInfo,\n /** Gets box model information for an element */\n getBoxModelInfo,\n /** Gets element attributes */\n getAttributes,\n /** Gets comprehensive element inspect information */\n getElementInspectInfo,\n /** Formats styles as CSS string */\n formatStylesAsCSS,\n /** Formats box model as readable string */\n formatBoxModel,\n /** Curated list of important CSS properties */\n CURATED_STYLE_PROPERTIES,\n /** All curated CSS properties */\n ALL_CURATED_PROPERTIES,\n} from \"@ewjdev/anyclick-core\";\n\nexport type {\n /** Computed styles information */\n ComputedStylesInfo,\n /** Accessibility information */\n AccessibilityInfo,\n /** Box model information */\n BoxModelInfo,\n /** Element inspection information */\n ElementInspectInfo,\n} from \"@ewjdev/anyclick-core\";\n","\"use client\";\n\nimport React from \"react\";\n\nexport interface AnyclickLogoProps {\n /** Size of the logo in pixels. Defaults to 64 */\n size?: number;\n /** Border width in pixels. Defaults to 2 (same as default cursor stroke) */\n borderWidth?: number;\n /** Primary color for the circle border and cursor. Defaults to #3b82f6 (blue-500) */\n primaryColor?: string;\n /** Background color of the circle. Defaults to rgba(59, 130, 246, 0.1) */\n backgroundColor?: string;\n /** Custom class name */\n className?: string;\n /** Custom styles */\n style?: React.CSSProperties;\n /** Click handler */\n onClick?: () => void;\n}\n\n/**\n * Anyclick Logo - A circle with a cursor pointer in the center\n * The cursor is styled similarly to the default system cursor\n */\nexport function AnyclickLogo({\n size = 64,\n borderWidth = 2,\n primaryColor = \"#3b82f6\",\n backgroundColor = \"rgba(59, 130, 246, 0.1)\",\n className,\n style,\n onClick,\n}: AnyclickLogoProps) {\n // Cursor size is proportional to the circle size\n const cursorSize = size * 0.45;\n const cursorStroke = borderWidth;\n\n return (\n <svg\n width={size}\n height={size}\n viewBox={`0 0 ${size} ${size}`}\n fill=\"none\"\n xmlns=\"http://www.w3.org/2000/svg\"\n className={className}\n style={{ cursor: onClick ? \"pointer\" : undefined, ...style }}\n onClick={onClick}\n role={onClick ? \"button\" : \"img\"}\n aria-label=\"Anyclick Logo\"\n >\n {/* Circle background */}\n <circle\n cx={size / 2}\n cy={size / 2}\n r={size / 2 - borderWidth / 2}\n fill={backgroundColor}\n stroke={primaryColor}\n strokeWidth={borderWidth}\n />\n\n {/* Cursor pointer - centered in the circle */}\n <g\n transform={`translate(${(size - cursorSize) / 2}, ${(size - cursorSize) / 2})`}\n >\n {/* Cursor shape - classic pointer arrow */}\n <path\n d={`\n M ${cursorSize * 0.15} ${cursorSize * 0.08}\n L ${cursorSize * 0.15} ${cursorSize * 0.85}\n L ${cursorSize * 0.35} ${cursorSize * 0.65}\n L ${cursorSize * 0.55} ${cursorSize * 0.85}\n L ${cursorSize * 0.65} ${cursorSize * 0.75}\n L ${cursorSize * 0.45} ${cursorSize * 0.55}\n L ${cursorSize * 0.7} ${cursorSize * 0.55}\n Z\n `}\n fill=\"white\"\n stroke={primaryColor}\n strokeWidth={cursorStroke}\n strokeLinejoin=\"round\"\n strokeLinecap=\"round\"\n />\n </g>\n </svg>\n );\n}\n\nexport default AnyclickLogo;\n"],"mappings":"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","names":["useCallback","useEffect","useMemo","useRef","useState","React","useCallback","useEffect","useRef","useState","useCallback","useEffect","useMemo","useRef","useState","LoadingDots","useRef","useState","useCallback","useEffect","useMemo","React","useMemo","useState","Fragment","jsx","jsxs","React","ScreenshotPreview","useState","useMemo","injectStyles","Fragment","jsx","jsxs","React","MenuItem","useState","BackButton","CommentForm","useRef","useEffect","useCallback","create","jsx","jsxs","OFFSCREEN_POSITION","useState","useRef","useCallback","useMemo","mergedTheme","useEffect","useEffect","useMemo","useRef","useRef","useMemo","useEffect","jsx","forwardRef","jsx","forwardRef","useCallback","useEffect","useState","useEffect","useMemo","useRef","useState","getElementInspectInfo","Copy","ExternalLink","X","Fragment","jsx","jsxs","useState","useEffect","useRef","getElementInspectInfo","useMemo","ExternalLink","X","Copy","jsx","useState","useCallback","useEffect","captureAllScreenshots","captureScreenshot","isScreenshotSupported","formatBytes","estimateTotalSize","DEFAULT_SCREENSHOT_CONFIG","jsx","jsxs","getElementInspectInfo"]}