/* eslint-disable react-hooks/rules-of-hooks */
import React, {useEffect, useState} from 'react';
import {StyleSheet, View} from 'react-native';
import {Meta, StoryObj} from '@storybook/react';
import {IconUser} from '@tabler/icons-react-native';
import {SPACING} from '@shared/theme';

import {Pill} from '../Pill';
import {List, ListItem, ListItemProps, ListSkeleton} from './index';

type StoryComponent = ListItemProps & {withAvatar: boolean};

interface ListMock {
  id: number;
  title: string;
  description: string;
}

const LIST_MOCK: ListMock[] = Array.from({length: 30}, (_, index) => ({
  id: index + 1,
  title: `Item nro ${index + 1}`,
  description: '25/03/2025 • Description',
}));

const ITEM_PER_PAGE = 10;

const styles = StyleSheet.create({
  decorator: {margin: -SPACING.x2},
  list: {paddingVertical: SPACING.x2, paddingBottom: SPACING.x2},
});

const getList = (offset = ITEM_PER_PAGE) => {
  return new Promise<ListMock[]>(res => {
    setTimeout(() => {
      res(LIST_MOCK.slice(0, offset));
    }, 1000);
  });
};

const meta: Meta<StoryComponent> = {
  title: 'HuGo/List',
};

export const ListItemComponent: StoryObj<StoryComponent> = {
  argTypes: {
    title: {control: 'text'},
    description: {control: 'text'},
    topText: {control: 'text'},
    withAvatar: {control: 'boolean'},
    withRightIcon: {control: 'boolean'},
  },
  args: {
    title: 'Title',
    description: 'Description',
    topText: 'Top Text',
    withAvatar: true,
    withRightIcon: true,
  },
  render: ({withAvatar, ...args}) => (
    <ListItem {...args} avatar={withAvatar ? {Icon: IconUser} : undefined} />
  ),
};

export const ListComponent: StoryObj = {
  argTypes: {
    presentation: {control: 'radio', options: ['card', 'flat']},
    paginationType: {
      control: 'radio',
      options: ['button', 'infiniteScroll', 'none'],
    },
    fetchingNextPageLoader: {
      control: 'radio',
      options: ['spinner', 'skeleton'],
    },
  },
  args: {
    presentation: 'card',
    paginationType: 'button',
    fetchingNextPageLoader: 'spinner',
  },
  decorators: Story => (
    <View style={styles.decorator}>
      <Story />
    </View>
  ),
  render: ({presentation, paginationType, fetchingNextPageLoader}: any) => {
    const [isLoading, setIsLoading] = useState(true);
    const [isRefreshing, setIsRefreshing] = useState(false);
    const [isFetchingNextPage, setIsFetchingNextPage] = useState(false);
    const [data, setData] = useState<ListMock[]>();
    const [offset, setOffset] = useState(ITEM_PER_PAGE);

    const onNextPage = async () => {
      setIsFetchingNextPage(true);
      const nextOffset = offset + ITEM_PER_PAGE;
      const response = await getList(nextOffset);
      setData(response);
      setOffset(nextOffset);
      setIsFetchingNextPage(false);
    };

    const onRefresh = async () => {
      setIsRefreshing(true);
      const response = await getList(offset);
      setData(response);
      setIsRefreshing(false);
    };

    useEffect(() => {
      getList().then(response => {
        setIsLoading(false);
        setData(response);
      });
    }, []);

    return (
      <List
        data={data}
        withDivider
        isLoading={isLoading}
        isFetchingNextPage={isFetchingNextPage}
        isRefreshing={isRefreshing}
        hasNextPage={offset < LIST_MOCK.length}
        onNextPage={onNextPage}
        onRefresh={onRefresh}
        renderItem={({item, index}) => (
          <ListItem
            title={item.title}
            avatar={{Icon: IconUser}}
            description={item.description}
            presentation={presentation}
            isFirstItem={index === 0}
            isLastItem={index === data!.length - 1}
            withRightIcon>
            <Pill variant="info" text="Information" size="sm" />
          </ListItem>
        )}
        style={styles.list}
        presentation={presentation}
        paginationType={paginationType}
        FetchingNextPageLoader={
          fetchingNextPageLoader === 'skeleton' ? (
            <ListSkeleton presentation="flat" />
          ) : undefined
        }
      />
    );
  },
};

export default meta;
