import { useMemo, useRef, useState } from 'react';
import { useInfiniteQuery } from 'react-query';
import { useOutletContext } from 'react-router-dom';

import { IconInfoCircle } from '@material-hu/icons/tabler';

import StateCard from '@material-hu/components/design-system/StateCard';

import Stack from '@material-hu/mui/Stack';
import { tableContainerClasses } from '@material-hu/mui/TableContainer';

import CommentsTableList from '@material-hu/components/composed-components/peopleExperience/npsResults/components/CommentsTableList';

import { FilterOption } from '@material-hu/components/composed-components/peopleExperience/npsResults/components/CommentsTableList/types';
import { pxKeys } from '../../../../../../queries';
import { getQuestionAnswers } from '../../../../../../services';
import {
  IntegerAnswer,
  QuestionAnswersParams,
  QuestionTemplateType,
  SegmentationFilterParams,
  TransformedManagerSurvey,
} from '../../../../../../types';
import { useLokaliseTranslation } from 'src/utils/i18n';

import { getIntegerAnswerByFilter } from './utils';

const CommentList = () => {
  const { t } = useLokaliseTranslation('people_experience');

  const { survey, filters } = useOutletContext<{
    survey: TransformedManagerSurvey;
    filters: SegmentationFilterParams;
  }>();

  const [selectedFilter, setSelectedFilter] = useState<FilterOption>(
    FilterOption.ALL,
  );
  const containerRef = useRef<HTMLDivElement>(null);

  const questionId = survey.templates
    .flatMap(template => template.formTemplate.questionTemplates)
    .find(q => q.type === QuestionTemplateType.NPS)?.id;

  const params: Omit<QuestionAnswersParams, 'page'> & IntegerAnswer = {
    formId: survey.id,
    questionId: questionId!,
    isHighlighted: undefined,
    hasComment: true,
    limit: 10,
    integerAnswer: getIntegerAnswerByFilter(selectedFilter),
    ...filters,
  };

  const { data, isLoading, fetchNextPage, isFetchingNextPage } =
    useInfiniteQuery(
      pxKeys.infiniteQuestionAnswers(params as QuestionAnswersParams),
      ({ pageParam = 1 }) =>
        getQuestionAnswers({
          ...params,
          page: pageParam,
        } as QuestionAnswersParams),
      {
        select: response => ({
          pages: response.pages.map(page => page.data),
          pageParams: response.pageParams,
        }),
        enabled: !!questionId,
        getNextPageParam: lastPage => {
          return lastPage.data.page === lastPage.data.totalPages
            ? undefined
            : lastPage.data.page + 1;
        },
      },
    );

  const comments = useMemo(
    () =>
      data?.pages.flatMap(page =>
        page.items.map(answer => ({
          score: answer.answer.integer,
          comment: answer.comment,
        })),
      ) ?? [],
    [data?.pages],
  );

  const totalCount = data?.pages[0]?.count ?? 0;
  const loadedCount = comments.length;

  const handleScrollToTop = () => {
    containerRef.current?.scrollIntoView({ behavior: 'smooth' });
  };

  return (
    <Stack ref={containerRef}>
      <CommentsTableList
        title={t('comment.comments')}
        columnHeadings={{
          score: t('score'),
          comment: t('comment.comment'),
        }}
        filterLabels={{
          [FilterOption.ALL]: {
            label: t('comment.all'),
            description: t('comment_count', { count: totalCount }),
          },
          [FilterOption.PROMOTERS]: {
            label: t('promoters'),
            description: t('comment_count', { count: totalCount }),
          },
          [FilterOption.NEUTRALS]: {
            label: t('neutrals'),
            description: t('comment_count', { count: totalCount }),
          },
          [FilterOption.DETRACTORS]: {
            label: t('detractors'),
            description: t('comment_count', { count: totalCount }),
          },
        }}
        selectedFilter={selectedFilter}
        onFilterChange={setSelectedFilter}
        data={comments}
        loading={isLoading}
        loadingMore={isFetchingNextPage}
        loadedCount={loadedCount}
        totalCount={totalCount}
        onLoadMore={fetchNextPage}
        onScrollToTop={handleScrollToTop}
        emptyStateSlot={
          <StateCard
            title={t('not_enough_data_title')}
            description={t('not_enough_data_description')}
            icon={IconInfoCircle}
            variant="primary"
          />
        }
        slotProps={{
          tableWrapper: {
            sx: {
              maxHeight: 600,
              [`& .${tableContainerClasses.root}`]: {
                flex: '1 0 auto',
                boxSizing: 'border-box',
              },
            },
          },
        }}
      />
    </Stack>
  );
};

export default CommentList;
