Spaces:
Running
Running
File size: 3,288 Bytes
f586f77 6c17bbb f586f77 2e0eaa2 f586f77 2e0eaa2 f586f77 2e0eaa2 f586f77 2e0eaa2 f586f77 6c17bbb f586f77 6c17bbb f586f77 6c17bbb f586f77 6c17bbb f586f77 6c17bbb f586f77 2e0eaa2 | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 | import { useEffect } from "react";
import { AppLayout, Button, DatasetPicker, describePlot, Divider, useDataset } from "@elvis/ui";
// import { LoadingScreen } from "@elvis/ui";
import { OKABE_ITO_COLORS } from "./colors.ts";
import { DATASETS } from "./datasets.ts";
import DecisionBoundaryPlot from "./DecisionBoundaryPlot.tsx";
import Sidebar from "./Sidebar.tsx";
import Usage from "./Usage.tsx";
import useAppLogic from "./useAppLogic.ts";
const MANUAL_CLASSES = OKABE_ITO_COLORS.map(({ name, value }) => ({ name, color: value }));
export default function App() {
const app = useAppLogic();
const dataset = useDataset({ task: "classification", builtins: DATASETS, classes: MANUAL_CLASSES });
const processed = dataset.result?.ok ? dataset.result.dataset : null;
// Plot whatever the picker produces and send it to Python. Drawing points by
// hand keeps the view still; loading a table zooms to fit it.
useEffect(() => {
app.handleSetDataset(processed, dataset.source !== "manual");
}, [dataset.result]);
//if (!app.backendReady) {
//return <LoadingScreen message="Loading" />;
//}
return (
<AppLayout
title="Decision Boundary"
usage={<Usage />}
examples={<p>Examples are coming soon.</p>}
panel={
<>
<DatasetPicker dataset={dataset} />
<Divider />
<Sidebar
modelSettings={app.modelSettings}
setModelSettings={app.handleModelSettingsChange}
/>
<Divider />
{app.pythonStatus === "loading" && (
<p className="text-sm text-ink-muted">Loading Python… actions will run once it is ready.</p>
)}
{app.pythonStatus === "failed" && (
<p className="text-red-600 font-semibold">Python failed to load. Try reloading the page.</p>
)}
<section className="flex flex-col gap-4">
<h3 className="text-xs font-semibold uppercase tracking-widest text-ink-muted">Fit</h3>
<Button
label="Get Decision Boundary"
onClick={app.handleGetDecisionBoundary}
variant="primary"
/>
<label className="flex items-center gap-2 text-sm text-gray-700 cursor-pointer">
<input
type="checkbox"
checked={app.autoFit}
onChange={(e) => app.handleAutoFitChange(e.target.checked)}
className="size-4 accent-ink"
/>
Fit automatically
</label>
{app.modelError && (
<p className="text-red-600 font-semibold">{app.modelError}</p>
)}
</section>
</>
}
>
<DecisionBoundaryPlot
dataPoints={app.dataPoints}
onDataClick={dataset.source === "manual" ? dataset.manual.add : null}
decisionBoundaryResult={app.decisionBoundaryResult}
xRangeRef={app.xRangeRef}
yRangeRef={app.yRangeRef}
setRanges={app.handleRangeChange}
labelColors={app.labelColors}
plotHandle={app.plotHandle}
/>
{dataset.source !== "manual" && dataset.result?.ok && (
<p className="mt-2 text-xs text-ink-muted">{describePlot(dataset.result.dataset)}</p>
)}
</AppLayout>
);
}
|