import { FC, useState, useEffect, useRef, useMemo } from 'react';

import Box from '@material-hu/mui/Box';
import CircularProgress from '@material-hu/mui/CircularProgress';

import { Document } from 'src/config/react-pdf';

import { usePdfDimensions } from 'src/hooks/usePdfDimensions';
import { Attachment } from 'src/types/attachments';

import DialogFilePreview from 'src/components/attachment/DialogFilePreview';
import PdfPageWithObserver from 'src/components/attachment/PdfPageWithObserver';
import { Header, ToolContainer } from 'src/components/attachment/preview';

export type PdfViewerProps = {
  file: Attachment;
  onClose: () => void;
  showHeader?: boolean;
  downloadFile?: boolean;
  onDownload?: (file) => void;
};

export const PdfViewer: FC<PdfViewerProps> = props => {
  const {
    file,
    onClose,
    showHeader = true,
    downloadFile = false,
    onDownload = () => null,
  } = props;

  const [numPages, setNumPages] = useState(null);
  const [pageNumber, setPageNumber] = useState(1);
  const [isLoading, setIsLoading] = useState(true);
  const [zoomValue, setZoomValue] = useState(1);
  const [showButtons, setShowButtons] = useState(true);

  const {
    ref: documentRef,
    dimensions: pageDimensions,
    handleLoadPage,
  } = usePdfDimensions();

  const timerRef = useRef(null);

  const handleResetTimeout = () => {
    setShowButtons(true);
    clearTimeout(timerRef.current);
    timerRef.current = setTimeout(() => setShowButtons(false), 3000);
  };

  useEffect(() => {
    setNumPages(null);
    setPageNumber(1);
    setZoomValue(1);
  }, [file]);

  useEffect(() => {
    window.addEventListener('mousemove', handleResetTimeout);

    return () => {
      window.removeEventListener('mousemove', handleResetTimeout);
      clearTimeout(timerRef.current);
    };
  }, []);

  const onDocumentLoadSuccess = ({ numPages: newNumPages }) => {
    setNumPages(newNumPages);
    setIsLoading(false);
  };

  const handleZoomValue = newZoomValue => setZoomValue(newZoomValue);

  const handleOnClose = () => {
    setPageNumber(1);
    setZoomValue(1);
    onClose();
  };

  const handleUpdatePageNumber = newPageNumber => {
    handleResetTimeout();
    setPageNumber(newPageNumber);
  };

  const dialogContentRef = useRef(null);

  const handleClickOutside = event => {
    if (dialogContentRef.current && event.target.nodeName !== 'CANVAS') {
      handleOnClose();
    }
  };

  const isSecureUrl = useMemo(
    () => file?.url.startsWith('https://secure-files'),
    [file],
  );

  const pdfFile = useMemo(() => {
    return isSecureUrl
      ? {
          url: file.url,
          withCredentials: true,
          crossOrigin: 'use-credentials',
        }
      : file.url;
  }, [file, isSecureUrl]);

  return (
    <DialogFilePreview
      open
      onClose={handleOnClose}
      onClick={handleClickOutside}
      ref={dialogContentRef}
      maxWidth="lg"
    >
      {!isLoading && showHeader && (
        <Header
          downloadFile={downloadFile}
          onDownload={onDownload}
          file={file}
          fileSource={file?.url}
          onClose={handleOnClose}
        />
      )}
      <Box
        ref={documentRef}
        sx={{
          width: '100%',
          height: '100vh',
          display: 'flex',
          justifyContent: 'center',
          alignItems: 'center',
          '& .react-pdf__Document': {
            width: '100%',
            maxWidth: '594px',
          },
        }}
      >
        <Document
          file={pdfFile}
          onLoadSuccess={onDocumentLoadSuccess}
          inputRef={documentRef}
          loading={
            <Box sx={{ textAlign: 'center' }}>
              <CircularProgress color="primary" />
            </Box>
          }
          externalLinkTarget="_blank"
        >
          {Array.from(new Array(numPages), (el, index) => (
            <PdfPageWithObserver
              key={index}
              index={index}
              zoomValue={zoomValue}
              onUpdatePageNumber={handleUpdatePageNumber}
              onLoadSuccess={handleLoadPage}
              dimensions={pageDimensions}
            />
          ))}
        </Document>
      </Box>
      {showButtons && (
        <ToolContainer
          onLoadMedia={!isLoading}
          pageNumber={pageNumber}
          totalPages={numPages}
          zoomValue={zoomValue}
          onZoom={handleZoomValue}
          isPdf
        />
      )}
    </DialogFilePreview>
  );
};

export default PdfViewer;
