import { useEffect, useRef, useState } from "react"; import PyodideWorker from "./pyodide.worker.ts?worker"; import type { PlotData, Settings, WorkerMessage } from "./types.ts"; export default function usePyodide(initialSettings: Settings) { const [plotData, setPlotData] = useState({}); const [isLoading, setIsLoading] = useState(true); const workerRef = useRef(null); function sendInit(settings: Settings) { if (workerRef.current) { workerRef.current.postMessage({ type: "INIT", settings }); } } function sendNextStep() { if (workerRef.current) { workerRef.current.postMessage({ type: "NEXT_STEP" }); } } function sendPrevStep() { if (workerRef.current) { workerRef.current.postMessage({ type: "PREV_STEP" }); } } function sendReset() { if (workerRef.current) { workerRef.current.postMessage({ type: "RESET" }); } } useEffect(() => { const worker = new PyodideWorker(); workerRef.current = worker; worker.onmessage = (event) => { const message = event.data as WorkerMessage; if (message.type === "READY") { console.log("Pyodide is ready"); setIsLoading(false); sendInit(initialSettings); } else if (message.type === "RESULT") { // todo data validation / type setPlotData((prevData) => ({ functionValues: message.data.functionValues || prevData.functionValues, trajectoryValues: message.data.trajectoryValues || prevData.trajectoryValues, })) } }; return () => { worker.terminate(); }; }, []); return { isLoading, plotData, sendInit: sendInit, sendReset: sendReset, sendNextStep: sendNextStep, sendPrevStep: sendPrevStep, } }