import React, { useState } from 'react';
import { BottomSheetScrollView } from '@gorhom/bottom-sheet';
import { useTheme, spacing } from '../../branding';
import themedStyles from './styles';
import MarketSection from './MarketSection';
import { useReactiveVar } from '@apollo/client';
import {
    bottomSheetHeaderAppliedFilters,
    setBottomSheetHeaderAppliedFiltersForScreen
} from '../../apollo/reactive-vars';
import type {
    FilterScreenValue,
    NamedFilterItem
} from '../../apollo/reactive-vars/bottom-sheet-header-applied-filters';
import useIsEmployee from '../../hooks/auth/useIsEmployee';
import BrandSection from './BrandSection';
import StoreSection from './StoreSection';
import LabelSection from './LabelSection';
import ArtistSection from './ArtistSection';
import useHasFeature from '../../hooks/auth/useHasFeature';
import { MOBILE_BOTTOM_SHEET_SORTING } from '../../constants/features';
import useMyCatalogSortParams from '../../hooks/useMyCatalogTabsSortParams';
import useMyCatalogSoundRecordingParams from '../../hooks/useMyCatalogSoundRecordingParams';
import {
    ABSOLUTE_CHANGE,
    STREAMS,
    STREAMS_1_DAY,
    STREAMS_ALL_TIME
} from '../../constants/sorting';
import { bottomSheetScreen } from '../../screens/MyCatalogScreen/BottomSheetFilter/constants';
import type {
    ArtistFilterItem,
    Brand,
    MyCatalogBottomSheetFilterProps
} from './types';
import type {
    RecentArtistFilter,
    RecentLabelFilter
} from '../../types/recent-selected-filters';
import { useSafeAreaInsets } from 'react-native-safe-area-context';
import { regions } from '../../constants/regions';
import type { RegionName } from '../../constants/regions';
import SortingSection from './SortingSection';
import useRecentSelectedFilters from '../../hooks/useRecentSelectedFilters';
import { getLabelId } from '../../components/LabelRow/utils';

const getSortOrderByWithType = (newOrderBy: string, sortType: string) => {
    const hasAbsolute = newOrderBy.includes(ABSOLUTE_CHANGE);
    if (sortType === ABSOLUTE_CHANGE && !hasAbsolute) {
        return `${newOrderBy}_${sortType}`;
    }
    if (sortType !== ABSOLUTE_CHANGE && hasAbsolute) {
        return newOrderBy.replace(`_${ABSOLUTE_CHANGE}`, '');
    }
    return newOrderBy;
};

