import React, { createRef, useEffect, useState, useRef, useReducer } from 'react';
import ReactDOM from 'react-dom';
import { observer } from 'mobx-react';

import SplitPane from 'react-split-pane';
import Pane from 'react-split-pane';

import { debounce, testLocalStorageAvailable } from '../../helpers/misc-helpers';

import './VoletsFractionnes.scss';

/**
 * Composant "Volets fractionnés" permettant de présenter plusieurs composants React côte-à-côte ou les uns sous les autres,
 * sous forme de volets dont la taille est redimensionnable par l'utilisateur via la souris.
 *
 *
 * @component
 * @param {array} props.volets - La liste des volets à afficher
 * @param {string} props.disposition - La disposition des volets "vertical" (volets verticaux présentés côte-à-côte)
 * ou "horizontal" (volets horizontaux présentés les uns au dessus des autres)
 * @param {string} props.persistenceId - Identifiant unique des volets (pour persistence de la configuration en localStorage)
 *
 * @example
 * return (
 * <VoletsFractionnes disposition="horizontal" volets={[<Volet1 />, <Volet2 />]} persistenceId="MesVolets" />
 * )
 */

const VoletsFractionnes = observer((props) => {
    const isLocalStorageAvailable = testLocalStorageAvailable();

    const getStorageKey = () => 'VoletsFractionnes_' + props.persistenceId;

    const [initialSizes, setInitialSizes] = useState(props.paneSizes);

    const splitPaneRef = useRef(null);

    //const [paneRefs, setPaneRefs] = React.useState([]);
    const [ignored, forceUpdate] = useReducer((x) => x + 1, 0);

    /*
    useEffect(() => {
        // Initialisation des paneRefs
        setPaneRefs((paneRefs) =>
            Array(props.volets.length || 0)
                .fill()
                .map((_, i) => paneRefs[i] || createRef())
        );
    }, [props.volets.length]);
    */

    const updateInitialSizes = () => {
        console.log('updateInitialSizes');
        if (isLocalStorageAvailable && props.persistenceId && props.volets.length == props.paneSizes?.length) {
            const sizesJSON = localStorage.getItem(getStorageKey());
            if (!sizesJSON) {
                setInitialSizes(props.paneSizes);
                return;
            }

            let tempInitialSizes = JSON.parse(sizesJSON);

            const initialSizesLength = tempInitialSizes.length;
            if (props.paneSizes && initialSizesLength < props.paneSizes.length) {
                // S'il y a moins d'éléments que prévu dans initialSizes, on initialise les dimensions manquantes au prorata de props.paneSizes
                const dispoARepartir = parseFloat(tempInitialSizes[initialSizesLength - 1]);

                let totalARepartir = 0,
                    i;
                for (i = initialSizesLength - 1; i < props.paneSizes.length; i++) {
                    totalARepartir += parseFloat(props.paneSizes[i]);
                }
                const k = dispoARepartir / totalARepartir;
                tempInitialSizes.splice(-1, 1);
                for (i = initialSizesLength - 1; i < props.paneSizes.length; i++) {
                    tempInitialSizes.push(parseFloat(props.paneSizes[i]) * k + '%');
                }
            } else if (props.paneSizes && initialSizesLength > props.paneSizes.length && props.paneSizes.length >= 2) {
                // S'il y a plus d'éléments que prévu dans initialSizes, la taille du dernier volet est égale à la somme de tous ceux en trop
                let totalDispo = 0;
                for (let i = props.paneSizes.length - 1; i < initialSizesLength; i++) {
                    totalDispo += parseFloat(tempInitialSizes[i]);
                }
                tempInitialSizes.length = props.paneSizes.length - 1;
                tempInitialSizes.push(totalDispo + '%');
            }
            setInitialSizes(tempInitialSizes);
        } else {
            setInitialSizes(props.paneSizes);
        }
    };

    useEffect(() => {
        updateInitialSizes();
    }, [props.paneSizes, props.volets]);

    const onChange = debounce((sizes) => {
        if (!props.persistenceId || !isLocalStorageAvailable) {
            return;
        }

        localStorage.setItem(getStorageKey(), JSON.stringify(sizes));
    }, 500);

    const onResizerDoubleClick = (event) => {
        if (props.persistenceId && isLocalStorageAvailable) {
            // RAZ aux dimensions par défaut
            localStorage.removeItem(getStorageKey());
        }

        setInitialSizes(props.paneSizes);

        /*
        //setSize non implémenté !! :-@
        // Redimensionnement aux dimensions par défaut
        if (props.paneSizes) {
            for (let i = 0; i < props.paneSizes.length; i++) {
                //paneRefs[i].current.setSize(props.paneSizes[i]);
            }
        }
        */
        forceUpdate();
    };

    // Comme la propriété onResizerDoubleClick de <SplitPane> n'est pas câblée, on le fait artificiellement ici
    useEffect(() => {
        let splitPaneDomNode = ReactDOM.findDOMNode(splitPaneRef.current);
        if (splitPaneDomNode) {
            const resizers = splitPaneDomNode.querySelectorAll("[data-type='Resizer']");
            if (resizers?.length) {
                for (let r of resizers) {
                    r.ondblclick = onResizerDoubleClick;
                    r.title = 'Double-cliquez pour réinitialiser le positionnement des volets';
                }
            }
        }
    });

    return (
        <SplitPane
            ref={splitPaneRef}
            minSize={100}
            split={props.disposition}
            className={'VoletsFractionnes disposition-' + props.disposition}
            resizerClassName="VoletsFractionnesResizer"
            resizerStyle={{ border: '1px solid red' }}
            onChange={onChange}
            //onResizerDoubleClick={onResizerDoubleClick}
        >
            {props.volets.map((volet, i) => (
                <Pane /*ref={paneRefs[i]}*/ key={'volet' + i} className="volet" minSize={'10%'} initialSize={initialSizes?.[i]}>
                    {[volet]}
                </Pane>
            ))}
        </SplitPane>
    );
});

export default VoletsFractionnes;
