import React, { useState, useRef, useEffect, useLayoutEffect } from 'react';
import { createPortal } from 'react-dom';
import { MODEL_TYPES } from './engine/ModelTypes';
import { AMBIENT_PRESETS, MUSIC_PRESETS } from './engine/AudioManager';
import Icon from './Icon';
import cl from './TopRibbon.module.css';

const CHARACTER_OPTIONS = MODEL_TYPES.filter(m => m.category === 'Персонажи');

// Глобальный реестр функций-закрывателей для всех Dropdown'ов.
// При открытии нового закрываем все предыдущие.
const _dropdownClosers = new Set();

/**
 * Выпадающий список через React portal — рендерится в body, поэтому
 * не обрезается overflow родительских контейнеров TopRibbon.
 */
const Dropdown = ({ trigger, children }) => {
    const [open, setOpen] = useState(false);
    const [pos, setPos] = useState({ top: 0, left: 0 });
    const triggerRef = useRef(null);
    const menuRef = useRef(null);

    // Регистрируем closer для глобальной координации
    useEffect(() => {
        const closer = () => setOpen(false);
        _dropdownClosers.add(closer);
        return () => { _dropdownClosers.delete(closer); };
    }, []);

    // Считаем позицию dropdown относительно viewport при открытии
    useLayoutEffect(() => {
        if (!open || !triggerRef.current) return;
        const rect = triggerRef.current.getBoundingClientRect();
        setPos({
            top: rect.bottom + 4,
            left: rect.left,
        });
    }, [open]);

    useEffect(() => {
        if (!open) return;
        const onDoc = (e) => {
            if (triggerRef.current && triggerRef.current.contains(e.target)) return;
            if (menuRef.current && menuRef.current.contains(e.target)) return;
            setOpen(false);
        };
        // setTimeout чтобы listener привязался ПОСЛЕ текущего click event
        // (иначе клик который открыл dropdown сразу же его закроет)
        const t = setTimeout(() => document.addEventListener('click', onDoc), 0);
        return () => {
            clearTimeout(t);
            document.removeEventListener('click', onDoc);
        };
    }, [open]);

    const handleTriggerClick = (e) => {
        e.stopPropagation();
        if (open) {
            setOpen(false);
        } else {
            // Закрываем все остальные открытые dropdown'ы
            _dropdownClosers.forEach(close => close());
            setOpen(true);
        }
    };

    return (
        <>
            <span
                className={cl.dropdownWrap}
                ref={triggerRef}
                onClick={handleTriggerClick}
                style={{ display: 'inline-flex', cursor: 'pointer' }}
            >
                {trigger}
            </span>
            {open && createPortal(
                <div
                    ref={menuRef}
                    className={cl.dropdownMenu}
                    style={{
                        position: 'fixed',
                        top: pos.top,
                        left: pos.left,
                        zIndex: 99999,
                        background: '#252525',
                        backdropFilter: 'blur(20px)',
                        WebkitBackdropFilter: 'blur(20px)',
                        border: '1px solid #3a3a3a',
                        borderRadius: 12,
                        padding: 6,
                        minWidth: 220,
                        maxHeight: 320,
                        overflowY: 'auto',
                        boxShadow: '0 16px 40px rgba(0, 0, 0, 0.55), 0 0 0 1px rgba(79, 116, 255, 0.12)',
                        color: '#e8e8ea',
                        fontFamily: '"Roboto Condensed", system-ui, -apple-system, sans-serif',
                    }}
                >
                    {typeof children === 'function' ? children(() => setOpen(false)) : children}
                </div>,
                document.body
            )}
        </>
    );
};

