import {createPortal, useEffect, useRef, useState} from "@wordpress/element";
import {__} from "@wordpress/i18n";
import useClickOutside from "../../../../components/hooks/use-click-outside";
import EmojiPicker from "emoji-picker-react";
import {CATEGORIES, EMOJI_PICKER} from "./_data";

export default function Emoji({chosen, inputRef, disabled}) {
    // States
    const [opened, setOpened] = useState(false);
    // Elements refs
    const openerRef = useRef(null);
    const metaBoxRef = useRef(document.getElementById('chatbot-meta-box'));
    const fieldMenuRef = useRef(document.getElementById('lbaic-settings-field-menu'));
    const pickerInRef = useRef(null);
    const pickerInCloseTimeout = useRef(null);
    const [position, setPosition] = useState({
        top: 0,
        right: 0,
        bottom: 'unset',
    });

    useClickOutside([pickerInRef, openerRef], () => setOpened(false));

    useEffect(() => {
        // Get the current position
        setupPickerPosition();
        // Events
        window.addEventListener('resize', setupPickerPosition);
        window.addEventListener('scroll', setupPickerPosition, true);

        return () => {
            window.removeEventListener('resize', setupPickerPosition);
            window.removeEventListener('scroll', setupPickerPosition, true);
        }
    }, []);

    useEffect(() => {
        if (opened) {
            setupPickerPosition();
        }
    }, [opened]);

    /**
     * Setup picker position
     */
    const setupPickerPosition = () => {
        if (openerRef.current) {
            const rect = openerRef.current.getBoundingClientRect();
            const metaBoxRect = metaBoxRef.current ? metaBoxRef.current.getBoundingClientRect() : null;
            const fieldMenuRect = fieldMenuRef.current ? fieldMenuRef.current.getBoundingClientRect() : null;
            const topMenuHeight = document.getElementById('wpadminbar')?.offsetHeight || 0;
            // Position
            let top = rect.top - (metaBoxRect ? -2 : (topMenuHeight ? topMenuHeight - 36 : 0)) - (metaBoxRect?.top || 0);
            let right = metaBoxRect ? (fieldMenuRect?.right || 0) - rect.right : window.innerWidth - rect.right;
            let bottom = 'unset';
            if (top + EMOJI_PICKER.height + rect.height > window.innerHeight) {
                top = 'unset';
                bottom = 0;
            }

            setPosition({
                top: typeof top === 'number' ? top + 'px' : top,
                right: typeof right === 'number' ? right + 'px' : right,
                bottom: typeof bottom === 'number' ? bottom + 'px' : bottom,
            });
        }
    }

    /**
     * Keep the picker opened if intend to close it within 400 ms
     */
    const pickerInMouseEnter = () => {
        if (pickerInCloseTimeout.current) {
            clearTimeout(pickerInCloseTimeout.current);
            pickerInCloseTimeout.current = null;
        }
    }

    /**
     * Close picker on mouse leave after 400 ms
     */
    const pickerInMouseLeave = () => {
        pickerInCloseTimeout.current = setTimeout(() => {
            setOpened(false);
        }, 400);
    }

    /**
     * On emoji click
     *
     * @param {object} emojiData Chosen emoji
     * @param {Event} e Event
     */
    const onEmojiClick = (emojiData, e) => {
        chosen(emojiData);
        // Focus the input
        if (inputRef?.current) {
            inputRef.current.focus();
        }
    }

    return <>
        <div ref={openerRef} className={`lbaic-settings-emoji${opened ? ' active' : ''}`}>
            <button type='button'
                    className={`lbaic-settings-button-reset lbaic-settings-emoji-toggle${disabled ? ' lbaic-settings-button-disabled' : ''}`}
                    onClick={() => !disabled && setOpened(!opened)} tabIndex='-1'>
                <svg className='lbaic-settings-emoji-toggle-i' xmlns='http://www.w3.org/2000/svg' fill='none'
                     viewBox='0 0 24 24'>
                    <use href='#lbaic-settings-emoji'/>
                </svg>
            </button>
        </div>
        {opened && !disabled && createPortal(
            <div ref={pickerInRef} className='lbaic-settings-emoji-in'
                 onMouseEnter={pickerInMouseEnter}
                 onMouseLeave={pickerInMouseLeave}
                 style={{
                     '--lbaic-settings-emoji-in-top': position.top,
                     '--lbaic-settings-emoji-in-right': position.right,
                     '--lbaic-settings-emoji-in-bottom': position.bottom,
                 }}>
                <EmojiPicker open={opened} onEmojiClick={onEmojiClick}
                             searchPlaceholder={__("Search", 'limb-chatbot')}
                             categories={CATEGORIES}
                             width={EMOJI_PICKER.width}
                             height={EMOJI_PICKER.height}
                             emojiStyle='native'
                             previewConfig={{
                                 showPreview: false
                             }}/>
            </div>
            , document.getElementById('lbaic-settings-field-menu'))}
    </>
}