import React, {
  useRef,
  useCallback,
  forwardRef,
  useImperativeHandle,
  useEffect,
  useState,
} from 'react';
import {View, FlatList, ListRenderItem} from 'react-native';
import {useTranslation} from 'react-i18next';
import {StackActions, useNavigation} from '@react-navigation/native';
import {
  MarginKeyboardAwareView,
  Spinner,
  Typography,
  CommentSkeleton,
  RefreshControl,
  AddComment,
  AddCommentRefType,
} from '@components';
import {PublishCommentData} from '@components/AddComment/interfaces';
import {Comment as CommentType} from '@interfaces/comments';
import {Reaction} from '@interfaces/reaction';
import {User} from '@interfaces/user';
import {ModalAction} from '@modules/app/redux';
import {styles} from '@modules/post/screens/CommentDetailRefactored/styles';
import FeedCommentItem from '@modules/post/components/FeedCommentItem';
import {useUserId} from '@redux/selectors';
import {getCompleteName, isIos} from '@shared/utils';
import {Screens} from '@shared/constants';
import {useTheme} from '@shared/theme';

const keyExtractor = (item: number) => `${item}`;
interface Props {
  commentIds: number[];
  canComment: boolean;
  postId: number;
  parentId: number;
  onToggleSelectNewReaction: ({comment}: {comment: CommentType}) => ModalAction;
  onReactionPress: ({
    reaction,
    commentId,
    reactions,
    parentId,
  }: {
    reaction: string;
    commentId: number;
    parentId?: number;
    reactions: Reaction[];
  }) => void;
  isLoading: boolean;
  user: Pick<User, 'firstName' | 'lastName'>;
  isLoadingNextPage?: boolean;
  isReplying?: boolean;
  groupId?: number;
  canInteract?: boolean;
  onRefresh: () => void;
  getNextPage: () => void;
  isAddingNewComment?: boolean;
  handlePublishComment: (
    data: PublishCommentData,
  ) => Promise<CommentType> | undefined;
}

const CommentDetail = forwardRef<FlatList, Props>(function CommentDetail(
  {
    commentIds = [],
    getNextPage,
    canComment,
    postId,
    parentId,
    user,
    onToggleSelectNewReaction,
    onReactionPress,
    isLoading,
    isLoadingNextPage,
    isReplying,
    groupId,
    canInteract,
    onRefresh,
    handlePublishComment,
    isAddingNewComment,
  }: Props,
  ref,
) {
  const [showAddComment, setShowAddComment] = useState(false);

  const {t} = useTranslation();
  const {theme} = useTheme();
  const navigation = useNavigation();
  const addCommentRef = useRef<AddCommentRefType>(null);
  const flatListRef = useRef<FlatList>(null);
  const userId = useUserId();

  useEffect(() => {
    const timeout = setTimeout(() => {
      setShowAddComment(true);
    }, 300);
    return () => clearTimeout(timeout);
  }, []);
  useImperativeHandle(ref, () => flatListRef.current as FlatList);

  const onTagPress = useCallback(
    (targetId: number) => {
      navigation.dispatch(
        StackActions.push(Screens.PROFILE, {userId: targetId}),
      );
    },
    [navigation],
  );

  const onReplyPress = useCallback(() => {
    addCommentRef.current?.focus();
  }, [addCommentRef]);

  const onCommentReplyPress = useCallback(
    (index: number) => (item: CommentType) => {
      flatListRef.current?.scrollToIndex({index, animated: true});
      addCommentRef.current?.initiateTag(
        item.user.id,
        getCompleteName(item.user),
      );
    },
    [addCommentRef],
  );

  const renderComment: ListRenderItem<number> = useCallback(
    ({item, index}: {item: number; index: number}) => (
      <FeedCommentItem
        postId={postId}
        parentId={parentId}
        commentId={item}
        isReply
        onTagPress={onTagPress}
        onReactionPress={onReactionPress}
        onToggleSelectNewReaction={onToggleSelectNewReaction}
        onReply={onCommentReplyPress(index)}
        userId={userId}
      />
    ),
    [
      postId,
      parentId,
      onTagPress,
      onReactionPress,
      onToggleSelectNewReaction,
      onCommentReplyPress,
      userId,
    ],
  );

  return (
    <View
      style={[
        styles.commentDetailContainer,
        {backgroundColor: theme.background.elements.grey},
      ]}>
      <View style={styles.container}>
        <Typography weight="semiBold" color={theme.text.neutral.default}>
          {t('post.responses_to')}{' '}
          <Typography weight="semiBold" color={theme.text.neutral.default}>
            {getCompleteName(user)}
          </Typography>
        </Typography>
      </View>
      <MarginKeyboardAwareView>
        <FlatList
          keyboardDismissMode={isIos ? 'interactive' : 'on-drag'}
          style={[
            styles.listContainer,
            {backgroundColor: theme.background.elements.default},
          ]}
          data={commentIds}
          ListHeaderComponent={
            <FeedCommentItem
              postId={postId}
              groupId={groupId}
              commentId={parentId}
              onTagPress={onTagPress}
              onReactionPress={onReactionPress}
              onToggleSelectNewReaction={onToggleSelectNewReaction}
              onReply={onReplyPress}
              userId={userId}
              isReply={false}
            />
          }
          keyExtractor={keyExtractor}
          ref={flatListRef}
          showsVerticalScrollIndicator={false}
          refreshControl={
            <RefreshControl refreshing={isLoading} onRefresh={onRefresh} />
          }
          renderItem={renderComment}
          onEndReached={getNextPage}
          ListFooterComponent={
            <View style={styles.footerContainer}>
              {isAddingNewComment && (
                <View style={styles.skeletonContainer}>
                  <CommentSkeleton />
                </View>
              )}
              {isLoadingNextPage && <Spinner />}
            </View>
          }
        />
      </MarginKeyboardAwareView>
      {canInteract && canComment && showAddComment && (
        <AddComment
          keyProp="comment-screen-add-comment"
          autoFocus={isReplying}
          onPublishComment={handlePublishComment}
          ref={addCommentRef}
        />
      )}
    </View>
  );
});

export default CommentDetail;