const MyCatalogBottomSheetFilter = ({
    navigation,
    showStoreSection = true
}: MyCatalogBottomSheetFilterProps) => {
    const { theme } = useTheme();
    const styles = themedStyles[theme];
    const filters = useReactiveVar(bottomSheetHeaderAppliedFilters);
    const hasMobileBottomSheetSorting = useHasFeature(
        MOBILE_BOTTOM_SHEET_SORTING
    );
    const { setTabsOrderParams } = useMyCatalogSortParams();
    const [soundRecordingParams] = useMyCatalogSoundRecordingParams();
    const orderBy: string = (soundRecordingParams as any).orderBy;
    const [selectedSortType, setSelectedSortType] = useState(
        orderBy.includes(ABSOLUTE_CHANGE) ? ABSOLUTE_CHANGE : STREAMS
    );

    const isEmployee = useIsEmployee();
    const { bottom } = useSafeAreaInsets();
    const { addRecentLabel, addRecentArtist } = useRecentSelectedFilters();

    const handleSortPress = (newOrderBy: string) => {
        const orderByWithType = getSortOrderByWithType(
            newOrderBy,
            selectedSortType
        );
        setTabsOrderParams(orderByWithType);
    };

    const handleSwitchSelectorPress = (sortType: string) => {
        setSelectedSortType(sortType);
        const isChange = sortType === ABSOLUTE_CHANGE;
        const effectiveOrderBy =
            isChange && orderBy === STREAMS_ALL_TIME ? STREAMS_1_DAY : orderBy;
        const orderByWithType = getSortOrderByWithType(
            effectiveOrderBy,
            sortType
        );
        setTabsOrderParams(orderByWithType);
    };

    const handleSearchPillPress = (navigationName: string) => {
        navigation.navigate(navigationName);
    };

    const handleStorePress = (
        storeId: string,
        keyScreenName: string,
        currentSelection: FilterScreenValue[]
    ) => {
        const isSelected = currentSelection.includes(storeId);
        const updatedFilters = isSelected
            ? currentSelection.filter(value => value !== storeId)
            : [...currentSelection, storeId];
        setBottomSheetHeaderAppliedFiltersForScreen(
            keyScreenName,
            updatedFilters
        );
    };

    const handleBrandPress = (brand: Brand, keyScreenName: string) => {
        const currentFilters = (filters[keyScreenName] || []) as string[];
        const isSelected = currentFilters.includes(brand.value);
        const relatedFilterBrands =
            brand.relatedBrands?.map(({ value }) => value) || [];

        const updatedFilters = isSelected
            ? currentFilters.filter(
                  value =>
                      value !== brand.value &&
                      !relatedFilterBrands.includes(value)
              )
            : [...currentFilters, brand.value, ...relatedFilterBrands];

        setBottomSheetHeaderAppliedFiltersForScreen(
            keyScreenName,
            updatedFilters
        );
    };

    const handleRegionPillPress = (region: RegionName, isSelected: boolean) => {
        const regionCountryCodes = Object.keys(regions[region]);
        const updatedFilters = isSelected ? [] : regionCountryCodes;

        setBottomSheetHeaderAppliedFiltersForScreen(
            bottomSheetScreen.countries,
            updatedFilters
        );
    };

    const handleCountryPillPress = (country: string, isSelected: boolean) => {
        const updatedFilters = isSelected ? [] : [country];

        setBottomSheetHeaderAppliedFiltersForScreen(
            bottomSheetScreen.countries,
            updatedFilters
        );
    };

    const handleCountriesPillPress = (
        countries: string[],
        isSelected: boolean
    ) => {
        const updatedFilters = isSelected ? [] : countries;

        setBottomSheetHeaderAppliedFiltersForScreen(
            bottomSheetScreen.countries,
            updatedFilters
        );
    };

    const handleLabelPillPress = (
        label: RecentLabelFilter,
        isSelected: boolean
    ) => {
        const currentFilters = (filters[bottomSheetScreen.labels] ||
            []) as NamedFilterItem[];
        const updatedFilters = isSelected
            ? currentFilters.filter(
                  item =>
                      item.name !== label.name &&
                      (!item.id ||
                          !label.id ||
                          getLabelId(item as RecentLabelFilter) !==
                              getLabelId(label))
              )
            : [...currentFilters, label];

        if (!isSelected && label.id) {
            addRecentLabel({ id: label.id, name: label.name });
        }

        setBottomSheetHeaderAppliedFiltersForScreen(
            bottomSheetScreen.labels,
            updatedFilters
        );
    };

    const handleArtistPillPress = (
        artist: RecentArtistFilter,
        isSelected: boolean
    ) => {
        const currentFilters = (filters[bottomSheetScreen.artists] ||
            []) as ArtistFilterItem[];
        const updatedFilters = isSelected
            ? currentFilters.filter(item => item.id !== artist.id)
            : [...currentFilters, artist];

        if (!isSelected) {
            addRecentArtist({
                id: artist.id,
                name: artist.name,
                imageUrl: artist.imageUrl
            });
        }

        setBottomSheetHeaderAppliedFiltersForScreen(
            bottomSheetScreen.artists,
            updatedFilters
        );
    };

    return (
        <BottomSheetScrollView
            nestedScrollEnabled
            style={styles.scrollView}
            contentContainerStyle={[
                styles.scrollContent,
                { paddingBottom: spacing.xl + bottom }
            ]}
        >
            {hasMobileBottomSheetSorting ? (
                <SortingSection
                    onSortPress={handleSortPress}
                    onSwitchSelectorPress={handleSwitchSelectorPress}
                    currentOrderBy={orderBy}
                    selectedSortType={selectedSortType}
                />
            ) : null}
            <MarketSection
                filters={filters}
                onSearchPress={handleSearchPillPress}
                onRegionPress={handleRegionPillPress}
                onCountryPress={handleCountryPillPress}
                onCountriesPress={handleCountriesPillPress}
            />
            {showStoreSection ? (
                <StoreSection
                    filters={filters}
                    onStorePress={handleStorePress}
                />
            ) : null}
            <BrandSection
                isEmployee={isEmployee}
                filters={filters}
                onBrandPress={handleBrandPress}
            />
            <LabelSection
                activeFilters={
                    (filters[bottomSheetScreen.labels] ||
                        []) as NamedFilterItem[]
                }
                onSearchPress={handleSearchPillPress}
                onLabelPress={handleLabelPillPress}
            />
            <ArtistSection
                activeFilters={
                    (filters[bottomSheetScreen.artists] ||
                        []) as ArtistFilterItem[]
                }
                onSearchPress={handleSearchPillPress}
                onArtistPress={handleArtistPillPress}
            />
        </BottomSheetScrollView>
    );
};

export default MyCatalogBottomSheetFilter;
