import {
    TouchableOpacity,
    View
} from "react-native";
import {
    type SelectedItem
} from "./type";
import type ISelectSheetProps from "./type";
import stylesheet, {
    useStyles
} from "./stylesheet";
import {
    NCoreUIKitLocalize,
    NCoreUIKitTheme
} from "../../core/hooks";
import {
    CheckIcon
} from "lucide-react-native";
import BottomSheet from "../bottomSheet";
import TextInput from "../textInput";
import CheckBox from "../checkBox";
import Loading from "../loading";
import Button from "../button";
import Text from "../text";

function SelectSheet<T>({
    LoadingIconComponentProp,
    isShowTools = true,
    isWorkWithRealtime,
    mainSelectedItems,
    moreLoadThreshold,
    bottomSheetProps,
    isMultipleSelect,
    renderOptionIcon,
    setIsMoreLoading,
    bottomSheetRef,
    customLocalize,
    isMoreLoading,
    setSearchText,
    isSearchable,
    keyExtractor,
    searchedData,
    selectBoxKey,
    selectObject,
    setIsLoading,
    customTheme,
    setIsActive,
    onMoreLoad,
    renderItem,
    searchText,
    customKey,
    isLoading,
    maxChoice,
    minChoice,
    selectAll,
    cleanAll,
    isActive,
    cancel,
    title,
    data,
    ok
}: ISelectSheetProps<T>) {
    const {
        radiuses,
        colors,
        spaces
    } = NCoreUIKitTheme.useContext(customTheme);

    const {
        localize
    } = NCoreUIKitLocalize.useContext(customLocalize);

    const {
        moreLoadingContainer: moreLoadingContainerDynamicStyle,
        checkIconContainer: checkIconContainerDynamicStyle,
        contentContainer: contentContainerDynamicStyle,
        loadingContainer: loadingContainerDynamicStyle,
        bottomContainer: bottomContainerDynamicStyle,
        headerContainer: headerContainerDynamicStyle,
        toolsContainer: toolsContainerDynamicStyle,
        itemContainer: itemContainerDynamicStyle,
        cancelButton: cancelButtonDynamicStyle,
        headerTitle: headerTitleDynamicStyle,
        okButton: okButtonDynamicStyle
    } = useStyles({
        isSearchable,
        radiuses,
        spaces,
        colors
    });

    const renderBottomSheetContent = () => {
        if(isLoading) {
            return <View
                style={[
                    stylesheet.loadingContainer,
                    loadingContainerDynamicStyle
                ]}
            >
                {
                    LoadingIconComponentProp ?
                        <LoadingIconComponentProp
                            color="emphasized"
                            size={20}
                        />
                    :
                        <Loading/>
                }
            </View>;
        }

        const currentData = searchText && searchText.length ? searchedData : data;

        return <View
            style={[
                contentContainerDynamicStyle
            ]}
        >
            {
                currentData.map((item: T & SelectedItem | SelectedItem, index: number) => {
                    const isSelected = mainSelectedItems.findIndex((sI: SelectedItem) => {
                        return sI.__key === item.__key;
                    }) !== -1;

                    if(renderItem) {
                        return renderItem({
                            key: keyExtractor(item as T & SelectedItem, index),
                            selectedItems: mainSelectedItems,
                            onSelect: (sItem) => {
                                selectObject(sItem);
                            },
                            setIsMoreLoading,
                            setIsLoading,
                            isSelected,
                            searchText,
                            index,
                            item,
                            data
                        });
                    }

                    let isDisabled = false;

                    if(isMultipleSelect && !isSelected && maxChoice !== -1) {
                        if(!maxChoice) {
                            throw new Error("If you want to use the \"isMultipleSelect\" prop, you must be provide \"maxChoice\" prop.");
                        }

                        if(mainSelectedItems.length >= maxChoice) {
                            isDisabled = true;
                        }
                    }

                    return <TouchableOpacity
                        style={[
                            stylesheet.itemContainer,
                            itemContainerDynamicStyle,
                            {
                                marginTop: index === 0 ? 0 : spaces.spacingSm
                            }
                        ]}
                        key={keyExtractor(item as T & SelectedItem, index)}
                        onPress={() => {
                            if(isDisabled) {
                                return;
                            }

                            selectObject(item);
                        }}
                        disabled={isDisabled}
                    >
                        <View
                            style={stylesheet.itemContentContainer}
                        >
                            {renderOptionIcon ? renderOptionIcon({
                                index,
                                item
                            }) : null}
                            <Text
                                color={isSelected ? "emphasized" : undefined}
                            >
                                {item.__title}
                            </Text>
                        </View>
                        <View
                            style={[
                                stylesheet.checkIconContainer,
                                checkIconContainerDynamicStyle
                            ]}
                        >
                            {
                                isSelected ?
                                    <CheckIcon
                                        color={colors.content.icon.emphasized}
                                        size={24}
                                    />
                                :
                                    null
                            }
                        </View>
                        {
                            isDisabled ?
                                <View
                                    style={[
                                        stylesheet.disabledOverlay,
                                        {
                                            backgroundColor: colors.system.disabled.content,
                                            borderRadius: radiuses.actions
                                        }
                                    ]}
                                />
                            :
                                null
                        }
                    </TouchableOpacity>;
                })
            }
            {renderMoreLoading()}
        </View>;
    };

    const renderBottomSheetSearchInput = () => {
        if(!isSearchable) {
            return null;
        }

        return <TextInput
            key={`${selectBoxKey}-searchInput`}
            onChangeText={(text: string) => {
                setSearchText(text);
            }}
            placeholder={localize("search")}
            spreadBehaviour="stretch"
        />;
    };

    const renderTools = () => {
        if(!isShowTools) {
            return null;
        }

        if(!isMultipleSelect) {
            return null;
        }

        if(minChoice && maxChoice !== -1) {
            return null;
        }

        return <View
            style={[
                stylesheet.toolsContainer,
                toolsContainerDynamicStyle
            ]}
        >
            {
                !minChoice ?
                    <CheckBox
                        isChecked={mainSelectedItems.length === 0 ? "checked" : null}
                        title={localize("clean-all")}
                        spreadBehaviour="free"
                        onPress={() => {
                            cleanAll();
                        }}
                    />
                :
                    null
            }
            {
                maxChoice === -1 ?
                    <CheckBox
                        isChecked={data.length === mainSelectedItems.length ? "checked" : mainSelectedItems.length ? "partially" : null}
                        title={localize("select-all")}
                        spreadBehaviour="free"
                        isFlip={!minChoice}
                        onPress={() => {
                            selectAll();
                        }}
                    />
                :
                    null
            }
        </View>;
    };

    const renderBottomSheetHeader = () => {
        return <View
            style={[
                stylesheet.headerContainer,
                headerContainerDynamicStyle
            ]}
        >
            <Text
                style={[
                    headerTitleDynamicStyle
                ]}
                variant="titleMediumSize"
            >
                {title}
            </Text>
            {renderBottomSheetSearchInput()}
            {renderTools()}
        </View>;
    };

    const renderBottomSheetBottom = () => {
        if(isWorkWithRealtime) {
            return null;
        }

        return <View
            style={[
                stylesheet.bottomContainer,
                bottomContainerDynamicStyle
            ]}
        >
            <Button
                style={{
                    ...cancelButtonDynamicStyle
                }}
                title={localize("cancel")}
                spreadBehaviour="stretch"
                variant="outline"
                onPress={() => {
                    cancel();
                }}
                type="neutral"
            />
            <Button
                style={{
                    ...okButtonDynamicStyle
                }}
                spreadBehaviour="stretch"
                title={localize("ok")}
                onPress={() => {
                    ok();
                }}
            />
        </View>;
    };

    const renderMoreLoading = () => {
        if(!isMoreLoading) {
            return null;
        }

        return <View
            style={[
                stylesheet.moreLoadingContainer,
                moreLoadingContainerDynamicStyle
            ]}
        >
            <Loading/>
        </View>;
    };

    return <BottomSheet
        {...bottomSheetProps}
        key={customKey ? customKey : `${selectBoxKey}-bottomsheet`}
        onScrollEnd={() => {
            if(onMoreLoad) onMoreLoad({
                selectedItems: mainSelectedItems,
                setIsMoreLoading,
                setIsLoading,
                searchText,
                data
            });
        }}
        scrollEndThreshold={moreLoadThreshold}
        renderBottom={() => {
            return renderBottomSheetBottom();
        }}
        renderHeader={() => {
            return renderBottomSheetHeader();
        }}
        customKey={selectBoxKey}
        onClosed={() => {
            setIsActive(false);
        }}
        ref={bottomSheetRef}
        isAutoHeight={true}
        isActive={isActive}
    >
        {renderBottomSheetContent()}
    </BottomSheet>;
};
export default SelectSheet;
