import LoaderSun from "@/components/common/Loader/LoaderSun";
import FileRenderer from "@/components/FileRenderer";
import Button from "@/components/Forms/Button";
import Input from "@/components/Forms/Input";
import InputSelectComponent from "@/components/Forms/InputSelect";
import {
  baixarAwsBase64,
  baixarAwsContent,
} from "@/requests/common/Aws/baixarAws";
import { obterAgendamentoInstalacaoNegocio } from "@/requests/CRM/AgendamentosInstalacoes/obterAgendamentoInstalacaoNegocio";
import { obterAgendamentoManutencao } from "@/requests/CRM/AgendamentosManutencoes/obterAgendamentoManutencao";
import { obterTemplateContrato } from "@/requests/CRM/Contrato/obterTemplateContrato";
import { listarResponsabilidadesFinanceiras } from "@/requests/CRUD/ResponsabilidadesFinanceiras/listarResponsabilidadesFinanceiras";
import { useAuth } from "@/src/contexts/authContext";
import { useKanbanContext } from "@/src/contexts/kanbanContext";
import { getDateBrasil, GetForm, GetGallery, handleDownload } from "@/utils";
import { Dispatch, useEffect, useState } from "react";
import { FieldValues } from "react-hook-form";
import { FaPaperclip } from "react-icons/fa";
import { MdClose } from "react-icons/md";
import FormTemplateGeracaoOS from "./FormTemplateGeracaoOS";

