<template>
    <UiContainer>
        <div class="flex justify-between mb-[25px] sm:mb-[55px] xl:mb-[75px] whitespace-nowrap gap-[100px]">
            <p>CZK cena (na EUR). Kč 25,2380 Kč +0,0030 (+0.01%)</p>
            <p>Cena zlata na trhu. 2 852,1450 € -21,6520 € (-0.75%)</p>
            <p>Cena stříbra na trhu. 28,6500 € -0,1570 € (-0.54%)</p>
            <p>PLN cena (na EUR). zł 4,2550</p>
        </div>
        <div class="flex flex-col gap-10 xl:flex-row">
            <Transition>
                <div v-if="openCategories" class="z-40 block w-full pt-8 xl:w-1/4 xl:pt-36 xl:hidden">
                    <BaseTitle>
                        {{ $t("FrontTranslations", "Categories") }}
                    </BaseTitle>
                    <div class="mt-14">
                        <div class="flex flex-col gap-12">
                            <div>
                                <CategoryTree :data="categoriesList" @change-category="changeCategory($event)"
                                    :active="categoryId" />
                            </div>
                            <div>
                                <p class="mb-8 text-2xl font-extrabold text-black dark:text-white">
                                    {{ $t("FrontTranslations", "Filtered by") }}
                                </p>

                                <div v-for="(item, itemIndex) in filters" :key="itemIndex" class="mb-8 text-white">
                                    <span
                                        class="flex justify-between font-bold text-black cursor-pointer 2xl:pr-24 dark:text-gray"
                                        @click="toggleFeature(item.feature)">
                                        {{ item.feature }}
                                        <span class="w-4 h-4 text-yellow"><i
                                                class="uil uil-angle-down text-2xl font-light cursor-pointer"></i></span>
                                    </span>
                                    <ul v-show="visibleFeatures[item.feature]"
                                        class="flex flex-col gap-8 pl-8 mt-8 text-black dark:text-gray">
                                        <li v-for="filter in item.feature_values" :key="filter.value_id"
                                            class="flex gap-1">
                                            <input :id="`${filter.value_id}`"
                                                :value="`${filter.parent}.${filter.value_id}`" v-model="selectedFilters"
                                                type="checkbox" />
                                            <label :for="`${filter.value_id}`">{{ filter.value }}</label>
                                        </li>
                                    </ul>
                                </div>
                            </div>
                        </div>
                    </div>
                </div>
            </Transition>

            <!-- button to open categories -->
            <div class="xl:hidden flex items-center w-full">
                <button @click="openCategories = !openCategories"
                    class="h-[40px] w-full cursor-pointer rounded-[10px] px-[22px] transition-all sm:h-[50px] md:h-[65px] md:rounded-[15px] md:px-[42px] bg-button text-text-dark group-hover:bg-button-hover">
                    Otevřené kategorie a filtry
                </button>
            </div>

            <!-- categories -->
            <div class="min-w-[250px] hidden xl:block">
                <h1 class="font-bounded leading-[140%] font-bold text-[40px] mb-[55px]">
                    {{ $t("category") }}
                </h1>
                <div class="flex flex-col gap-12">
                    <div>

                        <div v-if="categoriesList.length < 1" class="animate-pulse">
                            <div
                                class="flex items-center justify-between mt-4 text-white rounded-lg cursor-pointer xl:pr-24">
                                <div class="w-32 h-4 bg-gray-200 rounded"></div>
                                <div class="w-4 h-4 bg-gray-200 rounded-full"></div>
                            </div>
                        </div>
                        <CategoryTree :data="categoriesList" @change-category="changeCategory($event)"
                            :active="categoryId" />
                    </div>
                    <div>
                        <p class="mb-10 text-2xl font-extrabold text-black dark:text-white">
                            {{ $t("filtered_by") }}
                        </p>

                        <!-- <div v-if="filters.length < 1" class="mb-8 text-white animate-pulse">
                            <div v-for="i in 5"
                                class="mt-10 flex justify-between font-bold text-black cursor-pointer 2xl:pr-24 dark:text-gray">
                                <div class="w-32 h-4 bg-gray-200 rounded"></div>
                                <div class="w-4 h-4 bg-gray-200 rounded"></div>
                            </div>
                        </div> -->

                        <div v-for="(item, itemIndex) in filters" :key="itemIndex"
                            :class="['mb-[30px] text-white', visibleFeatures[item.feature] && 'border-b border-block pb-[10px]']">
                            <span
                                class="flex justify-between items-center font-bold text-black cursor-pointer dark:text-gray mb-[25px]"
                                @click="toggleFeature(item.feature)">
                                {{ item.feature }}
                                <span :class="[visibleFeatures[item.feature] && 'rotate-180', 'transition-all']"> <i
                                        class="uil uil-angle-down text-3xl text-button font-light cursor-pointer"></i></span>
                            </span>
                            <ul v-show="visibleFeatures[item.feature]"
                                class="flex flex-col gap-5 text-black dark:text-gray">
                                <li v-for="filter in item.feature_values" :key="filter.value_id"
                                    class="flex gap-[10px] cursor-pointer">
                                    <input :id="`${filter.value_id}`" :value="`${filter.parent}.${filter.value_id}`"
                                        v-model="selectedFilters" type="checkbox" />
                                    <label :for="`${filter.value_id}`" class="cursor-pointer">{{ filter.value }}</label>
                                </li>
                            </ul>
                        </div>
                    </div>
                </div>
            </div>

            <div class="w-full space-y-10">

                <!-- pop-up -->
                <div v-if="isInfo"
                    class="w-full xl:w-[70%] mx-auto border-y border-block py-[15px] sm:p-[30px] flex gap-[55px] relative">
                    <UButton @click="closeElement()" size="xl" icon="i-lucide-x" variant="ghost"
                        class="p-0 absolute right-0 top-2 sm:right-2 sm:top-2 cursor-pointer text-button font-light hover:bg-inherit hover:text-button-hover" />

                    <div class="flex flex-col gap-[25px]">
                        <div class="flex flex-col justify-between gap-[25px ]">
                            <h4 class="font-inter text-lg sm:text-[24px] leading-[150%] md:leading-[120%] font-bold">
                                {{ component.section_lang_data.title }}
                            </h4>
                            <p>{{ component.section_lang_data.description }}</p>
                        </div>
                        <img class="max-w-[150px] mx-auto"
                            :src="`/api/files/${component.image_collection}/${component.section_id}/${component.section_img[0]}?thumb=640x0')`"
                            alt="" />
                    </div>
                </div>

                <div v-if="products.length < 1" class="grid gap-12 pt-32 pb-16 md:grid-cols-2 2xl:grid-cols-3">
                    <TheProductSkeleton v-for="index in 6"></TheProductSkeleton>
                </div>

                <!-- products -->
                <div v-else ref="loadingElement"
                    class="xl:grid gap-5 sm:gap-10 grid grid-cols-2 sm:flex sm:flex-wrap justify-center xl:grid-cols-4">
                    <Product v-for="product in products" :key="product.id" :product="product" />
                </div>

                <div v-if="reachedEnd" class="w-full flex justify-center">
                    <p>
                        {{ $t("FrontTranslations", "You reached end of the list.") }}
                    </p>
                </div>
            </div>
        </div>
    </UiContainer>
