import { FontAwesome } from '@expo/vector-icons';
import React, { Dispatch, FC, SetStateAction, useEffect, useMemo, useState } from 'react';
import { Text, View } from 'react-native';

import { latinise } from '../../helpers/searchHelpers';
import { useSearchUnit } from '../../hooks/useSearchUnit';
import { useUserInfo } from '../../hooks/useStorage';
import { useUnitTree } from '../../hooks/useUnit';
import Button from '../Button/Button';
import IconButton from '../Button/IconButton';
import CheckboxList from '../List/CheckboxList';
import Loader from '../Loader/Loader';
import InfoModal from '../Modal/InfoModal';
import SelectModal from '../Modal/SelectModal';
import Switch from '../Switch/Switch';
import TextField from '../TextField/TextField';

type props = {
  unitId: string;
  selectedUnitIds: string[];
  setSelectedUnitIds: Dispatch<SetStateAction<string[]>>;
};

const UnitSelect: FC<props> = ({ setSelectedUnitIds, selectedUnitIds, unitId }) => {
  const [searchInNames, setCurrentSearchInNames] = useState(true);
  const [searchInRegNumbers, setCurrentSearchInRegNumbers] = useState(false);
  const [searchInPlace, setCurrentSearchInPlace] = useState(false);
  const [searchValue, setSearchValue] = useState('');
  const [userInfo] = useUserInfo();

  const [isUnitModalVisible, setIsUnitModalVisible] = useState(false);
  const [isInfoModalVisible, setIsInfoModalVisible] = useState(false);
  const [buttonClicked, setButtonClicked] = useState(false);
  const [selectedUnits, setSelectedUnits] = useState<Set<string>>(new Set());
  const [firstLoad, setFirstLoad] = useState(true);

  const {
    data: outsideList,
    isFetching: isOutsideLoading,
    refetch: refetchList,
  } = useSearchUnit(
    userInfo.token,
    searchInRegNumbers ? searchValue : '',
    false,
    searchInNames ? searchValue : '',
    searchInPlace ? searchValue : '',
    '',
    '',
    '',
  );

  const { data: list, isLoading: isTreeLoading } = useUnitTree(userInfo.token, unitId);

  const filteredOutsideList = useMemo(
    () => outsideList?.filter(item => item.type === 'Oddíl') || [],
    [outsideList],
  );

  useEffect(() => {
    if (!isOutsideLoading) {
      if (buttonClicked) {
        setButtonClicked(false);
        if (filteredOutsideList?.length === 0) {
          setIsInfoModalVisible(true);
        } else {
          setIsUnitModalVisible(true);
        }
      }
    }
  }, [isOutsideLoading]);

  useEffect(() => {
    if (selectedUnitIds.length > 0 && !isTreeLoading && !isOutsideLoading && firstLoad) {
      setFirstLoad(false);
      setSelectedUnits(
        prev =>
          new Set([
            ...prev,
            ...selectedUnitIds
              .map(id => formattedUnit(list?.find(unit => unit.id === id)))
              .filter(item => item.length),
            ...selectedUnitIds
              .map(id => formattedUnitOutside(outsideList?.find(unit => unit.id === id)))
              .filter(item => item.length),
          ]),
      );
    }
  }, [isTreeLoading, isOutsideLoading]);

  const formattedUnit = (unit: any) => {
    if (!unit) return '';
    return `${unit.registrationNumber} - ${unit.unit}`;
  };

  const formattedUnitOutside = (unit: any) => {
    if (!unit) return '';
    return `${unit.number} - ${unit.displayName}`;
  };

  return (
    <View>
      {!isTreeLoading && (!isOutsideLoading || !firstLoad) ? (
        <View>
          <Text className="mt-4 font-bold">Vybrat oddíly</Text>
          <View className="rounded bg-secondary-bg">
            <View className="my-2 flex-row items-center justify-between px-4">
              <Text className="font-bold text-secondary">Oddíly</Text>
            </View>
            <CheckboxList
              items={(list || [])?.map(unit => ({
                value: unit.id,
                label: formattedUnit(unit),
              }))}
              selected={value => selectedUnits.has(value?.label || '')}
              onPress={value => {
                if (selectedUnits.has(value?.label || '')) {
                  setSelectedUnits(prev => {
                    const newSet = new Set(prev);
                    newSet.delete(value?.label || '');
                    return newSet;
                  });
                  setSelectedUnitIds(prev => prev.filter(id => id !== value?.value));
                } else {
                  setSelectedUnitIds(prev => [...prev, value?.value || '']);
                  setSelectedUnits(prev => new Set(prev).add(value?.label || ''));
                }
              }}
            />
            <View className="p-4">
              <View className="h-1 bg-divider" />

              <View className="mt-4 mb-2 flex-row items-center justify-between">
                <Text className="font-bold text-secondary">Oddíly z jiného střediska</Text>
              </View>
              <View className="mb-4">
                <TextField
                  title="Text na vyhledání jednotky"
                  value={searchValue}
                  setValue={value => setSearchValue(latinise(value))}
                />
              </View>
              <View className="flex-row items-center justify-between">
                <Text className="font-bold">Hledat podle jména</Text>
                <Switch
                  setIsEnabled={value => {
                    if (value) {
                      setCurrentSearchInRegNumbers(false);
                      setCurrentSearchInPlace(false);
                    } else if (!searchInRegNumbers && !searchInPlace && !value) {
                      return;
                    }
                    setCurrentSearchInNames(value);
                  }}
                  isEnabled={searchInNames}
                />
              </View>
              <View className="flex-row items-center justify-between">
                <Text className="font-bold">Hledat podle evidenčního čísla</Text>
                <Switch
                  setIsEnabled={value => {
                    if (value) {
                      setCurrentSearchInNames(false);
                      setCurrentSearchInPlace(false);
                    } else if (!searchInNames && !searchInPlace && !value) {
                      return;
                    }
                    setCurrentSearchInRegNumbers(value);
                  }}
                  isEnabled={searchInRegNumbers}
                />
              </View>
              <View className="flex-row items-center justify-between">
                <Text className="font-bold">Hledat podle místa působení</Text>
                <Switch
                  setIsEnabled={value => {
                    if (value) {
                      setCurrentSearchInNames(false);
                      setCurrentSearchInRegNumbers(false);
                    } else if (!searchInNames && !searchInRegNumbers && !value) {
                      return;
                    }
                    setCurrentSearchInPlace(value);
                  }}
                  isEnabled={searchInPlace}
                />
              </View>
              <Button
                variant="ternary"
                onPress={() => {
                  setButtonClicked(true);
                  refetchList();
                }}
              >
                {isOutsideLoading ? 'Načítám...' : 'Přidat Jednotku'}
              </Button>
            </View>
            {selectedUnits.size > 0 && (
              <>
                <View className="px-4 pb-4">
                  <View className="h-1 bg-divider" />
                  <View className="mt-4 mb-2 flex-row items-center justify-between">
                    <Text className="font-bold text-secondary">Vybranné oddíly</Text>
                  </View>
                  {[...selectedUnits].map((item, index) => (
                    <View key={index} className="flex flex-row items-center">
                      <IconButton
                        variant="secondary"
                        onPress={() => {
                          setSelectedUnits(prev => {
                            const newSet = new Set(prev);
                            newSet.delete(item);
                            return newSet;
                          });
                          let unitId = filteredOutsideList.find(
                            unit => formattedUnitOutside(unit) === item,
                          )?.id;
                          if (!unitId) {
                            unitId = list?.find(unit => formattedUnit(unit) === item)?.id;
                          }
                          if (unitId) {
                            setSelectedUnitIds(prev => prev.filter(id => id !== unitId));
                          }
                        }}
                      >
                        <FontAwesome name="trash" size={28} />
                      </IconButton>
                      <Text className="ml-2 text-primary-text">{item}</Text>
                    </View>
                  ))}
                </View>
              </>
            )}
          </View>
        </View>
      ) : (
        <Loader />
      )}

      <InfoModal
        isVisible={isInfoModalVisible}
        setIsVisible={setIsInfoModalVisible}
        title="Hledání jednotky"
        text="Žádná jednotka nebyla nalezena."
      />
      <SelectModal
        items={filteredOutsideList.map(unit =>
          formattedUnit({
            registrationNumber: unit.number,
            unit: unit.displayName,
          }),
        )}
        setSelected={value => {
          const unit = filteredOutsideList.find(unit => formattedUnitOutside(unit) === value);
          if (unit) {
            setSelectedUnits(prev => new Set([...prev, value]));
            setSelectedUnitIds(prev => [...prev, unit.id]);
          }
        }}
        fullHeight={(filteredOutsideList?.length || 0) > 20}
        title="Vyberte položku"
        itemGetter={item => item}
        isVisible={isUnitModalVisible}
        setIsVisible={setIsUnitModalVisible}
      />
    </View>
  );
};

export default UnitSelect;