const FormGeracaoOS = ({
  onSubmitFunction,
  dadosCard,
  children,
  usuarios,

  defaultValues,
  dadosCliente,
  proposta,

  contrato,
  reloadOrdensServico,
  buscaPropostas,
  compareActiveStep,
  setActiveStepAtual,
  activeStep,
  stepsTemp,
  setDadosNegocio,

  ordensServico,
  botoes,
  lojas,
  tipoServicoName,
  ...rest
}: {
  [x: string]: any;
  setActiveStepAtual: Dispatch<any>;
}) => {
  const [agendamento, setAgendamento] = useState<any>();
  const [responsabilidaesFinanceiras, setResponsabilidaesFinanceiras] =
    useState<any[]>([]);
  const [isLoaded, setIsLoaded] = useState(false);

  const [anexos, setAnexos] = useState<File[]>(false || []);
  const [imageUrls, setImageUrls] = useState<string[]>([]);
  const [isLoadingAnexos, setIsLoadingAnexos] = useState(false);
  const [inputKey, setInputKey] = useState(1);
  const [templateOS, setTemplateOS] = useState("");
  const [isLoadingTemplateOS, setIsLoadingTemplateOS] = useState(true);
  const [dataFormGeracaoOS, setDataFormGeracaoOS] = useState<any>();
  const [step, setStep] = useState(0);

  const [isLoading, setIsLoading] = useState<any[] | undefined>(undefined);

  const [responsabilidaeFinanceira, setResponsabilidaeFinanceira] =
    useState<any>();

  const { handleSubmit, ...form } = GetForm();
  const { openGallery, setGallery } = GetGallery();
  const { valuesSession } = useAuth();
  const { session } = valuesSession();
  const { reListarDadosKanban } = useKanbanContext();

  const onSubmitFormGeracaoOS = (data: FieldValues) => {
    setDataFormGeracaoOS({
      ...data,
      data_servico_pvos: agendamento?.[`data_${tipoServicoName}`],
      // datafinal_servico_pvos: agendamento?.data_final_manutencao_formatada,
      // datafinal_servico_pvos: {
      //   query: `DATE_ADD('${agendamento?.data_manutencao}', INTERVAL ${agendamento?.dias_manutencao} DAY)`,
      // },
      anexos,
      terceiro_pvos:
        responsabilidaeFinanceira?.is_terceiro_respfin == "1"
          ? data?.terceiro_pvos
          : "0",
      codExecutor_pvos: agendamento?.[`instaladores_${tipoServicoName}`] || "0",
      codExecucao_pvos:
        agendamento?.instaladores?.length > 0 &&
        [null, 0, "0"].includes(
          agendamento?.instaladores[0]?.is_externo_usuario
        )
          ? "2"
          : "1",
      // ...agendamento?.instaladores?.[0],
      // ...(usuarios?.find(
      //   (usuario: any) => usuario?.id_usuario == data?.codExecutor_pvos
      // ) || {}),
    });
    setStep(1);
    // return onSubmitFunction(data);
  };

  const adicionarAnexo = (event: any) => {
    const inputElement = event.target as HTMLInputElement;

    // if (inputElement.files && inputElement.files.length > 0) {
    //   let arquivo = inputElement.files[0];
    //   setAnexos((prev) => {
    //     if (prev.some((anexo) => anexo.name == arquivo.name)) {
    //       let nomeArquivo = arquivo.name;
    //       let extensao = nomeArquivo.substring(nomeArquivo.lastIndexOf("."));
    //       let nomeBase = nomeArquivo.substring(0, nomeArquivo.lastIndexOf("."));

    //       let contador = 0;
    //       let novoNome = nomeArquivo;
    //       while (anexos.some((anexo) => anexo.name === novoNome)) {
    //         novoNome = `${nomeBase} (${++contador})${extensao}`;
    //       }
    //       arquivo = new File([arquivo], novoNome, {
    //         type: arquivo.type,
    //         lastModified: arquivo.lastModified,
    //       });
    //     }

    //     return [...prev, arquivo];
    //   });

    //   setInputKey(inputKey + 1);
    // }
    if (inputElement.files && inputElement.files.length > 0) {
      let arquivo = inputElement.files[0];
      setAnexos((prev) => {
        // if (prev.some((anexo) => anexo.name == arquivo.name)) {
        let nomeArquivo = arquivo.name?.replaceAll("/", "_");
        let extensao = nomeArquivo.substring(nomeArquivo.lastIndexOf("."));
        let nomeBase = nomeArquivo.substring(0, nomeArquivo.lastIndexOf("."));

        let contador = 0;
        let novoNome = nomeArquivo;
        while (prev.some((anexo) => anexo.name === novoNome)) {
          novoNome = `${nomeBase} (${++contador})${extensao}`;
        }
        arquivo = new File([arquivo], novoNome, {
          type: arquivo.type,
          lastModified: arquivo.lastModified,
        });
        // }

        return [...prev, arquivo];
      });

      setInputKey(inputKey + 1);
    }
  };

  useEffect(() => {
    if (!agendamento) {
      Promise.all([
        (tipoServicoName == "instalacao"
          ? obterAgendamentoInstalacaoNegocio
          : obterAgendamentoManutencao)(dadosCard.id_coleta_cliente).then(
          (res) => {
            const [year, month, day] = res?.[`data_${tipoServicoName}`]
              .split("-")
              .map(Number);
            const data = new Date(year, month - 1, day);

            // const dataFormat = format(data, "dd/MM/yyyy");
            const dataFormat = getDateBrasil(undefined, data);
            data.setDate(data.getDate() + Number(res?.[`dias_${tipoServicoName}`]));
            const dataFinal = getDateBrasil(undefined, data);
            setAgendamento({
              ...res,
              [`data_${tipoServicoName}_formatada`]: dataFormat,
              [`data_final_${tipoServicoName}_formatada`]: dataFinal,
            });
          }
        ),
        listarResponsabilidadesFinanceiras().then((res) =>
          setResponsabilidaesFinanceiras(res)
        ),
      ]).finally(() => setIsLoaded(true));
    } else {
      setIsLoaded(true);
    }

    if (defaultValues && defaultValues["anexos_data"]) {
      const anexos_data = defaultValues["anexos_data"];

      setIsLoadingAnexos(true);
      Promise.all(
        anexos_data.map((data: any) =>
          baixarAwsBase64(data["caminho_chamado_anexo"]).then((res) => {
            const resultObject =
              typeof res === "string" ? JSON.parse(res) : res;
            const base64Content = resultObject.base64;

            const byteCharacters = atob(base64Content);
            const byteNumbers = new Array(byteCharacters.length);
            for (let i = 0; i < byteCharacters.length; i++) {
              byteNumbers[i] = byteCharacters.charCodeAt(i);
            }
            const byteArray = new Uint8Array(byteNumbers);
            const blob = new Blob([byteArray], {
              type: "application/octet-stream",
            });

            const fileName = data["caminho_chamado_anexo"].split("/").pop();
            const file = new File([blob], fileName, { type: blob.type });
            return file;
          })
        )
      )
        .then((res) => {
          setAnexos(res);
        })
        .finally(() => setIsLoadingAnexos(false));
    }

    obterTemplateContrato({
      id_tipo_negocio: dadosCard.tipoNegocio_coleta,
      id_loja: dadosCard.id_loja_coleta,
    })
      .then((res) =>
        baixarAwsContent(res?.caminho_templateOS_loja).then((templateString) =>
          setTemplateOS(templateString)
        )
      )
      .finally(() => {
        setIsLoadingTemplateOS(false);
      });
  }, []);

  useEffect(() => {
    setInputKey(inputKey + 1);
    const loadImages = async () => {
      const newImageUrls = await Promise.all(
        anexos.map(async (anexo) => {
          const reader = new FileReader();
          return new Promise((resolve) => {
            reader.onload = () => resolve(reader.result as string);
            reader.readAsDataURL(anexo);
          }).catch(() => {});
        })
      );
      setImageUrls(newImageUrls as string[]);
      setGallery(
        newImageUrls.map((newImageUrl, index) => ({
          src: newImageUrl as string,
          name: anexos[index].name?.split("/").pop()!,
        }))
      );
      // setSchecklistValidacaoEngenharia((prev: any[]) => {
      //   const newItens = [...prev];
      //   newItens.splice(indexItem, 1, {
      //     ...itemValidacao,
      //     anexos,
      //     caminhos_anexos: anexos.map((anexo: File) => ({
      //       caminho_anexo_item_checklist_engenharia_negocio: `clientes/${dadosCard.cliente?.pasta_cliente}/${dadosCard.id_coleta_cliente}/CompraMaterial/${anexo.name}`,
      //     })),
      //   });

      //   return newItens;
      // });
    };

    loadImages();
  }, [anexos]);

  return isLoaded ? (
    step === 0 ? (
      <form
        onSubmit={handleSubmit(onSubmitFormGeracaoOS)}
        className="flex flex-col gap-5"
        {...rest}
        key={form?.key}
      >
        <div
          className="flex flex-row flex-wrap justify-center gap-3"
        >
          <div>
            <div className="flex flex-row justify-center">Instalador</div>
            <div
              className="font-semibold"
            >
              {agendamento?.instaladores?.[0]?.nome_usuario}
            </div>
          </div>
          <div>
            <div className="flex flex-row justify-center">Data Inicial</div>
            <div className="font-semibold">
              {agendamento?.[`data_${tipoServicoName}_formatada`]}
            </div>
          </div>
          <div>
            <div className="flex flex-row justify-center">Data Final</div>
            <div className="font-semibold">
              {agendamento?.[`data_final_${tipoServicoName}_formatada`]}
            </div>
          </div>
        </div>
        <div className="flex flex-row flex-wrap gap-3">
          <Input
            name="qtdModulos_pvos"
            label="Quantidade de Módulos"
            mascara="numerico"
            formulario={form}
            width={"flex-1"}
            required
            error={"Preencha a Quantidade de Módulos"}
            defaultValue={
              Number(dadosCard?.qtdModulos_coleta)
                ? dadosCard?.qtdModulos_coleta
                : proposta?.modulosDigitado_proposta
            }
          />
          <Input
            name="valorTerceiroAbertura_pvos"
            label="Custo do Serviço"
            mascara="numero"
            formulario={form}
            width={"flex-1"}
            prefix={"R$"}
            // required
            // error={"Preencha a Quantidade de Módulos"}
            // defaultValue={dadosCard?.qtdModulos_coleta}
          />
          <InputSelectComponent
            name="cod_respfin_pvos"
            label="Responsabilidade Financeira"
            formulario={form}
            options={responsabilidaesFinanceiras
              ?.filter(
                (responsabilidade) => responsabilidade?.status_respfin == "1"
              )
              ?.map((responsabilidade) => ({
                ...responsabilidade,
                label: responsabilidade?.nome_respfin,
                value: responsabilidade?.id_respfin,
              }))}
            // defaultValue={agendamento}
            width={"flex-1"}
            required
            error="Informe a responsabilidade"
            onChange={(e: any) => {
              setResponsabilidaeFinanceira(e);
              if (e?.is_terceiro_respfin != "1") {
                form?.unregister(["terceiro_pvos"], {
                  keepValue: false,
                  keepError: false,
                });
                form?.reload();
              }
            }}
          />
          {responsabilidaeFinanceira?.is_terceiro_respfin == 1 && (
            <InputSelectComponent
              name="terceiro_pvos"
              label="Instalador Responsável Financeiramente"
              formulario={form}
              options={usuarios
                .filter((usuario: any) => usuario.cargo_perfil == 6)
                .map((usuario: any) => ({
                  value: usuario.id_usuario,
                  label: usuario.nome_usuario,
                }))}
              // defaultValue={agendamento}
              width={"flex-1"}
              required
              error="Informe o responsável"
            />
          )}
          <Input
            name="telefone_adicional_pvos"
            label="Telefone Adicional do Cliente"
            mascara="telefone"
            formulario={form}
            width={"flex-1"}
            // required
            // error={"Preencha a Telefone Adicional do Cliente"}
            // defaultValue={dadosCard?.qtdModulos_coleta}
          />
          <Input
            name="obs_pvos"
            label="Observações"
            formulario={form}
            type="textarea"
          />
          <div>
            <div>Anexos da OS</div>
            <div className="pt-1">
              <div className="flex flex-col gap-1 max-h-[200px] overflow-auto">
                {isLoadingAnexos ? (
                  <div className="flex justify-center items-center">
                    <LoaderSun height={100} />
                  </div>
                ) : (
                  imageUrls.map((imageUrl, index) => {
                    const anexo: File = anexos[index];
                    return (
                      <div
                        key={index}
                        className="flex flex-row justify-between px-2 cursor-pointer hover:bg-[rgb(0,0,0)]/[.1] border border-transparent hover:border-black/[0.4] rounded"
                        onClick={() => handleDownload(anexo)}
                      >
                        <div className="w-[400px] overflow-hidden text-ellipsis p-1 flex flex-row items-center gap-1">
                          <figure
                            className="flex flex-col items-center overflow-hidden w-[20%] hover:w-[50%] transition-all"
                            onClick={(e) => {
                              e.stopPropagation();
                              openGallery(index);
                            }}
                          >
                            <FileRenderer
                              src={imageUrl}
                              name={anexo?.name?.split("/").pop()!}
                              className={
                                "h-full w-30 flex flex-col items-center justify-center bg-animate-pulse bg-white rounded overflow-hidden"
                              }
                              width={200}
                            />
                          </figure>
                          {anexo?.name}
                        </div>
                        <button
                          type="button"
                          onClick={(e) => {
                            e.stopPropagation();
                            setAnexos((prev) => {
                              const newAnexos = [...prev];
                              newAnexos.splice(index, 1);
                              return newAnexos;
                            });
                          }}
                        >
                          <MdClose />
                        </button>
                      </div>
                    );
                  })
                )}
              </div>
              <label
                htmlFor="add_anexo"
                // htmlFor={indexItem}
                className="justify-center dark:text-white whitespace-nowrap rounded-md font-medium ring-offset-background transition-colors focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:pointer-events-none disabled:opacity-50 text-primary-foreground flex bg-success hover:brightness-90 hover:bg-success text-sm h-fit items-center w-fit m-1 mb-4 p-1 px-2 cursor-pointer"
              >
                <FaPaperclip /> Adicionar Documento
              </label>
              <input
                id="add_anexo"
                // id={indexItem}
                type="file"
                // accept="image/png, image/gif, image/jpeg"
                className="hidden"
                key={inputKey}
                onInput={(e) => adicionarAnexo(e)}
              />
            </div>
          </div>
        </div>

        <Button>Próximo</Button>
      </form>
    ) : isLoadingTemplateOS ? (
      <div className="flex justify-center w-full">
        <LoaderSun />
      </div>
    ) : (
      <div>
        {/* <div onClick={() => setStep(0)}>Voltar</div> */}
        <FormTemplateGeracaoOS
          dadosCard={dadosCard}
          dadosCliente={dadosCliente}
          proposta={proposta}
          contrato={contrato}
          reloadOrdensServico={reloadOrdensServico}
          // camposPersonalizados={dataFormGeracaoOS}
          camposPersonalizados={{}}
          lojas={lojas}
          setActiveStepAtual={setActiveStepAtual}
          cronogramaInstalacao={[]}
          setIsLoading={setIsLoading}
          activeStep={activeStep}
          templateString={templateOS}
          ordensServico={ordensServico}
          dataFormGeracaoOS={dataFormGeracaoOS}
          agendamento={agendamento}
          usuarios={usuarios}
          responsabilidaesFinanceiras={responsabilidaesFinanceiras}
          botoes={botoes}
          tipoServicoName={tipoServicoName}
        />
      </div>
    )
  ) : (
    <div className="flex justify-center w-full">
      <LoaderSun />
    </div>
  );
};

export default FormGeracaoOS;