</template>
<script setup lang="ts">
import { ref } from "vue";
import Product from "./Product.vue";
import type { Feature, ProductType } from "~/types";
import CategoryTree from "./CategoryTree.vue";

defineProps<{ component: Component }>();
type Component = {
    image_collection: string;
    section_id: string;
    section_img: string;
    section_lang_data: {
        title: string;
        description: string
    };
};

const openCategories = ref(false);
const isInfo = ref<boolean>(true);
const selectedFilters = ref<any>([]);
const categoryId = ref<number>(1);
const itemsCount = ref(0);

const loading = ref(false);
const reachedEnd = ref(false);

const loadingElement = ref<HTMLElement | null>(null);

const page = ref(1);
const elems = ref(12);
const maxElements = ref(0);

const products = ref([] as ProductType[]);
async function getProducts() {
    try {
        const res = await fetch(
            `http://127.0.0.1:4000/api/public/products/category/${categoryId.value}?p=${page.value}&elems=${elems.value}`,
            {
                headers: {
                    "Content-Type": "application/json",
                },
            }
        );

        const data = await res.json();

        products.value = data.data.items;
        maxElements.value = data.data.items_count + 1;

    } catch (error) {
        console.error("getProducts error:", error);
    }
}

const filters = ref([] as Feature[]);
async function getCategory() {
    try {
        const res = await fetch(
            `http://127.0.0.1:4000/api/public/products/category/1/classification`,
            {
                headers: {
                    "Content-Type": "application/json",
                },
            }
        );

        const data = await res.json();

        filters.value = data.data as Feature[];
        filters.value.forEach((el) => {
            const parentId = el.feature_id;
            el.feature_values.forEach((el) => {
                el.parent = parentId;
            });
        });

    } catch (error) {
        console.error("getCategory error:", error);
    }
}