/**
 * Roblox Studio-style верхняя панель инструментов.
 *
 * Архитектура: Tabs (вкладки сверху) + Ribbon (лента кнопок-групп).
 * Каждая кнопка = крупная иконка-эмодзи + подпись снизу.
 *
 * Props:
 *   activeTab          — 'home' | 'model' | 'test' | 'view'
 *   onTabChange(tab)
 *
 *   gizmoMode          — 'select' | 'move' | 'rotate' | 'scale'
 *   onGizmoModeChange(mode)
 *
 *   snap               — 1.0 | 0.5 | 0.25 | 0
 *   onSnapChange(step)
 *
 *   activeTool         — 'select' | 'block' | 'model' | 'erase'  (создание)
 *   onToolChange(tool)
 *
 *   isPlaying          — режим Play
 *   onPlayToggle()
 *   onSetSpawn()
 *
 *   hasSelection       — есть ли выделенный объект (для активации Model-инструментов)
 *   onDuplicate()
 *   onAlignToFloor()
 *   onDelete()
 *
 *   onClearScene()
 *
 *   onViewPreset(preset) — 'top' | 'front' | 'side' | 'iso'
 */

const TABS = [
    { id: 'home',  label: 'Главная',  iconName: 'home'     },
    { id: 'model', label: 'Модель',   iconName: 'wrench'   },
    { id: 'test',  label: 'Игра',     iconName: 'gamepad'  },
    { id: 'view',  label: 'Вид',      iconName: 'eye'      },
];

const SNAP_OPTIONS = [
    { value: 1.0,  label: '1.0' },
    { value: 0.5,  label: '0.5' },
    { value: 0.25, label: '0.25' },
    { value: 0,    label: 'Off' },
];

/** Группа кнопок в ribbon с подписью. */
const Group = ({ title, children }) => (
    <div className={cl.group}>
        <div className={cl.groupBody}>{children}</div>
        {title && <div className={cl.groupTitle}>{title}</div>}
    </div>
);

/** Большая кнопка ribbon. Принимает либо iconName (имя для Icon из Icon.jsx)
 *  либо icon (готовый JSX, для legacy/особых случаев). */
const RibbonBtn = ({ iconName, icon, label, active, disabled, danger, onClick, title }) => (
    <button
        className={`${cl.ribbonBtn} ${active ? cl.btnActive : ''} ${danger ? cl.btnDanger : ''}`}
        onClick={onClick}
        disabled={disabled}
        title={title || label}
    >
        <span className={cl.btnIcon}>
            {iconName ? <Icon name={iconName} size={20} /> : icon}
        </span>
        <span className={cl.btnLabel}>{label}</span>
    </button>
);

/** Большая кнопка с акцентным фоном — для Play/Stop в правом углу ленты.
 *  Принимает iconName (имя для Icon) или icon (готовый JSX). */
const BigBtn = ({ iconName, icon, label, gradient, onClick, title, disabled, glow }) => (
    <button
        onClick={onClick}
        disabled={disabled}
        title={title || label}
        style={{
            display: 'flex',
            flexDirection: 'column',
            alignItems: 'center',
            justifyContent: 'center',
            minWidth: 84,
            height: 70,
            padding: '6px 12px',
            border: '1px solid transparent',
            borderRadius: 12,
            background: disabled
                ? 'rgba(148, 163, 184, 0.12)'
                : (gradient || 'linear-gradient(135deg, #3357ff 0%, #1e2da5 100%)'),
            color: disabled ? '#94a3b8' : '#fff',
            cursor: disabled ? 'not-allowed' : 'pointer',
            opacity: disabled ? 0.85 : 1,
            fontWeight: 800,
            transition: 'all 200ms cubic-bezier(0.34, 1.56, 0.64, 1)',
            boxShadow: disabled ? 'none' : (glow || '0 8px 20px rgba(51, 87, 255, 0.40)'),
            fontFamily: '"Roboto Condensed", system-ui, sans-serif',
            letterSpacing: 0.2,
        }}
        onMouseEnter={(e) => {
            if (disabled) return;
            e.currentTarget.style.transform = 'translateY(-2px)';
            e.currentTarget.style.filter = 'brightness(1.08)';
        }}
        onMouseLeave={(e) => {
            e.currentTarget.style.transform = 'translateY(0)';
            e.currentTarget.style.filter = 'brightness(1)';
        }}
    >
        <span style={{ fontSize: 22, lineHeight: 1, marginBottom: 4, display: 'flex', alignItems: 'center' }}>
            {iconName ? <Icon name={iconName} size={26} strokeWidth={2.2} /> : icon}
        </span>
        <span style={{ fontSize: 12, letterSpacing: 0.3, fontWeight: 800 }}>{label}</span>
    </button>
);


