import React, { useEffect, useRef, useState } from 'react';
import { useNavigate } from 'react-router-dom';
import Layout from '../../components/Layout';
import { api } from '../../lib/api';
import { toast } from 'sonner';
import { ArrowLeft, Clock, Tag, MapPin, Plus, Trash2, Save, Settings as SettingsIcon } from 'lucide-react';

export default function PalettesReliquatSettings() {
    const navigate = useNavigate();

    // Section Archivage
    const [archiveHour, setArchiveHour] = useState(6);
    const [archiveMinute, setArchiveMinute] = useState(1);
    const [savingTime, setSavingTime] = useState(false);
    const [origTime, setOrigTime] = useState({ h: 6, m: 1 });

    // Section Motifs
    const [motifs, setMotifs] = useState([]);
    const [motifColors, setMotifColors] = useState({}); // {label_norm: '#xxxxxx'}
    const [newMotif, setNewMotif] = useState('');
    const [addingMotif, setAddingMotif] = useState(false);

    // Section Zones
    const [zones, setZones] = useState([]);
    const [newZone, setNewZone] = useState('');
    const [addingZone, setAddingZone] = useState(false);

    const [loading, setLoading] = useState(true);

    // Helpers couleur
    const labelNorm = (label) => {
        return (label || '')
            .trim()
            .toLowerCase()
            .normalize('NFD')
            .replace(/[\u0300-\u036f]/g, '')
            .replace(/[^a-z0-9]+/g, ' ')
            .trim();
    };
    const colorOf = (motif) => motifColors[labelNorm(motif.label)] || '#E0E0E0';

    const loadAll = async () => {
        setLoading(true);
        try {
            const [s, m, z, mc] = await Promise.all([
                api.get('/gp/reliquat-settings'),
                api.get('/gp/motifs'),
                api.get('/gp/zones'),
                api.get('/gp/motif-colors'),
            ]);
            setArchiveHour(s.data.archive_hour);
            setArchiveMinute(s.data.archive_minute);
            setOrigTime({ h: s.data.archive_hour, m: s.data.archive_minute });
            setMotifs(m.data || []);
            setZones(z.data || []);
            const cmap = {};
            (mc.data || []).forEach((c) => {
                cmap[labelNorm(c.label)] = c.color_hex;
            });
            setMotifColors(cmap);
        } catch (err) {
            toast.error(err?.response?.data?.detail || 'Erreur de chargement');
        } finally {
            setLoading(false);
        }
    };

    useEffect(() => { loadAll(); }, []);

    const saveTime = async () => {
        if (archiveHour < 0 || archiveHour > 23 || archiveMinute < 0 || archiveMinute > 59) {
            toast.error('Heure invalide');
            return;
        }
        setSavingTime(true);
        try {
            await api.put('/gp/reliquat-settings', { archive_hour: archiveHour, archive_minute: archiveMinute });
            setOrigTime({ h: archiveHour, m: archiveMinute });
            toast.success(`Archivage programmé à ${String(archiveHour).padStart(2,'0')}:${String(archiveMinute).padStart(2,'0')}`);
        } catch (err) {
            toast.error(err?.response?.data?.detail || 'Erreur');
        } finally {
            setSavingTime(false);
        }
    };

    const addMotif = async (e) => {
        e?.preventDefault();
        const label = newMotif.trim();
        if (!label) return;
        setAddingMotif(true);
        try {
            const r = await api.post('/gp/motifs', { label });
            setMotifs((arr) => [...arr, { id: r.data.id, label: r.data.label }].sort((a, b) => a.label.localeCompare(b.label, 'fr')));
            setNewMotif('');
            toast.success('Motif ajouté');
        } catch (err) {
            toast.error(err?.response?.data?.detail || 'Erreur');
        } finally {
            setAddingMotif(false);
        }
    };

    const deleteMotif = async (m) => {
        if (!window.confirm(`Supprimer le motif "${m.label}" ?`)) return;
        try {
            await api.delete(`/gp/motifs/${m.id}`);
            setMotifs((arr) => arr.filter((x) => x.id !== m.id));
            toast.success('Motif supprimé');
        } catch (err) {
            toast.error(err?.response?.data?.detail || 'Erreur');
        }
    };

    // Debounce per motif label to avoid hammering the API
    const colorTimersRef = useRef({});
    const setMotifColorLocal = (label, hex) => {
        const norm = labelNorm(label);
        setMotifColors((m) => ({ ...m, [norm]: hex }));
        if (colorTimersRef.current[norm]) clearTimeout(colorTimersRef.current[norm]);
        colorTimersRef.current[norm] = setTimeout(async () => {
            try {
                await api.put('/gp/motif-colors', { label, color_hex: hex });
            } catch (err) {
                toast.error(err?.response?.data?.detail || 'Erreur enregistrement couleur');
            }
        }, 350);
    };

    const addZone = async (e) => {
        e?.preventDefault();
        const label = newZone.trim().toUpperCase();
        if (!label) return;
        setAddingZone(true);
        try {
            const r = await api.post('/gp/zones', { label });
            const sortFn = (a, b) => {
                const la = (a.label || '').slice(0, 1);
                const lb = (b.label || '').slice(0, 1);
                if (la !== lb) return la.localeCompare(lb);
                return parseInt((a.label || '').slice(1) || '0', 10) - parseInt((b.label || '').slice(1) || '0', 10);
            };
            setZones((arr) => [...arr, { id: r.data.id, label: r.data.label }].sort(sortFn));
            setNewZone('');
            toast.success('Zone ajoutée');
        } catch (err) {
            toast.error(err?.response?.data?.detail || 'Erreur');
        } finally {
            setAddingZone(false);
        }
    };

    const deleteZone = async (z) => {
        if (!window.confirm(`Supprimer la zone "${z.label}" ?`)) return;
        try {
            await api.delete(`/gp/zones/${z.id}`);
            setZones((arr) => arr.filter((x) => x.id !== z.id));
            toast.success('Zone supprimée');
        } catch (err) {
            toast.error(err?.response?.data?.detail || 'Erreur');
        }
    };

    const timeDirty = archiveHour !== origTime.h || archiveMinute !== origTime.m;

    return (
        <Layout>
            <button
                data-testid="back-btn"
                onClick={() => navigate('/palettes/reliquat')}
                className="mb-5 inline-flex items-center gap-2 text-sm font-semibold text-slate-600 hover:text-amber-600 transition"
            >
                <ArrowLeft className="h-4 w-4" />
                Retour aux Palettes Reliquat
            </button>

            <div className="mb-6 flex items-center gap-3">
                <div className="flex h-11 w-11 items-center justify-center rounded-md bg-amber-100 text-amber-600">
                    <SettingsIcon className="h-5 w-5" />
                </div>
                <div>
                    <p className="text-xs font-bold uppercase tracking-[0.2em] text-amber-600">Gestion Palettes</p>
                    <h1 className="font-heading text-2xl sm:text-3xl font-black tracking-tight text-slate-900">Paramètres Reliquat</h1>
                </div>
            </div>

            {loading ? (
                <div className="rounded-lg border border-slate-200 bg-white p-12 text-center text-slate-500">Chargement…</div>
            ) : (
                <div className="grid grid-cols-1 lg:grid-cols-2 gap-5">
                    {/* === Archivage automatique === */}
                    <div className="lg:col-span-2 rounded-lg border border-slate-200 bg-white p-5 sm:p-6" data-testid="archive-time-card">
                        <div className="flex items-start gap-3 mb-4">
                            <div className="flex h-10 w-10 shrink-0 items-center justify-center rounded-md bg-amber-100 text-amber-600">
                                <Clock className="h-5 w-5" />
                            </div>
                            <div className="flex-1">
                                <h2 className="font-heading text-lg font-bold text-slate-900">Archivage automatique</h2>
                                <p className="text-sm text-slate-500 mt-0.5">
                                    Heure à laquelle toutes les palettes actives sont archivées chaque jour.
                                </p>
                            </div>
                        </div>

                        <div className="flex items-end gap-3 flex-wrap">
                            <div>
                                <label className="text-[11px] font-bold uppercase tracking-[0.2em] text-slate-600">Heure</label>
                                <input
                                    data-testid="archive-hour-input"
                                    type="number"
                                    min={0}
                                    max={23}
                                    value={archiveHour}
                                    onChange={(e) => setArchiveHour(Math.max(0, Math.min(23, parseInt(e.target.value || '0', 10))))}
                                    className="mt-1.5 w-24 h-11 rounded-md border border-slate-300 bg-white px-3 text-center text-lg font-bold text-slate-900 focus:border-amber-500 focus:outline-none focus:ring-2 focus:ring-amber-500/20"
                                />
                            </div>
                            <span className="text-2xl font-black text-slate-400 self-center pb-1">:</span>
                            <div>
                                <label className="text-[11px] font-bold uppercase tracking-[0.2em] text-slate-600">Minute</label>
                                <input
                                    data-testid="archive-minute-input"
                                    type="number"
                                    min={0}
                                    max={59}
                                    value={archiveMinute}
                                    onChange={(e) => setArchiveMinute(Math.max(0, Math.min(59, parseInt(e.target.value || '0', 10))))}
                                    className="mt-1.5 w-24 h-11 rounded-md border border-slate-300 bg-white px-3 text-center text-lg font-bold text-slate-900 focus:border-amber-500 focus:outline-none focus:ring-2 focus:ring-amber-500/20"
                                />
                            </div>
                            <button
                                data-testid="archive-time-save"
                                onClick={saveTime}
                                disabled={!timeDirty || savingTime}
                                className="inline-flex items-center gap-2 rounded-md bg-amber-500 text-white px-5 h-11 text-sm font-heading font-bold hover:bg-amber-600 active:scale-[0.99] transition-all disabled:opacity-50 disabled:cursor-not-allowed"
                            >
                                <Save className="h-4 w-4" /> {savingTime ? 'Enregistrement…' : 'Enregistrer'}
                            </button>
                            {!timeDirty && (
                                <span className="text-xs text-emerald-600 font-semibold self-center pb-3">
                                    Actuellement programmé à {String(origTime.h).padStart(2, '0')}:{String(origTime.m).padStart(2, '0')}
                                </span>
                            )}
                        </div>
                    </div>

                    {/* === Motifs === */}
                    <div className="rounded-lg border border-slate-200 bg-white p-5 sm:p-6" data-testid="motifs-card">
                        <div className="flex items-start gap-3 mb-4">
                            <div className="flex h-10 w-10 shrink-0 items-center justify-center rounded-md bg-amber-100 text-amber-600">
                                <Tag className="h-5 w-5" />
                            </div>
                            <div className="flex-1">
                                <h2 className="font-heading text-lg font-bold text-slate-900">Motifs</h2>
                                <p className="text-sm text-slate-500 mt-0.5">{motifs.length} motif{motifs.length > 1 ? 's' : ''} disponible{motifs.length > 1 ? 's' : ''}.</p>
                            </div>
                        </div>

                        <form onSubmit={addMotif} className="flex gap-2 mb-4">
                            <input
                                data-testid="new-motif-input"
                                value={newMotif}
                                onChange={(e) => setNewMotif(e.target.value)}
                                placeholder="Ajouter un motif…"
                                className="flex-1 h-11 rounded-md border border-slate-300 bg-white px-3 text-sm font-medium text-slate-900 focus:border-amber-500 focus:outline-none focus:ring-2 focus:ring-amber-500/20"
                            />
                            <button
                                type="submit"
                                data-testid="add-motif-btn"
                                disabled={!newMotif.trim() || addingMotif}
                                className="inline-flex items-center gap-1.5 rounded-md bg-amber-500 text-white px-4 h-11 text-sm font-heading font-bold hover:bg-amber-600 active:scale-[0.99] transition-all disabled:opacity-50"
                            >
                                <Plus className="h-4 w-4" /> Ajouter
                            </button>
                        </form>

                        <div className="max-h-96 overflow-auto -mx-1 px-1 divide-y divide-slate-100 rounded border border-slate-200">
                            {motifs.length === 0 ? (
                                <p className="text-sm text-slate-400 italic p-4 text-center">Aucun motif. Ajoute le premier ci-dessus.</p>
                            ) : motifs.map((m) => {
                                const hex = colorOf(m);
                                return (
                                    <div key={m.id} data-testid={`motif-row-${m.id}`} className="flex items-center justify-between gap-3 px-3 py-2.5 hover:bg-slate-50">
                                        <div className="flex items-center gap-2.5 min-w-0 flex-1">
                                            <label
                                                className="relative h-7 w-7 shrink-0 rounded-md border border-slate-200 cursor-pointer overflow-hidden hover:ring-2 hover:ring-amber-300 transition"
                                                style={{ backgroundColor: hex }}
                                                title="Cliquer pour changer la couleur"
                                            >
                                                <input
                                                    type="color"
                                                    value={hex}
                                                    onChange={(e) => setMotifColorLocal(m.label, e.target.value.toUpperCase())}
                                                    data-testid={`motif-color-${m.id}`}
                                                    className="absolute inset-0 opacity-0 cursor-pointer w-full h-full"
                                                />
                                            </label>
                                            <span className="text-sm font-medium text-slate-800 truncate">{m.label}</span>
                                        </div>
                                        <button
                                            data-testid={`delete-motif-${m.id}`}
                                            onClick={() => deleteMotif(m)}
                                            className="h-8 w-8 inline-flex items-center justify-center rounded-md text-red-600 hover:bg-red-50 transition shrink-0"
                                            title="Supprimer"
                                        >
                                            <Trash2 className="h-4 w-4" />
                                        </button>
                                    </div>
                                );
                            })}
                        </div>
                    </div>

                    {/* === Zones === */}
                    <div className="rounded-lg border border-slate-200 bg-white p-5 sm:p-6" data-testid="zones-card">
                        <div className="flex items-start gap-3 mb-4">
                            <div className="flex h-10 w-10 shrink-0 items-center justify-center rounded-md bg-amber-100 text-amber-600">
                                <MapPin className="h-5 w-5" />
                            </div>
                            <div className="flex-1">
                                <h2 className="font-heading text-lg font-bold text-slate-900">Zones</h2>
                                <p className="text-sm text-slate-500 mt-0.5">{zones.length} zone{zones.length > 1 ? 's' : ''} disponible{zones.length > 1 ? 's' : ''}.</p>
                            </div>
                        </div>

                        <form onSubmit={addZone} className="flex gap-2 mb-4">
                            <input
                                data-testid="new-zone-input"
                                value={newZone}
                                onChange={(e) => setNewZone(e.target.value)}
                                placeholder="Ajouter une zone (ex: A1)…"
                                className="flex-1 h-11 rounded-md border border-slate-300 bg-white px-3 text-sm font-medium text-slate-900 uppercase tracking-wider focus:border-amber-500 focus:outline-none focus:ring-2 focus:ring-amber-500/20"
                                style={{ textTransform: 'uppercase' }}
                            />
                            <button
                                type="submit"
                                data-testid="add-zone-btn"
                                disabled={!newZone.trim() || addingZone}
                                className="inline-flex items-center gap-1.5 rounded-md bg-amber-500 text-white px-4 h-11 text-sm font-heading font-bold hover:bg-amber-600 active:scale-[0.99] transition-all disabled:opacity-50"
                            >
                                <Plus className="h-4 w-4" /> Ajouter
                            </button>
                        </form>

                        <div className="max-h-96 overflow-auto -mx-1 px-1 grid grid-cols-3 sm:grid-cols-4 md:grid-cols-5 gap-2 p-2 rounded border border-slate-200">
                            {zones.length === 0 ? (
                                <p className="col-span-full text-sm text-slate-400 italic p-4 text-center">Aucune zone. Ajoute la première ci-dessus.</p>
                            ) : zones.map((z) => (
                                <div
                                    key={z.id}
                                    data-testid={`zone-chip-${z.id}`}
                                    className="group relative inline-flex items-center justify-center h-11 rounded-md border border-slate-200 bg-slate-50 text-slate-800 font-heading font-bold text-sm tracking-wider hover:border-amber-400 hover:bg-amber-50 transition"
                                >
                                    {z.label}
                                    <button
                                        data-testid={`delete-zone-${z.id}`}
                                        onClick={() => deleteZone(z)}
                                        className="absolute -top-1.5 -right-1.5 h-5 w-5 rounded-full bg-red-500 text-white opacity-0 group-hover:opacity-100 transition-opacity flex items-center justify-center shadow"
                                        title="Supprimer"
                                    >
                                        <Trash2 className="h-2.5 w-2.5" />
                                    </button>
                                </div>
                            ))}
                        </div>
                    </div>
                </div>
            )}
        </Layout>
    );
}
