import { useCallback, useEffect, useMemo, useState } from 'react';
import styled from 'styled-components';
import { loadInitialData, setOption } from './api/promoApi';
import { Cart } from './components/Cart/Cart';
import { CookiePopup } from './components/CookiePopup/CookiePopup';
import { FamilySection } from './components/Family/FamilySection';
import { CategoriesSection } from './components/Categories/CategoriesSection';
import { DaysSection } from './components/Days/DaysSection';
import { Accordion } from './components/Accordion/Accordion';
import { normalizeProductImage } from './utils/product';
import type { InitialData } from './types/api';
import type { Product } from './types/cart';
import type { User } from './types/user';

export function App() {
    const [initialData, setInitialData] = useState<InitialData | null>(null);
    const [products, setProducts] = useState<Product[]>([]);
    const [isCartComplete, setIsCartComplete] = useState(false);
    const [isCartLoading, setIsCartLoading] = useState(true);
    const [openSection, setOpenSection] = useState<string>('family');

    useEffect(() => {
        loadInitialData().then(data => {
            setInitialData(data);
            setProducts(data.cart.flat().map(product => normalizeProductImage(product)));
        });
    }, []);

    const users = initialData?.users ?? [];
    const categories = initialData?.available_groups ?? [];
    const selectedCategories = initialData?.initial_groups ?? [];
    const days = initialData?.days ?? 7;

    const handleDaysChange = useCallback(async (nextDays: number) => {
        setInitialData(current => current ? { ...current, days: nextDays } : current);
        await setOption('days', nextDays);
    }, []);

    const handleUsersChange = useCallback(async (nextUsers: User[]) => {
        setInitialData(current => current ? { ...current, users: nextUsers } : current);
        await setOption('users', nextUsers);
    }, []);

    const handleCategoriesChange = useCallback((nextCategories: string[]) => {
        setInitialData(current => current ? { ...current, initial_groups: nextCategories } : current);
    }, []);

    const pageContent = useMemo(() => {
        if (!initialData) {
            return <LoadingPage>Загрузка...</LoadingPage>;
        }

        return (
            <Container>
                <LeftColumn>
                    <TitleBlock>
                        <h1>Автокорзина</h1>
                        <p>Собираем продукты под ваши настройки</p>
                    </TitleBlock>

                    <Cart
                        products={products}
                        days={initialData.days}
                        excess={initialData.excess ?? 0}
                        isComplete={isCartComplete}
                        isLoading={isCartLoading}
                        onProductsChange={setProducts}
                        onComplete={() => {
                            setIsCartComplete(true);
                            setIsCartLoading(false);
                        }}
                        onLoadingChange={setIsCartLoading}
                    />
                </LeftColumn>

                <RightColumn>
                    <FilterTitle>
                        <h2>Настройте корзину под себя</h2>
                        <p>Чем больше вы расскажете, тем точнее будет подбор</p>
                    </FilterTitle>

                    <SettingsPanel>
                        <Accordion
                            id="days"
                            title="На сколько дней собираем корзину?"
                            icon={<img src="/images/calendar.svg" alt="календарь" />}
                            isOpen={openSection === 'days'}
                            onToggle={() => setOpenSection(openSection === 'days' ? '' : 'days')}
                        >
                            <DaysSection value={days} onChange={handleDaysChange} />
                        </Accordion>

                        <Accordion
                            id="family"
                            title="Кто будет есть?"
                            description={
                                users.length > 0
                                    ? `${users.length} человек`
                                    : 'Не указаны'
                            }
                            icon={<img src="/images/family.svg" alt="семья" />}
                            isOpen={openSection === 'family'}
                            onToggle={() => setOpenSection(openSection === 'family' ? '' : 'family')}
                        >
                            <FamilySection
                                users={users}
                                availableTags={categories}
                                onChange={handleUsersChange}
                            />
                        </Accordion>

                        <Accordion
                            id="preferences"
                            title="Предпочтения"
                            description={
                                selectedCategories.length > 0
                                    ? `Выбраны ${selectedCategories.length}`
                                    : 'Не указаны'
                            }
                            isHighlighted={selectedCategories.length > 0}
                            isOpen={openSection === 'preferences'}
                            onToggle={() => setOpenSection(openSection === 'preferences' ? '' : 'preferences')}
                        >
                            <CategoriesSection
                                categories={categories}
                                selectedCategories={selectedCategories}
                                onLocalChange={handleCategoriesChange}
                                onSaved={() => undefined}
                            />
                        </Accordion>
                    </SettingsPanel>
                </RightColumn>
            </Container>
        );
    }, [
        categories,
        days,
        handleCategoriesChange,
        handleDaysChange,
        handleUsersChange,
        initialData,
        isCartComplete,
        isCartLoading,
        openSection,
        products,
        selectedCategories.length,
        users,
    ]);

    return (
        <>
            {pageContent}
            <CookiePopup />
        </>
    );
}

const LoadingPage = styled.div`
    min-height: 100vh;
    display: flex;
    align-items: center;
    justify-content: center;
    color: ${({ theme }) => theme.colors.white};
    font-size: 20px;
`;

const Container = styled.main`
    position: relative;
    display: flex;
    width: calc(100% - 40px);
    max-width: 1228px;
    height: 90vh;
    margin: 40px auto 0;
    background: ${({ theme }) => theme.colors.white};
    border-radius: ${({ theme }) => theme.radius.page};
    box-shadow: 0 4px 20px rgba(0, 0, 0, 0.04);
    overflow: hidden;

    @media (max-width: 900px) {
        flex-direction: column;
        height: auto;
        min-height: 90vh;
    }
`;

const Column = styled.section`
    padding: 40px;
    flex: 1;
    width: 50%;
    overflow-y: auto;

    & + & {
        border-left: 1px solid #f0f0f0;
    }

    @media (max-width: 900px) {
        width: 100%;
        padding: 20px;

        & + & {
            border-left: none;
            border-top: 1px solid #f0f0f0;
        }
    }
`;

const LeftColumn = styled(Column)`
    display: flex;
    flex-direction: column;
    height: 100%;
    max-width: 490px;
`;

const RightColumn = styled(Column)``;

const TitleBlock = styled.div`
    margin-bottom: 32px;

    h1 {
        font-size: 32px;
        line-height: 38px;
        font-weight: 700;
        color: ${({ theme }) => theme.colors.darkGreen};
        margin-bottom: 8px;
    }

    p {
        font-size: 16px;
        line-height: 19px;
        color: ${({ theme }) => theme.colors.gray};
        font-weight: 350;
    }
`;

const FilterTitle = styled.div`
    margin-bottom: 40px;

    h2 {
        font-size: 20px;
        line-height: 24px;
        margin-bottom: 8px;
        color: ${({ theme }) => theme.colors.darkGreen};
    }

    p {
        font-size: 16px;
        line-height: 19px;
        color: ${({ theme }) => theme.colors.gray};
        font-weight: 350;
    }
`;

const SettingsPanel = styled.div`
    border: 1px solid ${({ theme }) => theme.colors.border};
    border-radius: 16px;
`;