import { createContext, useCallback, useRef, useState } from "react";
import type { Screen } from "../types/screen";
import type { Component } from "../types/component";

export interface CurrentScreenStates {
    curScreen: Screen,
    curScreenIndex: number
    curScreenComponents: Component[]
    selectingComponent: Component | null
    selectingComponentIndex: number
}

export interface CurrentScreenActions {
    changeCurScreen: (index: number) => void
    selectComponent: (index: number) => void
    setSelectComponentListener: (listener: SelectComponentListenerType) => void
    resetSelectingComponent: () => void
    activateSelectMode: () => void
}

export interface CurrentScreenStatesAndActions {
    curScreenStates: CurrentScreenStates
    curScreenActions: CurrentScreenActions
}

export type SelectComponentListenerType = (selected: Component | null) => void

export function useCurrentScreen(screens: Screen[]): CurrentScreenStatesAndActions {

    const [curScreenIndex, setCurScreenIndex] = useState<number>(0);
    const [selectingComponentIndex, setSelectingComponentIndex] = useState<number>(-1);
    const [selectMode, setSelectMode] = useState<boolean>(false);
    const selectComponentCallbackRef = useRef<SelectComponentListenerType | null>(null);

    const curScreen = screens[curScreenIndex];
    const components = screens[curScreenIndex].components;
    const selectingComponent = selectingComponentIndex !== -1 ? screens[curScreenIndex].components[selectingComponentIndex] : null;

    const changeCurScreen = (index: number) => {
        if (index >= screens.length) return;
        setCurScreenIndex(index);
    }

    const selectComponent = (index: number) => {
        if (components.length <= index) return;
        if (selectMode) {
            selectComponentCallbackRef.current?.(components[index]);
            selectComponentCallbackRef.current = null;
            setSelectMode(false);
        } else {
            setSelectingComponentIndex(index);
        }
    }

    const setSelectComponentListener = useCallback((listener: SelectComponentListenerType) => {
        selectComponentCallbackRef.current = listener;
    }, [])

    const resetSelectingComponent = () => {
        if (selectMode) {
            setSelectMode(false);
        } else {
            setSelectingComponentIndex(-1);
        }
    }

    const activateSelectMode = () => {
        setSelectMode(true);
    }

    return {
        curScreenStates: {
            curScreen,
            curScreenIndex,
            curScreenComponents: components,
            selectingComponent,
            selectingComponentIndex,
        },
        curScreenActions: {
            changeCurScreen,
            selectComponent,
            setSelectComponentListener,
            resetSelectingComponent,
            activateSelectMode
        }
    }

}

export const CurrentScreenContext = createContext<CurrentScreenStatesAndActions | null>(null)