const TopRibbon = (props) => {
    const {
        activeTab, onTabChange,
        gizmoMode, onGizmoModeChange,
        snap, onSnapChange,
        activeTool, onToolChange,
        isPlaying, onPlayToggle, onSetSpawn,
        hasSelection,
        onDuplicate, onAlignToFloor, onDelete,
        onClearScene,
        onViewPreset,
        // === Этап 3: Создание моделей ===
        onCreateVoxelModel,
        onCreateSmoothModel,
        // Открыть Toolbox на нужной вкладке: стандартные / мои / сообщество.
        onOpenStandardModels,
        onOpenMyModels,
        onOpenCommunityModels,
    } = props;

    return (
        <div className={cl.ribbon}>
            {/* === Вкладки === */}
            <div className={cl.tabs}>
                {TABS.map(t => (
                    <button
                        key={t.id}
                        className={`${cl.tab} ${activeTab === t.id ? cl.tabActive : ''}`}
                        onClick={() => onTabChange(t.id)}
                    >
                        <span className={cl.tabIcon}><Icon name={t.iconName} size={14} /></span> {t.label}
                    </button>
                ))}
            </div>

            {/* === Лента содержимого вкладки === */}
            <div className={cl.body}>
                {activeTab === 'home' && (
                    <>
                        <Group title="Манипуляторы">
                            {/* Подсвечиваем только если activeTool='select' (инструмент создания не активен) */}
                            <RibbonBtn
                                iconName="cursor" label="Выделить"
                                active={activeTool === 'select' && gizmoMode === 'select'}
                                onClick={() => onGizmoModeChange('select')}
                                title="Выбрать без манипулятора"
                            />
                            <RibbonBtn
                                iconName="move" label="Двигать"
                                active={activeTool === 'select' && gizmoMode === 'move'}
                                onClick={() => onGizmoModeChange('move')}
                                title="Стрелки X/Y/Z для перемещения"
                            />
                            <RibbonBtn
                                iconName="rotate" label="Вращать"
                                active={activeTool === 'select' && gizmoMode === 'rotate'}
                                onClick={() => onGizmoModeChange('rotate')}
                                title="Кольца X/Y/Z для поворота"
                            />
                            <RibbonBtn
                                iconName="ruler" label="Масштаб"
                                active={activeTool === 'select' && gizmoMode === 'scale'}
                                onClick={() => onGizmoModeChange('scale')}
                                title="Кубики X/Y/Z для масштабирования"
                            />
                        </Group>

                        <Group title="Шаг привязки">
                            <div
                                className={cl.snapBox}
                                title="Шаг при перетаскивании гизмо «Двигать». 1.0 — координаты округляются до целых (как блоки), 0.5 — до полушагов, Off — плавно без привязки."
                            >
                                <div className={cl.snapLabel}>Шаг</div>
                                <div className={cl.snapButtons}>
                                    {SNAP_OPTIONS.map(o => (
                                        <button
                                            key={o.value}
                                            className={`${cl.snapBtn} ${snap === o.value ? cl.snapBtnActive : ''}`}
                                            onClick={() => onSnapChange(o.value)}
                                            title={
                                                o.value === 0
                                                    ? 'Без привязки — плавное перемещение'
                                                    : `Шаг ${o.label} (округление координат)`
                                            }
                                        >
                                            {o.label}
                                        </button>
                                    ))}
                                </div>
                            </div>
                        </Group>

                        <Group title="Создать">
                            <RibbonBtn
                                iconName="boxes" label="Блок"
                                active={activeTool === 'block'}
                                onClick={() => onToolChange('block')}
                            />
                            <RibbonBtn
                                iconName="cube" label="Примитив"
                                active={activeTool === 'primitive'}
                                onClick={() => onToolChange('primitive')}
                                title="Параметрическая фигура (куб/сфера/...)"
                            />
                            <RibbonBtn
                                iconName="trees" label="Модель"
                                active={activeTool === 'model'}
                                onClick={() => onToolChange('model')}
                            />
                            <RibbonBtn
                                iconName="image" label="Интерфейс"
                                active={activeTool === 'gui'}
                                onClick={() => onToolChange('gui')}
                                title="2D-интерфейс игры — перетащи элемент на экран"
                            />
                            <RibbonBtn
                                iconName="mountain" label="Ландшафт"
                                active={activeTool === 'terrain'}
                                onClick={() => onToolChange('terrain')}
                                title="Создание и редактирование ландшафта (как Terrain в Roblox Studio)"
                            />
                            <RibbonBtn
                                iconName="dice" label="Генератор"
                                active={activeTool === 'gen'}
                                onClick={() => onToolChange('gen')}
                                title="Процедурная генерация ландшафта по параметрам noise"
                            />
                            <RibbonBtn
                                iconName="trash" label="Очистить"
                                danger
                                onClick={onClearScene}
                                title="Удалить ВСЁ из сцены"
                            />
                        </Group>
                    </>
                )}

                {activeTab === 'model' && (
                    <>
                        {/* Редактор моделей: создание своих моделей.
                            Воксельная — кубики 0.25м как Minecraft/MagicaVoxel.
                            (Гладкий редактор пока не реализован — кнопка убрана.) */}
                        <Group title="Создать модель">
                            <RibbonBtn
                                iconName="cube" label="Воксельная"
                                onClick={onCreateVoxelModel}
                                title="Создать модель из кубиков 0.25м (как Minecraft)"
                            />
                        </Group>
                        <Group title="Библиотека">
                            <RibbonBtn
                                iconName="package" label="Стандартные"
                                onClick={onOpenStandardModels}
                                title="Открыть Тулбокс — каталог стандартных моделей"
                            />
                            <RibbonBtn
                                iconName="user" label="Мои модели"
                                onClick={onOpenMyModels}
                                title="Открыть Тулбокс на вкладке «Мои модели»"
                            />
                            <RibbonBtn
                                iconName="globe" label="Сообщество"
                                onClick={onOpenCommunityModels}
                                title="Открыть Тулбокс на вкладке «Сообщество»"
                            />
                        </Group>
                        <Group title="Действия">
                            <RibbonBtn
                                iconName="duplicate" label="Дублировать"
                                disabled={!hasSelection}
                                onClick={onDuplicate}
                                title="Создать копию рядом (Ctrl+D)"
                            />
                            <RibbonBtn
                                iconName="arrow-down" label="На пол"
                                disabled={!hasSelection}
                                onClick={onAlignToFloor}
                                title="Опустить выделенный объект на y=0"
                            />
                            <RibbonBtn
                                iconName="delete" label="Удалить"
                                disabled={!hasSelection}
                                danger
                                onClick={onDelete}
                                title="Удалить выделенное (Del)"
                            />
                        </Group>
                    </>
                )}

                {activeTab === 'test' && (
                    <>
                        <Group title="Игра">
                            <RibbonBtn
                                iconName={isPlaying ? 'stop' : 'play'}
                                label={isPlaying ? 'Стоп' : 'Играть'}
                                active={isPlaying}
                                onClick={onPlayToggle}
                                title={isPlaying ? 'Выйти из игры (Esc)' : 'Запустить тест'}
                            />
                            <RibbonBtn
                                iconName="flag" label="Ставить спавн"
                                onClick={onSetSpawn}
                                title="Поставить точку спавна там где смотрит камера"
                            />
                        </Group>

                        {/* «Окружение» (время суток / амбиент / музыка) и
                            «Скин игрока» переехали в иерархию объектов сцены:
                            🌞 Освещение / 🎵 Звук / 👤 Игрок. */}
                    </>
                )}

                {activeTab === 'view' && (
                    <>
                        <Group title="Перспективы">
                            <RibbonBtn
                                iconName="arrow-up" label="Сверху"
                                onClick={() => onViewPreset('top')}
                            />
                            <RibbonBtn
                                iconName="arrow-right" label="Спереди"
                                onClick={() => onViewPreset('front')}
                            />
                            <RibbonBtn
                                iconName="arrow-left" label="Сбоку"
                                onClick={() => onViewPreset('side')}
                            />
                            <RibbonBtn
                                iconName="cube" label="Изо"
                                onClick={() => onViewPreset('iso')}
                            />
                        </Group>

                        <Group title="Размер пола">
                            <div className={cl.snapBox} title="Сторона прямоугольного пола в юнитах">
                                <div className={cl.snapLabel}>Размер</div>
                                <div className={cl.snapButtons}>
                                    {[50, 100, 200, 500].map(sz => (
                                        <button
                                            key={sz}
                                            className={`${cl.snapBtn} ${(props.worldSize || 80) === sz ? cl.snapBtnActive : ''}`}
                                            onClick={() => props.onWorldSizeChange?.(sz)}
                                            title={`Пол ${sz}×${sz}`}
                                        >
                                            {sz}
                                        </button>
                                    ))}
                                </div>
                            </div>
                        </Group>

                        <Group title="Тени">
                            <div className={cl.snapBox} title="Качество теней">
                                <div className={cl.snapLabel}>Тени</div>
                                <div className={cl.snapButtons}>
                                    {[
                                        { id: 'off',  label: 'Выкл' },
                                        { id: 'hard', label: 'Жёсткие' },
                                        { id: 'soft', label: 'Мягкие' },
                                    ].map(o => (
                                        <button
                                            key={o.id}
                                            className={`${cl.snapBtn} ${(props.shadowQuality || 'soft') === o.id ? cl.snapBtnActive : ''}`}
                                            onClick={() => props.onShadowQualityChange?.(o.id)}
                                        >
                                            {o.label}
                                        </button>
                                    ))}
                                </div>
                            </div>
                        </Group>
                    </>
                )}

                {/* === Запустить / Стоп — всегда видны, не зависят от вкладок ===
                    Большие кнопки с иконкой сверху и подписью снизу (как в Roblox Studio). */}
                <div style={{ marginLeft: 'auto', display: 'flex', alignItems: 'center', gap: 8, padding: '0 14px' }}>
                    <BigBtn
                        iconName="play"
                        label="Запустить"
                        gradient="linear-gradient(135deg, #22d97a 0%, #0f9d56 100%)"
                        glow="0 8px 20px rgba(34, 217, 122, 0.45)"
                        onClick={() => { if (!isPlaying) onPlayToggle?.(); }}
                        disabled={isPlaying}
                        title="Запустить игру (тестировать)"
                    />
                    <BigBtn
                        iconName="stop"
                        label="Стоп"
                        gradient="linear-gradient(135deg, #ff6f7a 0%, #c0303f 100%)"
                        glow="0 8px 20px rgba(239, 68, 68, 0.45)"
                        onClick={() => { if (isPlaying) onPlayToggle?.(); }}
                        disabled={!isPlaying}
                        title="Остановить игру"
                    />
                </div>
            </div>
        </div>
    );
};

export default TopRibbon;