const categoriesList = ref([]);
async function getCategoryTree() {
    try {
        const res = await fetch(
            `http://127.0.0.1:4000/api/public/categories/tree`,
            {
                headers: {
                    "Content-Type": "application/json",
                },
            }
        );

        const data = await res.json();
        categoriesList.value = data.data.children;

    } catch (error) {
        console.error("getCategory error:", error);
    }
}


getProducts()
getCategory()
getCategoryTree()

const closeElement = () => {
    isInfo.value = false;
};

onMounted(() => {
    window.addEventListener("scroll", scrollEvent);
});

onUnmounted(() => {
    window.removeEventListener("scroll", scrollEvent);
});

async function scrollEvent(e: Event) {
    let maxScrollY = window.scrollY || document.documentElement.scrollHeight - document.documentElement.clientHeight;

    if (window.scrollY >= maxScrollY - 500 && !reachedEnd.value && !loading.value) {
        loading.value = true;
        await loadMoreProducts();
        loading.value = false;
    }
}

filters.value.forEach((item) => {
    visibleFeatures[item.feature] = false;
});

const visibleFeatures = reactive<any>({});
function toggleFeature(feature: any) {
    if (visibleFeatures.hasOwnProperty(feature)) {
        visibleFeatures[feature] = !visibleFeatures[feature];
    } else {
        visibleFeatures[feature] = true;
    }
}

class FilteredQueryString extends URLSearchParams {
    override append(name: string, value: string): void {
        if (value == null) {
            return;
        }

        super.append(name, value);
    }
}

async function loadMoreProducts() {
    let qParams = new FilteredQueryString();

    page.value = page.value + 1;

    qParams.append("p", `${page.value}`);
    qParams.append("elems", `${elems.value}`);
    qParams.append("features", selectedFilters.value.length > 0 ? selectedFilters.value : null);

    try {
        const res = await fetch(
            `http://127.0.0.1:4000/api/public/products/category/${categoryId.value}?${qParams.toString()}`,
            {
                headers: {
                    "Content-Type": "application/json",
                },
            }
        );

        const data = await res.json();
        maxElements.value = data.data.items_count;

        if (data.data.items) {
            products.value.push(...(data.data.items as ProductType[]));
        } else {
            reachedEnd.value = true;
        }

        if (products.value.length >= maxElements.value) {
            reachedEnd.value = true;
        }

    } catch (error) {
        console.error("getCategory error:", error);
    }
}

const changeCategory = (item: any) => {
    categoryId.value = item.id;
};

watch(selectedFilters, async (newQuestion) => {
    if (newQuestion) {
        page.value = 1;
        reachedEnd.value = false;
        loadingElement.value?.scrollIntoView();

        let qParams = new FilteredQueryString();

        qParams.append("p", `${page.value}`);
        qParams.append("elems", `${elems.value}`);
        qParams.append("features", selectedFilters.value.length > 0 ? selectedFilters.value : null);

        try {
            const res = await fetch(
                `http://127.0.0.1:4000/api/public/products/category/1?${qParams.toString()}`,
                {
                    headers: {
                        "Content-Type": "application/json",
                    },
                }
            );

            const data = await res.json();
            products.value = data.data.items;
            maxElements.value = data.data.items_count;

        } catch (error) {
            console.error("selectedFilters error:", error);
        }
    }
});

watch(categoryId, async (newQuestion) => {
    if (newQuestion) {
        page.value = 1;
        reachedEnd.value = false;
        loadingElement.value?.scrollIntoView();

        let qParams = new FilteredQueryString();

        qParams.append("p", `${page.value}`);
        qParams.append("elems", `${elems.value}`);
        qParams.append("features", selectedFilters.value.length > 0 ? selectedFilters.value : null);

        try {
            const res = await fetch(
                `http://127.0.0.1:4000/api/public/products/category/${categoryId.value}?${qParams.toString()}`,
                {
                    headers: {
                        "Content-Type": "application/json",
                    },
                }
            );

            const data = await res.json();
            products.value = data.data.items;
            maxElements.value = data.data.items_count;

        } catch (error) {
            console.error("getCategory error:", error);
        }
    }
});
</script>

<style scoped>
.v-enter-active,
.v-leave-active {
    transition: opacity 0.5s ease;
}

.v-enter-from,
.v-leave-to {
    opacity: 0;
}
</style>