Spatial Canvas
Open in playgroundPlace items on a two-axis canvas. Position encodes two dimensions at once — effort × impact, cost × value, risk × reward.
Preview
Usage
import { SpatialCanvas } from "@/components/socratic-ui/spatial-canvas";
const [value, setValue] = useState<Record<string, { x: number; y: number }>>({});
<SpatialCanvas
question="Map these on effort vs impact"
xAxisLabel="Effort"
yAxisLabel="Impact"
items={[
{ id: "a", title: "Onboarding flow" },
{ id: "b", title: "API docs" },
]}
value={value}
onChange={setValue}
/>
API Reference
| Prop | Type | Default |
|---|---|---|
questionrequiredThe headline shown above the canvas. | string | — |
subtitleOptional supporting copy beneath the question. | string | — |
itemsrequiredItems the user can pick up and place on the canvas. | { id: string; title: string; subtitle?: string }[] | — |
xAxisLabelrequiredHorizontal axis name (e.g. "Effort"). | string | — |
yAxisLabelrequiredVertical axis name (e.g. "Impact"). | string | — |
xLowLabelOptional low-end label for the X axis. | string | — |
xHighLabelOptional high-end label for the X axis. | string | — |
yLowLabelOptional low-end label for the Y axis. | string | — |
yHighLabelOptional high-end label for the Y axis. | string | — |
valuerequiredMap of item id to normalized position. Both axes run 0 (low) to 1 (high); unplaced items are absent from the map. | Record<string, { x: number; y: number }> | — |
onChangerequiredCalled whenever a position is placed, moved, or removed. | (value: Record<string, { x: number; y: number }>) => void | — |
numberOptional leading question number, e.g. "01". | string | — |
motionOpt-in entrance animation config. Omit for static rendering; pass `{ enabled: true }` (or a preset from `motion.ts`) to animate in on mount. | SocraticMotion | — |