import { ThemeProvider } from "@emotion/react";
import { Grid } from "@mui/material";
import { enqueueSnackbar } from "notistack";
import { useEffect, useState } from "react";
import { buildTheme } from "../../infrastructure/theme/theme";
import baseUrl from "../../services/api/api.config";
import postData from "../../services/api/base";
import BarPlot from "../BarPlot";
import { SemanticDifferencesContext } from "../Context/WordsContext";
import DimensionsList from "../DimensionList";
import IntroSemantic from "../IntroSemantic";
import ScatterDicionary from "../ScatterDicionary";
import WordCard from "../WordCard";

export default function SemanticDifferences() {
  const [SemanticDifferencesWords, setSemanticDifferencesWords] = useState([]);
  const [selectedDimensions, setSelectedDimensions] = useState([0, 0]);
  const [wordOne, setWordOne] = useState("");
  const [wordTwo, setWordTwo] = useState("");
  const [variance, setVariance] = useState({
    variances: new Array(50).fill(0),
    dimensions: [1, 2, 3],
  });

  const onChangeWordOne = (event) => {
    const newWordOne = event.target.value;
    setWordOne(newWordOne);
  };

  const onChangeWordTwo = (event) => {
    const newWordTwo = event.target.value;
    setWordTwo(newWordTwo);
  };

  const handleDimensionClick = (dimension) => {
    setSelectedDimensions((prev) => {
      if (prev.includes(dimension)) {
        return prev.filter((dim) => dim !== dimension);
      } else if (prev.length < 2) {
        return [...prev, dimension];
      } else {
        return [prev[1], dimension];
      }
    });
  };

  const onPressButton = async () => {
    const url = `/add-difference-semantic-words`;
    const data = {
      word1: wordOne,
      word2: wordTwo,
    };
    if (!wordOne.trim() || !wordTwo.trim()) {
      enqueueSnackbar("Please enter both words with at least 1 character", {
        variant: "alert",
      });
      return;
    }

    postData(url, data)
      .catch((error) => {
        enqueueSnackbar(error.detail || error.message, {
          variant: "error",
        });
      })
      .then(fetchSemanticDifferenceWords)
      .then(fetchEmebedding);
    setWordOne("");
    setWordTwo("");
  };

  const fetchSemanticDifferenceWords = async () => {
    const url = `${baseUrl}/difference-semantic-words`;
    const response = await fetch(url);
    const SemanticDifferencesWords = await response.json();
    setSemanticDifferencesWords(SemanticDifferencesWords.data);
  };

  const fetchEmebedding = async () => {
    const url = `${baseUrl}/get-embedding-difference`;
    const response = await fetch(url);
    const embeddingResponse = await response.json();
    setVariance(embeddingResponse.data.variance);
    setSelectedDimensions(
      embeddingResponse.data.top_variance_dims.slice(0, 2).map((d) => d + 1)
    );

    if (!embeddingResponse.success) {
      enqueueSnackbar("Not enough word to create variance");
    }
  };

  const deleteSemanticDifferenceWord = async (id) => {
    const url = `${baseUrl}/delete-difference-semantic-words/${id}`;
    await fetch(url, {
      method: "DELETE",
      headers: { "Content-Type": "application/json" },
    });
    await fetchSemanticDifferenceWords();
    await fetchEmebedding();
  };

  useEffect(() => {
    fetchSemanticDifferenceWords();
  }, []);

  console.log(variance);

  return (
    <>
      <SemanticDifferencesContext.Provider
        value={{ SemanticDifferencesWords, setSemanticDifferencesWords }}
      >
        <ThemeProvider theme={buildTheme()}>
          <Grid>
            <IntroSemantic
              wordOne={wordOne}
              wordTwo={wordTwo}
              onChangeWordOne={onChangeWordOne}
              onChangeWordTwo={onChangeWordTwo}
              onPressButton={onPressButton}
            />
          </Grid>
          <Grid container mt={2} textAlign={"center"} spacing={2}>
            <Grid item xs={9}>
              <BarPlot variance={variance} />
            </Grid>
            <Grid item xs={3}>
              {Object.entries(SemanticDifferencesWords).map(([key, value]) => (
                <Grid item key={value.id} mb={1} ml={4}>
                  <WordCard
                    word={key}
                    id={value.id}
                    deleteWord={deleteSemanticDifferenceWord}
                  />
                </Grid>
              ))}
            </Grid>
          </Grid>

          <DimensionsList
            embedding={variance}
            selectedDimensions={selectedDimensions}
            onDimensionClick={handleDimensionClick}
          />

          <Grid item xs={12} container>
            <ScatterDicionary
              words={SemanticDifferencesWords}
              x={selectedDimensions[0]}
              y={selectedDimensions[1]}
            />
          </Grid>
        </ThemeProvider>
      </SemanticDifferencesContext.Provider>
    </>
  );
}
