import styles from "./styles.module.css";
import { useCallback, useEffect, useRef, useState } from "react";
import { UserCallbacks, useApi, useApiCall } from "@/api";
import { useDispatch, useSelector } from "react-redux";
import { actions, selectors } from "@/store";
import { useTranslations } from "@/hooks/translations";
import FullScreenModal from "../FullScreenModal";
import StartBreathModalChild from "../StartBreathModalChild";
import Title from "../Title";
import { useNavigate } from "react-router-dom";
import routes from "@/routes";
import { APNG } from "apng-js";
import Player from "apng-js/types/library/player";

let apngPlayer: Player | null = null;

interface BreathPageProps {
  leoApng: Error | APNG;
}

function BreathPage({ leoApng }: BreathPageProps): JSX.Element {
  const { translate } = useTranslations();
  const [isOpenModal, setIsOpenModal] = useState<boolean>(true);
  const [isShowPreview, setIsShowPreview] = useState<boolean>(true);
  const leoCanvasRef = useRef<HTMLCanvasElement>(null);
  const pageRef = useRef<HTMLElement>(null);
  const api = useApi();
  const dispatch = useDispatch();
  const navigate = useNavigate();
  const homeConfig = useSelector(selectors.selectHome);
  const showNavbarFooter = homeConfig.isShowNavbar;
  const queryTimeOutRef = useRef<NodeJS.Timeout>();

  useEffect(() => {
    return () => {
      if (queryTimeOutRef.current) {
        clearTimeout(queryTimeOutRef.current);
      }
    };
  }, []);

  useEffect(() => {
    if (isOpenModal) return;
    const previewTimeOut = setTimeout(() => {
      setIsShowPreview(false);
      apngPlayer?.play();
    }, 10_000);

    const navigateTimeOut = setTimeout(() => {
      navigate(routes.client.breathResult());
    }, 50_000);

    return () => {
      clearTimeout(navigateTimeOut);
      clearTimeout(previewTimeOut);
    };
  }, [navigate, isOpenModal]);

  useEffect(() => {
    async function getApngPlayer() {
      const context = leoCanvasRef.current?.getContext("2d");
      if (context && !(leoApng instanceof Error)) {
        context.canvas.height = leoApng.height;
        context.canvas.width = leoApng.width;
        const _apngPlayer = await leoApng.getPlayer(context);
        apngPlayer = _apngPlayer;
        if (apngPlayer) {
          apngPlayer.stop();
        }
      }
    }
    getApngPlayer();
  }, [leoApng]);

  const beginBreath = () => {
    setIsOpenModal(false);
  };

  const token = useSelector(selectors.selectToken);
  const createCallback = useCallback(async () => {
    const data: UserCallbacks.PayloadPost = {
      data: {
        user_callback: {
          kind: "breathing_end",
        },
      },
      token,
    };
    const createCallbackRequest = await api.createUserCallbacks(data);
    dispatch(actions.userCallbacks.update(createCallbackRequest.user_callback));
    if (!createCallbackRequest.user_callback.is_complete) {
      const getUserCallbacksRequest = async () => {
        const getCallback = await api.getUserCallbacks({
          id: createCallbackRequest.user_callback.id,
          token,
        });
        if (!getCallback.user_callback.is_complete) {
          queryTimeOutRef.current = setTimeout(getUserCallbacksRequest, 3000);
        }
        dispatch(
          actions.userCallbacks.update({
            description: getCallback.user_callback.description || "Loading...",
          })
        );
        return getCallback.user_callback;
      };
      return await getUserCallbacksRequest();
    }

    return createCallbackRequest.user_callback;
  }, [api, dispatch, token]);

  useApiCall<UserCallbacks.IUserCallbacks>(createCallback);

  const handleCross = () => {
    navigate(routes.client.breathResult());
  };

  return (
    <>
      <section
        className={`${styles.page} page`}
        ref={pageRef}
        style={{ paddingBottom: showNavbarFooter ? "48px" : "16px" }}
      >
        {!showNavbarFooter && (
          <div className={styles.cross} onClick={handleCross}></div>
        )}
        <canvas
          style={{ display: isOpenModal ? "hidden" : "block" }}
          className={`${styles["leo-apng"]} ${
            !isOpenModal && isShowPreview ? styles.leo : ""
          }`}
          ref={leoCanvasRef}
        ></canvas>
        {!isOpenModal && isShowPreview && (
          <div className={styles.preview}>
            <Title
              variant="h2"
              className={`${styles.text} ${styles["breath-relax"]}`}
            >
              {translate("aura.breath_relax.text")}
            </Title>
          </div>
        )}
        <FullScreenModal isOpen={isOpenModal}>
          <StartBreathModalChild
            handleBegin={beginBreath}
            isShowNavbar={showNavbarFooter}
          />
        </FullScreenModal>
        {!isOpenModal && !isShowPreview && (
          <div className={styles["text-container"]}>
            <Title
              variant="h2"
              className={`${styles.text} ${styles["breath-in"]}`}
            >
              {translate("breathIn")}
            </Title>
            <Title
              variant="h2"
              className={`${styles.text} ${styles["breath-out"]}`}
            >
              {translate("breathOut")}
            </Title>
          </div>
        )}
      </section>
    </>
  );
}

export default BreathPage;
