import { jsx, jsxs } from 'react/jsx-runtime';
import React__default, { useMemo, useState, useRef, useEffect, useCallback, useLayoutEffect } from 'react';
import { createPortal } from 'react-dom';
import { AnimatePresence, motion } from 'motion/react';
import { mentionTheme } from './Mention.theme.js';
import { cn } from '../../../utils/cn.js';
import { Avatar } from '../../core/Avatar/Avatar.js';
import { Tag } from '../../core/Tag/Tag.js';
import { useIsClient } from '../../../hooks/useIsClient.js';
import { normalizeSegments, setCaretAtOffset, getPlainTextOffset, parseDOMToSegments, serializeSegments, serializeSegmentsMasked, insertMentionIntoSegments, MENTION_ATTR } from './Mention.utils.js';

// ---------------------------------------------------------------------------
// Helpers
// ---------------------------------------------------------------------------
const detectActiveMention = (text, caretPos, triggerChars) => {
    if (caretPos === 0)
        return null;
    for (let i = caretPos - 1; i >= 0; i--) {
        const ch = text[i];
        if (ch === "\n")
            return null;
        if (triggerChars.includes(ch)) {
            if (i === 0 || /\s/.test(text[i - 1])) {
                const query = text.slice(i + 1, caretPos);
                return { trigger: ch, query, startIndex: i };
            }
            return null;
        }
    }
    return null;
};
const filterSuggestions = (suggestions, query, max) => {
    if (!query)
        return suggestions.slice(0, max);
    const lower = query.toLowerCase();
    return suggestions
        .filter((s) => s.label.toLowerCase().includes(lower) ||
        (s.description && s.description.toLowerCase().includes(lower)))
        .slice(0, max);
};
/** Plain-text offset at the start of a given segment index. */
const getOffsetAtSegment = (segs, segIndex) => {
    let offset = 0;
    for (let i = 0; i < segIndex; i++) {
        const s = segs[i];
        if (s.type === "text") {
            offset += s.text.length;
        }
        else {
            offset += s.data.trigger.length + s.data.label.length;
        }
    }
    return offset;
};
// ---------------------------------------------------------------------------
// Dropdown animation
// ---------------------------------------------------------------------------
const dropdownVariants = {
    initial: { opacity: 0, y: -6, scale: 0.96 },
    visible: {
        opacity: 1,
        y: 0,
        scale: 1,
        transition: { duration: 0.18, ease: "easeOut" },
    },
    exit: {
        opacity: 0,
        y: -6,
        scale: 0.96,
        transition: { duration: 0.12, ease: "easeIn" },
    },
};
// ---------------------------------------------------------------------------
// Mention component
// ---------------------------------------------------------------------------
const Mention = React__default.forwardRef(({ triggers: triggersProp, suggestions: suggestionsProp, onSearch: onSearchProp, value: controlledValue, defaultValue = "", onChange, onMentionSelect, onMentionsChange, placeholder, size = "md", maxSuggestions = 8, className, wrapperClassName, dropdownClassName, theme: themeOverrides, disabled = false, renderSuggestion, emptyMessage = "No results found", loading = false, mentionTagSize = "sm", mentionTagClassName, rows = 3, ...props }, ref) => {
    const theme = useMemo(() => ({ ...mentionTheme, ...(themeOverrides || {}) }), [themeOverrides]);
    const triggers = useMemo(() => {
        if (triggersProp && triggersProp.length > 0)
            return triggersProp;
        return [
            {
                trigger: "@",
                suggestions: suggestionsProp || [],
                onSearch: onSearchProp,
            },
        ];
    }, [triggersProp, suggestionsProp, onSearchProp]);
    const triggerChars = useMemo(() => triggers.map((t) => t.trigger), [triggers]);
    // --- Segment model ---
    const [segments, setSegments] = useState(() => normalizeSegments([{ type: "text", text: defaultValue }]));
    const mentionMapRef = useRef(new Map());
    // Controlled mode: if external value diverges, reset segments to plain text
    const lastSerializedRef = useRef(defaultValue);
    const isControlled = controlledValue !== undefined;
    useEffect(() => {
        if (isControlled && controlledValue !== lastSerializedRef.current) {
            // External value changed — reset to plain text
            const newSegs = normalizeSegments([
                { type: "text", text: controlledValue },
            ]);
            setSegments(newSegs);
            mentionMapRef.current.clear();
            lastSerializedRef.current = controlledValue;
        }
    }, [isControlled, controlledValue]);
    // Focus state
    const [isFocused, setIsFocused] = useState(false);
    // Active mention context
    const [activeMention, setActiveMention] = useState(null);
    const [highlightedIndex, setHighlightedIndex] = useState(-1);
    // Dropdown position
    const [dropdownPos, setDropdownPos] = useState({
        top: -9999,
        left: -9999,
        width: 280,
    });
    // Refs
    const editableRef = useRef(null);
    const wrapperRef = useRef(null);
    const dropdownRef = useRef(null);
    const composingRef = useRef(false);
    const caretRestoreRef = useRef(null);
    // Track which segment index is "selected" when clicking a mention tag
    const [selectedMentionIndex, setSelectedMentionIndex] = useState(null);
    const isClient = useIsClient();
    const setEditableRef = useCallback((el) => {
        editableRef.current = el;
        if (typeof ref === "function") {
            ref(el);
        }
        else if (ref) {
            ref.current = el;
        }
    }, [ref]);
    // --- Derived ---
    const activeTriggerConfig = useMemo(() => {
        if (!activeMention)
            return null;
        return triggers.find((t) => t.trigger === activeMention.trigger) || null;
    }, [activeMention, triggers]);
    const filteredSuggestions = useMemo(() => {
        if (!activeTriggerConfig)
            return [];
        return filterSuggestions(activeTriggerConfig.suggestions, (activeMention === null || activeMention === void 0 ? void 0 : activeMention.query) || "", maxSuggestions);
    }, [activeTriggerConfig, activeMention === null || activeMention === void 0 ? void 0 : activeMention.query, maxSuggestions]);
    const isDropdownOpen = activeMention !== null && (filteredSuggestions.length > 0 || loading);
    // Fire onSearch when query changes
    useEffect(() => {
        if (!activeMention || !(activeTriggerConfig === null || activeTriggerConfig === void 0 ? void 0 : activeTriggerConfig.onSearch))
            return;
        activeTriggerConfig.onSearch(activeMention.query);
    }, [activeMention === null || activeMention === void 0 ? void 0 : activeMention.query, activeMention === null || activeMention === void 0 ? void 0 : activeMention.trigger]); // eslint-disable-line react-hooks/exhaustive-deps
    // Reset highlighted index when suggestions change
    useEffect(() => {
        setHighlightedIndex(filteredSuggestions.length > 0 ? 0 : -1);
    }, [filteredSuggestions.length, activeMention === null || activeMention === void 0 ? void 0 : activeMention.query]);
    // --- Notify onMentionsChange ---
    const notifyMentionsChange = useCallback((segs) => {
        if (!onMentionsChange)
            return;
        const mentions = segs
            .filter((s) => s.type === "mention")
            .map((s) => s.data);
        onMentionsChange(mentions);
    }, [onMentionsChange]);
    // --- Dropdown positioning via Range API ---
    const updateDropdownPosition = useCallback(() => {
        const sel = window.getSelection();
        if (!sel || sel.rangeCount === 0 || !editableRef.current)
            return;
        const range = sel.getRangeAt(0).cloneRange();
        range.collapse(true);
        const rect = range.getBoundingClientRect();
        // Fallback if rect is zero (e.g. empty container)
        if (rect.top === 0 && rect.left === 0) {
            const containerRect = editableRef.current.getBoundingClientRect();
            setDropdownPos({
                top: containerRect.bottom + 4,
                left: containerRect.left,
                width: 280,
            });
            return;
        }
        setDropdownPos({
            top: rect.bottom + 4,
            left: rect.left,
            width: 280,
        });
    }, []);
    useLayoutEffect(() => {
        if (activeMention) {
            updateDropdownPosition();
        }
    }, [activeMention, updateDropdownPosition]);
    // Reposition on scroll / resize
    useEffect(() => {
        if (!isDropdownOpen)
            return;
        const handleReposition = () => updateDropdownPosition();
        window.addEventListener("scroll", handleReposition, {
            passive: true,
            capture: true,
        });
        window.addEventListener("resize", handleReposition, { passive: true });
        return () => {
            window.removeEventListener("scroll", handleReposition, true);
            window.removeEventListener("resize", handleReposition);
        };
    }, [isDropdownOpen, updateDropdownPosition]);
    // Click outside to close dropdown
    useEffect(() => {
        if (!isDropdownOpen)
            return;
        const handleClickOutside = (e) => {
            if (dropdownRef.current &&
                !dropdownRef.current.contains(e.target) &&
                editableRef.current &&
                !editableRef.current.contains(e.target)) {
                setActiveMention(null);
            }
        };
        document.addEventListener("mousedown", handleClickOutside);
        return () => document.removeEventListener("mousedown", handleClickOutside);
    }, [isDropdownOpen]);
    // --- DOM cleanup & caret restore after React re-render ---
    useLayoutEffect(() => {
        const el = editableRef.current;
        if (!el || composingRef.current)
            return;
        // Remove stray text nodes that are direct children of the container.
        // Browser contentEditable can insert characters as direct text children
        // instead of inside our React-managed <span> elements. These stray nodes
        // cause text duplication when parseDOMToSegments reads them alongside
        // the span content on the next input event.
        for (let i = el.childNodes.length - 1; i >= 0; i--) {
            const child = el.childNodes[i];
            if (child.nodeType === Node.TEXT_NODE) {
                el.removeChild(child);
            }
        }
        if (caretRestoreRef.current !== null) {
            setCaretAtOffset(el, caretRestoreRef.current);
            caretRestoreRef.current = null;
        }
    });
    // --- Handlers ---
    const updateFromDOM = useCallback(() => {
        if (!editableRef.current || composingRef.current)
            return;
        // Save caret position BEFORE triggering re-render
        const offset = getPlainTextOffset(editableRef.current);
        const newSegs = parseDOMToSegments(editableRef.current, mentionMapRef.current);
        const serialized = serializeSegments(newSegs);
        // Restore caret after React re-renders the contentEditable
        if (offset !== null) {
            caretRestoreRef.current = offset;
        }
        setSegments(newSegs);
        lastSerializedRef.current = serialized;
        if (!isControlled) {
            onChange === null || onChange === void 0 ? void 0 : onChange(serialized);
        }
        else {
            onChange === null || onChange === void 0 ? void 0 : onChange(serialized);
        }
        notifyMentionsChange(newSegs);
        // Detect active mention using masked text (hides @ from existing mentions)
        if (offset !== null) {
            const maskedText = serializeSegmentsMasked(newSegs);
            const mention = detectActiveMention(maskedText, offset, triggerChars);
            setActiveMention(mention);
        }
    }, [isControlled, onChange, triggerChars, notifyMentionsChange]);
    const handleInput = useCallback(() => {
        setSelectedMentionIndex(null);
        updateFromDOM();
    }, [updateFromDOM]);
    const handleSelect = useCallback(() => {
        if (!editableRef.current || composingRef.current)
            return;
        const offset = getPlainTextOffset(editableRef.current);
        if (offset !== null) {
            const maskedText = serializeSegmentsMasked(segments);
            const mention = detectActiveMention(maskedText, offset, triggerChars);
            setActiveMention(mention);
        }
    }, [segments, triggerChars]);
    const insertMention = useCallback((suggestion) => {
        if (!activeMention || !editableRef.current)
            return;
        const { trigger, startIndex, query } = activeMention;
        const replaceLength = 1 + query.length; // trigger + query
        const mentionData = {
            id: suggestion.id,
            label: suggestion.label,
            trigger,
            avatar: suggestion.avatar,
        };
        // Store in mention map for DOM parsing
        mentionMapRef.current.set(suggestion.id, mentionData);
        const newSegs = insertMentionIntoSegments(segments, mentionData, startIndex, replaceLength);
        const serialized = serializeSegments(newSegs);
        lastSerializedRef.current = serialized;
        // Calculate where caret should go: after trigger+label+space
        const caretPos = startIndex + trigger.length + suggestion.label.length + 1;
        caretRestoreRef.current = caretPos;
        setSegments(newSegs);
        setActiveMention(null);
        setHighlightedIndex(-1);
        onChange === null || onChange === void 0 ? void 0 : onChange(serialized);
        notifyMentionsChange(newSegs);
        onMentionSelect === null || onMentionSelect === void 0 ? void 0 : onMentionSelect(suggestion, trigger);
    }, [
        activeMention,
        segments,
        onChange,
        onMentionSelect,
        notifyMentionsChange,
    ]);
    const handleKeyDown = useCallback((e) => {
        var _a, _b, _c, _d, _e;
        // --- Selected mention: delete / replace / deselect ---
        if (selectedMentionIndex !== null &&
            ((_a = segments[selectedMentionIndex]) === null || _a === void 0 ? void 0 : _a.type) === "mention") {
            if (e.key === "Backspace" || e.key === "Delete") {
                e.preventDefault();
                const newSegs = normalizeSegments([
                    ...segments.slice(0, selectedMentionIndex),
                    ...segments.slice(selectedMentionIndex + 1),
                ]);
                caretRestoreRef.current = getOffsetAtSegment(segments, selectedMentionIndex);
                const serialized = serializeSegments(newSegs);
                lastSerializedRef.current = serialized;
                setSegments(newSegs);
                setSelectedMentionIndex(null);
                onChange === null || onChange === void 0 ? void 0 : onChange(serialized);
                notifyMentionsChange(newSegs);
                return;
            }
            // Printable character → remove mention and insert the character
            if (e.key.length === 1 && !e.ctrlKey && !e.metaKey) {
                e.preventDefault();
                const newSegs = normalizeSegments([
                    ...segments.slice(0, selectedMentionIndex),
                    { type: "text", text: e.key },
                    ...segments.slice(selectedMentionIndex + 1),
                ]);
                caretRestoreRef.current =
                    getOffsetAtSegment(segments, selectedMentionIndex) + 1;
                const serialized = serializeSegments(newSegs);
                lastSerializedRef.current = serialized;
                setSegments(newSegs);
                setSelectedMentionIndex(null);
                onChange === null || onChange === void 0 ? void 0 : onChange(serialized);
                notifyMentionsChange(newSegs);
                return;
            }
            // Arrow keys / Escape → just deselect
            if (e.key.startsWith("Arrow") || e.key === "Escape") {
                setSelectedMentionIndex(null);
                return;
            }
        }
        // --- Dropdown navigation ---
        if (isDropdownOpen) {
            switch (e.key) {
                case "ArrowDown":
                    e.preventDefault();
                    setHighlightedIndex((prev) => prev >= filteredSuggestions.length - 1 ? 0 : prev + 1);
                    return;
                case "ArrowUp":
                    e.preventDefault();
                    setHighlightedIndex((prev) => prev <= 0 ? filteredSuggestions.length - 1 : prev - 1);
                    return;
                case "Enter":
                    if (highlightedIndex >= 0 &&
                        highlightedIndex < filteredSuggestions.length) {
                        e.preventDefault();
                        insertMention(filteredSuggestions[highlightedIndex]);
                    }
                    return;
                case "Escape":
                    e.preventDefault();
                    setActiveMention(null);
                    return;
                case "Tab":
                    setActiveMention(null);
                    return;
            }
        }
        // --- Backspace into mention (atomic delete) ---
        if (e.key === "Backspace" && editableRef.current) {
            const sel = window.getSelection();
            if (!sel || sel.rangeCount === 0)
                return;
            const range = sel.getRangeAt(0);
            if (!range.collapsed)
                return; // Let browser handle selection delete
            const { startContainer, startOffset } = range;
            // Case 1: Caret in a text node at offset 0, previous sibling is a mention
            if (startContainer.nodeType === Node.TEXT_NODE && startOffset === 0) {
                const prevSibling = startContainer.previousSibling;
                if (prevSibling &&
                    prevSibling.nodeType === Node.ELEMENT_NODE &&
                    prevSibling.hasAttribute(MENTION_ATTR)) {
                    e.preventDefault();
                    (_b = prevSibling.parentNode) === null || _b === void 0 ? void 0 : _b.removeChild(prevSibling);
                    updateFromDOM();
                    return;
                }
            }
            // Case 2: Caret in parent element, child before offset is a mention
            if (startContainer.nodeType === Node.ELEMENT_NODE &&
                startOffset > 0) {
                const children = Array.from(startContainer.childNodes);
                const prevChild = children[startOffset - 1];
                if (prevChild &&
                    prevChild.nodeType === Node.ELEMENT_NODE &&
                    prevChild.hasAttribute(MENTION_ATTR)) {
                    e.preventDefault();
                    (_c = prevChild.parentNode) === null || _c === void 0 ? void 0 : _c.removeChild(prevChild);
                    updateFromDOM();
                    return;
                }
            }
        }
        // --- Delete into mention (atomic delete) ---
        if (e.key === "Delete" && editableRef.current) {
            const sel = window.getSelection();
            if (!sel || sel.rangeCount === 0)
                return;
            const range = sel.getRangeAt(0);
            if (!range.collapsed)
                return;
            const { startContainer, startOffset } = range;
            if (startContainer.nodeType === Node.TEXT_NODE) {
                const textLen = (startContainer.textContent || "").length;
                if (startOffset === textLen) {
                    const nextSibling = startContainer.nextSibling;
                    if (nextSibling &&
                        nextSibling.nodeType === Node.ELEMENT_NODE &&
                        nextSibling.hasAttribute(MENTION_ATTR)) {
                        e.preventDefault();
                        (_d = nextSibling.parentNode) === null || _d === void 0 ? void 0 : _d.removeChild(nextSibling);
                        updateFromDOM();
                        return;
                    }
                }
            }
            if (startContainer.nodeType === Node.ELEMENT_NODE) {
                const children = Array.from(startContainer.childNodes);
                const nextChild = children[startOffset];
                if (nextChild &&
                    nextChild.nodeType === Node.ELEMENT_NODE &&
                    nextChild.hasAttribute(MENTION_ATTR)) {
                    e.preventDefault();
                    (_e = nextChild.parentNode) === null || _e === void 0 ? void 0 : _e.removeChild(nextChild);
                    updateFromDOM();
                    return;
                }
            }
        }
        // Prevent Enter from creating <div> - insert <br> or \n instead
        if (e.key === "Enter" && !e.shiftKey && !isDropdownOpen) {
            e.preventDefault();
            document.execCommand("insertLineBreak");
        }
    }, [
        isDropdownOpen,
        highlightedIndex,
        filteredSuggestions,
        insertMention,
        updateFromDOM,
        selectedMentionIndex,
        segments,
        onChange,
        notifyMentionsChange,
    ]);
    const handlePaste = useCallback((e) => {
        e.preventDefault();
        const text = e.clipboardData.getData("text/plain");
        document.execCommand("insertText", false, text);
    }, []);
    const handleFocus = useCallback((e) => {
        var _a;
        setIsFocused(true);
        (_a = props.onFocus) === null || _a === void 0 ? void 0 : _a.call(props, e);
    }, [props.onFocus]);
    const handleBlur = useCallback((e) => {
        var _a;
        setSelectedMentionIndex(null);
        setIsFocused(false);
        (_a = props.onBlur) === null || _a === void 0 ? void 0 : _a.call(props, e);
    }, [props.onBlur]);
    const handleCompositionStart = useCallback(() => {
        composingRef.current = true;
    }, []);
    const handleCompositionEnd = useCallback(() => {
        composingRef.current = false;
        updateFromDOM();
    }, [updateFromDOM]);
    // Click on a mention tag → mark its segment index as selected
    const handleClick = useCallback((e) => {
        var _a;
        const target = e.target;
        const mentionEl = (_a = target.closest) === null || _a === void 0 ? void 0 : _a.call(target, `[${MENTION_ATTR}]`);
        if (!mentionEl || !editableRef.current) {
            setSelectedMentionIndex(null);
            return;
        }
        // Find which DOM mention this is (nth occurrence)
        const allMentions = editableRef.current.querySelectorAll(`[${MENTION_ATTR}]`);
        const domIdx = Array.from(allMentions).indexOf(mentionEl);
        if (domIdx === -1) {
            setSelectedMentionIndex(null);
            return;
        }
        // Map nth DOM mention → segment index
        let count = 0;
        for (let i = 0; i < segments.length; i++) {
            if (segments[i].type === "mention") {
                if (count === domIdx) {
                    setSelectedMentionIndex(i);
                    return;
                }
                count++;
            }
        }
        setSelectedMentionIndex(null);
    }, [segments]);
    // Scroll highlighted suggestion into view
    useEffect(() => {
        if (highlightedIndex >= 0 && dropdownRef.current) {
            const item = dropdownRef.current.querySelector(`[data-suggestion-index="${highlightedIndex}"]`);
            if (item) {
                item.scrollIntoView({ block: "nearest" });
            }
        }
    }, [highlightedIndex]);
    // --- Check if content is empty for placeholder ---
    const isContentEmpty = useMemo(() => {
        return segments.every((s) => s.type === "text" && s.text === "");
    }, [segments]);
    // -----------------------------------------------------------------------
    // Render segments as React children
    // -----------------------------------------------------------------------
    const renderedSegments = useMemo(() => {
        return segments.map((seg, i) => {
            if (seg.type === "text") {
                return (jsx("span", { "data-segment": "text", children: seg.text || (i === 0 ? "" : "") }, `text-${i}`));
            }
            return (jsx(Tag, { size: mentionTagSize, removable: false, avatar: seg.data.avatar
                    ? { src: seg.data.avatar, name: seg.data.label }
                    : undefined, contentEditable: false, className: cn(theme.mentionTagStyle, i === selectedMentionIndex &&
                    "ring-2 ring-[var(--color-primary)] ring-offset-1", mentionTagClassName), [MENTION_ATTR]: seg.data.id,
                "data-mention-label": seg.data.label,
                "data-mention-trigger": seg.data.trigger, children: seg.data.label }, `mention-${seg.data.id}-${i}`));
        });
    }, [
        segments,
        mentionTagSize,
        mentionTagClassName,
        theme.mentionTagStyle,
        selectedMentionIndex,
    ]);
    // -----------------------------------------------------------------------
    // Render suggestion item
    // -----------------------------------------------------------------------
    const renderSuggestionItem = (suggestion, index) => {
        const isHighlighted = index === highlightedIndex;
        const triggerChar = (activeMention === null || activeMention === void 0 ? void 0 : activeMention.trigger) || "@";
        if (renderSuggestion) {
            return (jsx("div", { role: "option", "aria-selected": isHighlighted, "data-suggestion-index": index, className: cn(theme.suggestionStyle, isHighlighted && theme.suggestionHighlightedStyle), onMouseEnter: () => setHighlightedIndex(index), onMouseDown: (e) => {
                    e.preventDefault();
                    insertMention(suggestion);
                }, children: renderSuggestion(suggestion, isHighlighted, triggerChar) }, suggestion.id));
        }
        return (jsxs("div", { role: "option", "aria-selected": isHighlighted, "data-suggestion-index": index, className: cn(theme.suggestionStyle, isHighlighted && theme.suggestionHighlightedStyle), onMouseEnter: () => setHighlightedIndex(index), onMouseDown: (e) => {
                e.preventDefault();
                insertMention(suggestion);
            }, children: [jsx(Avatar, { src: suggestion.avatar, name: suggestion.label, size: "xs", className: "ring-0 border-0" }), jsxs("div", { className: "flex flex-col min-w-0", children: [jsx("span", { className: theme.suggestionLabelStyle, children: suggestion.label }), suggestion.description && (jsx("span", { className: theme.suggestionDescriptionStyle, children: suggestion.description }))] })] }, suggestion.id));
    };
    // -----------------------------------------------------------------------
    // Dropdown portal content
    // -----------------------------------------------------------------------
    const dropdownContent = (jsx(AnimatePresence, { mode: "wait", children: isDropdownOpen && (jsx(motion.div, { ref: dropdownRef, role: "listbox", "aria-label": "Suggestions", className: cn(theme.dropdownStyle, dropdownClassName), style: {
                position: "fixed",
                top: `${dropdownPos.top}px`,
                left: `${dropdownPos.left}px`,
                minWidth: `${dropdownPos.width}px`,
                maxWidth: "360px",
                zIndex: 1000,
                overscrollBehavior: "contain",
            }, variants: dropdownVariants, initial: "initial", animate: "visible", exit: "exit", children: loading ? (jsx("div", { className: theme.loadingStyle, children: "Searching..." })) : filteredSuggestions.length === 0 ? (jsx("div", { className: theme.emptyMessageStyle, children: emptyMessage })) : (filteredSuggestions.map((suggestion, index) => renderSuggestionItem(suggestion, index))) })) }));
    // -----------------------------------------------------------------------
    // Render
    // -----------------------------------------------------------------------
    return (jsxs("div", { className: cn(theme.wrapperStyle, wrapperClassName), children: [jsx("div", { ref: wrapperRef, className: cn(theme.inputGroupStyle, isFocused && theme.inputGroupFocusStyle), children: jsx("div", { ref: setEditableRef, contentEditable: !disabled, suppressContentEditableWarning: true, onInput: handleInput, onKeyDown: handleKeyDown, onClick: handleClick, onFocus: handleFocus, onBlur: handleBlur, onPaste: handlePaste, onSelect: handleSelect, onCompositionStart: handleCompositionStart, onCompositionEnd: handleCompositionEnd, role: "textbox", "aria-multiline": "true", "aria-autocomplete": "list", "aria-expanded": isDropdownOpen, "aria-haspopup": "listbox", "aria-placeholder": placeholder, "data-placeholder": placeholder, "aria-disabled": disabled || undefined, className: cn(theme.editableStyle, theme.sizes[size], isContentEmpty &&
                        "before:content-[attr(data-placeholder)] before:text-[var(--color-text-placeholder)] before:pointer-events-none before:absolute dark:before:text-[var(--color-neutral-500)]", disabled && "cursor-not-allowed opacity-60", className), style: {
                        minHeight: rows ? `${rows * 1.5}em` : undefined,
                        position: "relative",
                    }, ...props, children: renderedSegments }) }), isClient && createPortal(dropdownContent, document.body)] }));
});
Mention.displayName = "Mention";

export { Mention };
