import { useEffect, useRef } from "react";

let echartsLoader;

function loadEcharts() {
  if (!echartsLoader) {
    echartsLoader = Promise.all([
      import("echarts/lib/echarts"),
      import("echarts/lib/chart/line"),
      import("echarts/lib/chart/bar"),
      import("echarts/lib/chart/pie"),
      import("echarts/lib/component/grid"),
      import("echarts/lib/component/tooltip"),
      import("echarts/lib/component/legend")
    ]).then(([echarts]) => echarts);
  }

  return echartsLoader;
}

export function EChart({ className = "", option }) {
  const elementRef = useRef(null);
  const chartRef = useRef(null);
  const optionRef = useRef(option);

  useEffect(() => {
    optionRef.current = option;
    chartRef.current?.setOption(option, true);
  }, [option]);

  useEffect(() => {
    const element = elementRef.current;

    if (!element) {
      return undefined;
    }

    let disposed = false;
    let removeResize = () => {};

    loadEcharts().then((echarts) => {
      if (disposed) {
        return;
      }

      const chart = echarts.init(element, null, { renderer: "canvas" });
      chartRef.current = chart;
      chart.setOption(optionRef.current);

      const resize = () => chart.resize();
      const observer = typeof ResizeObserver === "function" ? new ResizeObserver(resize) : null;
      observer?.observe(element);
      window.addEventListener("resize", resize);

      removeResize = () => {
        observer?.disconnect();
        window.removeEventListener("resize", resize);
      };
    });

    return () => {
      disposed = true;
      removeResize();
      chartRef.current?.dispose();
      chartRef.current = null;
    };
  }, []);

  return <div className={["echart", className].filter(Boolean).join(" ")} ref={elementRef} />;
}
