/*
    Парус 8 - Панели мониторинга - Редакторы панелей
    Компонент: Редактор условия
*/

//---------------------
//Подключение библиотек
//---------------------

import React, { useState, useEffect } from "react"; //Классы React
import PropTypes from "prop-types"; //Контроль свойств компонента
import { TextField, Select, MenuItem, FormControl, InputLabel, Stack, Box } from "@mui/material"; //Интерфейсные элементы
import { TITLES } from "../../../../app.text"; //Общие текстовые ресурсы
import { P8PConfigDialog } from "../p8p_config_dialog"; //Диалог настройки
import { P8P_CC_INITIAL, P8P_CC_SHAPE, P8P_CC_OPERATORS, P8P_CC_FIELD_PRM_SHAPE } from "./common"; //Общие ресурсы условий
import { deepCopyObject } from "../../../core/utils"; //Вспомогательные функции
import { isConditionOkDisabled } from "./util"; //Вспомогательные ресурсы условий

//---------
//Константы
//---------

//Стили
const STYLES = {
    BOX_COND_GROUP: { display: "flex", flexDirection: "row", gap: "10px", paddingBottom: "10px" },
    BOX_COND_ELEMENT: width => ({ minWidth: width })
};

//-----------
//Тело модуля
//-----------

//Редактор условия
const P8PCCEditor = ({ condition = null, onOk = null, onCancel = null, condFields = [], resFields = [] }) => {
    //Собственное состояние - признак инициализиации
    const [init, setInit] = useState(true);

    //Собственное состояние - параметры элемента формы
    const [state, setState] = useState({});

    //При закрытии редактора с сохранением
    const handleOk = () => onOk && onOk({ ...state });

    //Собственное состояние - доступность поля "Элемент условия"
    const [hasCondElement, setHasCondElement] = useState(false);

    //Собственное состояние - доступность поля "Элемент результата"
    const [hasResElement, setHasResElement] = useState(false);

    //При закрытии редактора с отменой
    const handleCancel = () => onCancel && onCancel();

    //При изменении параметра элемента
    const handleChange = e => setState(pv => ({ ...pv, [e.target.name]: e.target.value }));

    //При изменении поля условия
    const handleCondFieldChange = e => {
        //Считываем нужный элемент
        const newCondField = condFields.find(item => item.name === e.target.value);
        //Обновляем поле (объект)
        setState(pv => ({ ...pv, [e.target.name]: { name: newCondField.name, value: newCondField.value } }));
        //Определяем доступность поля "Элемент условия"
        setHasCondElement(newCondField?.hasElement || false);
    };

    //При изменении поля результата
    const handleResFieldChange = e => {
        //Считываем нужный элемент
        const newResField = resFields.find(item => item.name === e.target.value);
        //Обновляем поле результата
        setState(pv => ({ ...pv, [e.target.name]: { name: newResField.name, value: newResField.value } }));
        //Определяем доступность поля "Элемент результата"
        setHasResElement(newResField?.hasElement || false);
    };

    //При изменении оператора условия
    const handleOperatorChange = e => {
        //Считываем нужный элемент
        const newOperator = P8P_CC_OPERATORS.find(item => item.name === e.target.value);
        //Обновляем оператор
        setState(pv => ({ ...pv, [e.target.name]: { ...newOperator } }));
    };

    //При инициализации условия
    useEffect(() => {
        //Если это иницализация
        if (init) {
            //Если это открытие условия - берем его параметры, иначе - инициализируем изначальными
            const initCondition = condition
                ? condition
                : {
                      ...P8P_CC_INITIAL,
                      condField: { name: condFields[0].name, value: condFields[0].value },
                      resField: { name: resFields[0].name, value: resFields[0].value }
                  };
            //Устанавливаем параметры действия
            setState(deepCopyObject(initCondition));
            //Определяем доступность "Элемент условия"
            setHasCondElement(condFields.find(item => item.name === initCondition.condField.name)?.hasElement || false);
            //Определяем доступность "Элемент результата"
            setHasResElement(resFields.find(item => item.name === initCondition.resField.name)?.hasElement || false);
            //Сбрасываем признак инициализации
            setInit(false);
        }
        // eslint-disable-next-line react-hooks/exhaustive-deps
    }, [init]);

    //Формирование представления
    return (
        <>
            {!init ? (
                <P8PConfigDialog
                    title={`${condition ? TITLES.UPDATE : TITLES.INSERT} условия`}
                    onOk={handleOk}
                    onCancel={handleCancel}
                    okDisabled={isConditionOkDisabled(state)}
                >
                    <Stack direction={"column"} spacing={1}>
                        <Box>
                            <Box sx={STYLES.BOX_COND_GROUP}>
                                <FormControl variant={"standard"} sx={STYLES.BOX_COND_ELEMENT("160px")}>
                                    <InputLabel id={"condField-label"}>Поле</InputLabel>
                                    <Select
                                        name={"condField"}
                                        value={state.condField.name}
                                        labelId={"condField-label"}
                                        label={"Поле"}
                                        onChange={handleCondFieldChange}
                                    >
                                        {condFields.map((item, index) => (
                                            <MenuItem value={item.name} key={index}>
                                                {item.name}
                                            </MenuItem>
                                        ))}
                                    </Select>
                                </FormControl>
                                <FormControl variant={"standard"} sx={STYLES.BOX_COND_ELEMENT("70px")}>
                                    <InputLabel id={"condOperator-label"}>Оператор</InputLabel>
                                    <Select
                                        name={"condOperator"}
                                        value={state.condOperator.name}
                                        labelId={"condOperator-label"}
                                        label={"Оператор"}
                                        onChange={handleOperatorChange}
                                    >
                                        {P8P_CC_OPERATORS.map((item, index) => (
                                            <MenuItem value={item.name} key={index}>
                                                {item.name}
                                            </MenuItem>
                                        ))}
                                    </Select>
                                </FormControl>
                                <TextField
                                    InputLabelProps={{ shrink: true }}
                                    type={"text"}
                                    variant={"standard"}
                                    value={state.condValue}
                                    label={"Значение"}
                                    name={"condValue"}
                                    onChange={handleChange}
                                    sx={STYLES.BOX_COND_ELEMENT("160px")}
                                />
                            </Box>
                            {hasCondElement ? (
                                <TextField
                                    InputLabelProps={{ shrink: true }}
                                    sx={{ pb: 1.25 }}
                                    type={"text"}
                                    variant={"standard"}
                                    value={state.condElement}
                                    label={"Элемент условия"}
                                    name={"condElement"}
                                    onChange={handleChange}
                                    fullWidth
                                />
                            ) : null}
                            <Box sx={STYLES.BOX_COND_GROUP}>
                                <FormControl variant={"standard"} sx={STYLES.BOX_COND_ELEMENT("160px")}>
                                    <InputLabel id={"resField-label"}>Поле результата</InputLabel>
                                    <Select
                                        name={"resField"}
                                        value={state.resField.name}
                                        labelId={"resField-label"}
                                        label={"Поле результата"}
                                        onChange={handleResFieldChange}
                                    >
                                        {resFields.map((item, index) => (
                                            <MenuItem value={item.name} key={index}>
                                                {item.name}
                                            </MenuItem>
                                        ))}
                                    </Select>
                                </FormControl>
                                <TextField
                                    InputLabelProps={{ shrink: true }}
                                    type={"text"}
                                    variant={"standard"}
                                    value={state.resValue}
                                    label={"Результат"}
                                    name={"resValue"}
                                    onChange={handleChange}
                                    fullWidth
                                />
                            </Box>
                            {hasResElement ? (
                                <TextField
                                    InputLabelProps={{ shrink: true }}
                                    sx={{ pb: 1.25 }}
                                    type={"text"}
                                    variant={"standard"}
                                    value={state.resElement}
                                    label={"Элемент результата"}
                                    name={"resElement"}
                                    onChange={handleChange}
                                    fullWidth
                                />
                            ) : null}
                        </Box>
                    </Stack>
                </P8PConfigDialog>
            ) : null}
        </>
    );
};

//Контроль свойств - Редактор условия
P8PCCEditor.propTypes = {
    condition: P8P_CC_SHAPE,
    onOk: PropTypes.func.isRequired,
    onCancel: PropTypes.func.isRequired,
    condFields: PropTypes.arrayOf(P8P_CC_FIELD_PRM_SHAPE).isRequired,
    resFields: PropTypes.arrayOf(P8P_CC_FIELD_PRM_SHAPE).isRequired
};

//----------------
//Интерфейс модуля
//----------------

export { P8PCCEditor };
