import {
    useEffect
} from "react";
import {
    View
} from "react-native";
import type {
    TimeInputRangeType
} from "./components/timeInput/type";
import type ITimeSelectorProps from "./type";
import type {
    UpdateDateRangeType,
    UpdateDateType
} from "./type";
import stylesheet, {
    useStyles
} from "./stylesheet";
import TimeInput from "./components/timeInput";
import {
    NCoreUIKitLocalize,
    NCoreUIKitTheme,
    NCoreUIKitToast
} from "../../core/hooks";
import type {
    DateTimePickerDateRange
} from "../dateTimePicker/type";
import {
    Fragment
} from "react/jsx-runtime";
import moment from "moment";
import Text from "../text";

const TimeSelector = ({
    isTimeSelectWorksWithCenterWhenTimePicker,
    isWorkWith24HoursFormat = true,
    multipleSelectMinimumRequireMS,
    isWorkWithSeconds = false,
    multipleSelectMaximumMS,
    setIsSheetContentReady,
    selectMultipleObject,
    selectObject,
    pickerType,
    dateRange,
    maxDate,
    minDate,
    variant,
    date
}: ITimeSelectorProps) => {
    const {
        spaces
    } = NCoreUIKitTheme.useContext();

    const {
        localize
    } = NCoreUIKitLocalize.useContext();

    const {
        inputsContainer: inputsContainerDynamicStyle,
        rangeContainer: rangeContainerDynamicStyle,
        colonText: colonTextDynamicStyle,
        container: containerDynamicStyle,
        timeTitle: timeTitleDynamicStyle
    } = useStyles({
        isTimeSelectWorksWithCenterWhenTimePicker,
        pickerType,
        spaces
    });

    useEffect(() => {
        if(pickerType === "time") setIsSheetContentReady(true);
    }, []);

    const setDateRangeValue = ({
        rangeType,
        minutes,
        seconds,
        hours
    }: UpdateDateRangeType) => {
        if(!dateRange) {
            return;
        }

        const newRangeDate = dateRange[rangeType] ? dateRange[rangeType] : new Date();

        if(hours !== undefined) {
            newRangeDate?.setHours(hours);
        }

        if(minutes !== undefined) {
            newRangeDate?.setMinutes(minutes);
        }

        if(seconds !== undefined) {
            newRangeDate?.setSeconds(seconds);
        }

        const newMultipleObject = dateRange;
        newMultipleObject[rangeType] = newRangeDate;

        return newMultipleObject;
    };

    const setDateValue = ({
        minutes,
        seconds,
        hours
    }: UpdateDateType) => {
        const newDate = date ? date : new Date();

        if(hours !== undefined) {
            newDate?.setHours(hours);
        }

        if(minutes !== undefined) {
            newDate?.setMinutes(minutes);
        }

        if(seconds !== undefined) {
            newDate?.setSeconds(seconds);
        }

        return newDate;
    };

    const rangeValidation = ({
        dateRangeValue,
        rangeType
    }: {
        dateRangeValue: DateTimePickerDateRange;
        rangeType: TimeInputRangeType;
    }) => {
        const start = rangeType === "start" ? dateRangeValue[rangeType] : dateRange?.start;
        const end = rangeType === "end" ? dateRangeValue[rangeType] : dateRange?.end;

        if(start && end) {
            if(multipleSelectMinimumRequireMS && Math.abs(moment(end).diff(start, "milliseconds")) < multipleSelectMinimumRequireMS) {
                NCoreUIKitToast.open({
                    title: localize("selected-start-and-end-times-cannot-be-less-than-x-times-apart", [
                        moment.duration(multipleSelectMinimumRequireMS).humanize()
                    ])
                });
                return false;
            }

            if(multipleSelectMaximumMS && Math.abs(moment(end).diff(start, "milliseconds")) > multipleSelectMaximumMS) {
                NCoreUIKitToast.open({
                    title: localize("selected-start-and-end-times-cannot-exceed-x-intervals", [
                        moment.duration(multipleSelectMaximumMS).humanize()
                    ])
                });
                return false;
            }

            if(moment(end).isBefore(start)) {
                NCoreUIKitToast.open({
                    title: localize("selected-end-time-cannot-before-from-start-time")
                });
                return false;
            }

            if(moment(start).isAfter(end)) {
                NCoreUIKitToast.open({
                    title: localize("selected-start-time-cannot-after-then-end-time")
                });
                return false;
            }
        }

        return true;
    };

    const renderTimeInputs = () => {
        if(variant === "range") {
            return <View
                style={[
                    stylesheet.rangeContainer,
                    rangeContainerDynamicStyle
                ]}
            >
                <Text
                    style={{
                        ...stylesheet.timeTitle,
                        ...timeTitleDynamicStyle
                    }}
                    variant="labelMediumSize"
                >
                    {localize("start-time")}:
                </Text>
                <View
                    style={[
                        stylesheet.inputsContainer,
                        inputsContainerDynamicStyle,
                        {
                            marginBottom: spaces.spacingMd
                        }
                    ]}
                >
                    <TimeInput
                        initialValue={dateRange?.start?.getHours().toString().padStart(2, "0")}
                        isWorkWith24HoursFormat={isWorkWith24HoursFormat}
                        selectMultipleObject={selectMultipleObject}
                        setDateRangeValue={setDateRangeValue}
                        rangeValidation={rangeValidation}
                        setDateValue={setDateValue}
                        selectObject={selectObject}
                        variant={variant}
                        maxDate={maxDate}
                        minDate={minDate}
                        rangeType="start"
                        timeType="hours"
                    />
                    <Text
                        style={{
                            ...stylesheet.colonText,
                            ...colonTextDynamicStyle
                        }}
                        variant="titleMediumSize"
                    >
                        :
                    </Text>
                    <TimeInput
                        initialValue={dateRange?.start?.getMinutes().toString().padStart(2, "0")}
                        isWorkWith24HoursFormat={isWorkWith24HoursFormat}
                        selectMultipleObject={selectMultipleObject}
                        setDateRangeValue={setDateRangeValue}
                        rangeValidation={rangeValidation}
                        setDateValue={setDateValue}
                        selectObject={selectObject}
                        timeType="minutes"
                        variant={variant}
                        maxDate={maxDate}
                        minDate={minDate}
                        rangeType="start"
                    />
                    {
                        isWorkWithSeconds ?
                            <Fragment>
                                <Text
                                    style={{
                                        ...stylesheet.colonText,
                                        ...colonTextDynamicStyle
                                    }}
                                    variant="titleMediumSize"
                                >
                                    :
                                </Text>
                                <TimeInput
                                    initialValue={dateRange?.start?.getSeconds().toString().padStart(2, "0")}
                                    isWorkWith24HoursFormat={isWorkWith24HoursFormat}
                                    selectMultipleObject={selectMultipleObject}
                                    setDateRangeValue={setDateRangeValue}
                                    rangeValidation={rangeValidation}
                                    setDateValue={setDateValue}
                                    selectObject={selectObject}
                                    timeType="seconds"
                                    variant={variant}
                                    maxDate={maxDate}
                                    minDate={minDate}
                                    rangeType="start"
                                />
                            </Fragment>
                        :
                            null
                    }
                </View>
                <Text
                    style={{
                        ...stylesheet.timeTitle,
                        ...timeTitleDynamicStyle
                    }}
                    variant="labelMediumSize"
                >
                    {localize("end-time")}:
                </Text>
                <View
                    style={[
                        stylesheet.inputsContainer,
                        inputsContainerDynamicStyle
                    ]}
                >
                    <TimeInput
                        initialValue={dateRange?.end?.getHours().toString().padStart(2, "0")}
                        isWorkWith24HoursFormat={isWorkWith24HoursFormat}
                        selectMultipleObject={selectMultipleObject}
                        setDateRangeValue={setDateRangeValue}
                        rangeValidation={rangeValidation}
                        setDateValue={setDateValue}
                        selectObject={selectObject}
                        variant={variant}
                        maxDate={maxDate}
                        minDate={minDate}
                        timeType="hours"
                        rangeType="end"
                    />
                    <Text
                        style={{
                            ...stylesheet.colonText,
                            ...colonTextDynamicStyle
                        }}
                        variant="titleMediumSize"
                    >
                        :
                    </Text>
                    <TimeInput
                        initialValue={dateRange?.end?.getMinutes().toString().padStart(2, "0")}
                        isWorkWith24HoursFormat={isWorkWith24HoursFormat}
                        selectMultipleObject={selectMultipleObject}
                        setDateRangeValue={setDateRangeValue}
                        rangeValidation={rangeValidation}
                        setDateValue={setDateValue}
                        selectObject={selectObject}
                        timeType="minutes"
                        variant={variant}
                        maxDate={maxDate}
                        minDate={minDate}
                        rangeType="end"
                    />
                    {
                        isWorkWithSeconds ?
                            <Fragment>
                                <Text
                                    style={{
                                        ...stylesheet.colonText,
                                        ...colonTextDynamicStyle
                                    }}
                                    variant="titleMediumSize"
                                >
                                    :
                                </Text>
                                <TimeInput
                                    initialValue={dateRange?.end?.getSeconds().toString().padStart(2, "0")}
                                    isWorkWith24HoursFormat={isWorkWith24HoursFormat}
                                    selectMultipleObject={selectMultipleObject}
                                    setDateRangeValue={setDateRangeValue}
                                    rangeValidation={rangeValidation}
                                    setDateValue={setDateValue}
                                    selectObject={selectObject}
                                    timeType="seconds"
                                    variant={variant}
                                    maxDate={maxDate}
                                    minDate={minDate}
                                    rangeType="end"
                                />
                            </Fragment>
                        :
                            null
                    }
                </View>
            </View>;
        }

        return <View>
            <Text
                style={{
                    ...stylesheet.timeTitle,
                    ...timeTitleDynamicStyle
                }}
                variant="labelMediumSize"
            >
                {localize("end-time")}:
            </Text>
            <View
                style={[
                    stylesheet.inputsContainer,
                    inputsContainerDynamicStyle
                ]}
            >
                <TimeInput
                    initialValue={date?.getHours().toString().padStart(2, "0")}
                    isWorkWith24HoursFormat={isWorkWith24HoursFormat}
                    selectMultipleObject={selectMultipleObject}
                    setDateRangeValue={setDateRangeValue}
                    setDateValue={setDateValue}
                    selectObject={selectObject}
                    variant={variant}
                    maxDate={maxDate}
                    minDate={minDate}
                    timeType="hours"
                />
                <Text
                    style={{
                        ...stylesheet.colonText,
                        ...colonTextDynamicStyle
                    }}
                    variant="titleMediumSize"
                >
                    :
                </Text>
                <TimeInput
                    initialValue={date?.getMinutes().toString().padStart(2, "0")}
                    isWorkWith24HoursFormat={isWorkWith24HoursFormat}
                    selectMultipleObject={selectMultipleObject}
                    setDateRangeValue={setDateRangeValue}
                    setDateValue={setDateValue}
                    selectObject={selectObject}
                    timeType="minutes"
                    variant={variant}
                    maxDate={maxDate}
                    minDate={minDate}
                />
                {
                    isWorkWithSeconds ?
                        <Fragment>
                            <Text
                                style={{
                                    ...stylesheet.colonText,
                                    ...colonTextDynamicStyle
                                }}
                                variant="titleMediumSize"
                            >
                                :
                            </Text>
                            <TimeInput
                                initialValue={date?.getSeconds().toString().padStart(2, "0")}
                                isWorkWith24HoursFormat={isWorkWith24HoursFormat}
                                selectMultipleObject={selectMultipleObject}
                                setDateRangeValue={setDateRangeValue}
                                setDateValue={setDateValue}
                                selectObject={selectObject}
                                timeType="seconds"
                                variant={variant}
                                maxDate={maxDate}
                                minDate={minDate}
                            />
                        </Fragment>
                    :
                        null
                }
            </View>
        </View>;
    };

    return <View
        style={[
            stylesheet.container,
            containerDynamicStyle
        ]}
    >
        {renderTimeInputs()}
    </View>;
};
export default TimeSelector;
