import React, { useEffect, useState } from "react";
import * as FileSystem from "expo-file-system";
import NetInfo from "@react-native-community/netinfo";
import useAuthStore from "@/store/auth";
import { ArchivedFormat } from "@linkwarden/types";
import { Link as LinkType } from "@linkwarden/prisma/client";
import WebView from "react-native-webview";
import { Image, Platform, ScrollView } from "react-native";

type Props = {
  link: LinkType;
  setIsLoading: (state: boolean) => void;
  format: ArchivedFormat.png | ArchivedFormat.jpeg;
};

export default function ImageFormat({ link, setIsLoading, format }: Props) {
  const FORMAT = format;

  const extension = format === ArchivedFormat.png ? "png" : "jpeg";

  const { auth } = useAuthStore();
  const [content, setContent] = useState<string>("");
  const [dimension, setDimension] = useState<{
    width: number;
    height: number;
  }>();

  useEffect(() => {
    if (content)
      Image.getSize(content, (width, height) => {
        setDimension({ width, height });
      });
  }, [content]);

  useEffect(() => {
    async function loadCacheOrFetch() {
      const filePath =
        FileSystem.documentDirectory +
        `archivedData/${extension}/link_${link.id}.${extension}`;

      await FileSystem.makeDirectoryAsync(
        filePath.substring(0, filePath.lastIndexOf("/")),
        {
          intermediates: true,
        }
      ).catch(() => {});

      const [info] = await Promise.all([FileSystem.getInfoAsync(filePath)]);

      if (info.exists) {
        setContent(filePath);
      }

      const net = await NetInfo.fetch();

      if (net.isConnected) {
        const apiUrl = `${auth.instance}/api/v1/archives/${link.id}?format=${FORMAT}`;

        try {
          const result = await FileSystem.downloadAsync(apiUrl, filePath, {
            headers: { Authorization: `Bearer ${auth.session}` },
          });

          setContent(result.uri);
        } catch (e) {
          console.error("Failed to fetch content", e);
        }
      }
    }

    loadCacheOrFetch();
  }, [link]);

  if (Platform.OS === "ios")
    return (
      content &&
      dimension && (
        <ScrollView maximumZoomScale={10}>
          <Image
            source={{ uri: content }}
            onLoadEnd={() => setIsLoading(false)}
            style={{
              width: "100%",
              height: "auto",
              aspectRatio: dimension.width / dimension.height,
            }}
            resizeMode="contain"
          />
        </ScrollView>
      )
    );
  else
    return (
      content && (
        <WebView
          style={{
            flex: 1,
          }}
          source={{
            baseUrl: content,
            html: `
            <!DOCTYPE html>
            <html>
              <head>
                <style>
                  body {
                    margin: 0;
                    padding: 0;
                    display: flex;
                    justify-content: center;
                    align-items: center;
                  }
                  img {
                    max-width: 100%;
                    height: auto;
                  }
                </style>
              </head>
              <body>
                <img src="${content}" />
              </body>
            </html>
          `,
          }}
          scalesPageToFit
          originWhitelist={["*"]}
          mixedContentMode="always"
          javaScriptEnabled={true}
          allowFileAccess={true}
          allowFileAccessFromFileURLs={true}
          allowUniversalAccessFromFileURLs={true}
          onLoadEnd={() => setIsLoading(false)}
        />
      )
    );
}
