Configuration & Callbacks
WorkspaceConfig
Options passed to the Workspace constructor to customize interaction tolerances and visual appearance.
const ws = new Workspace(container, callbacks, {
overlayStyle: { ... },
snapThreshold: 5,
minResizeSize: 40,
enableSnapGuides: true,
})| Property | Type | Default | Description |
|---|---|---|---|
overlayStyle | Partial<OverlayStyle> | See below | Overrides default canvas overlay colors, border widths, and fonts |
snapThreshold | number | 5 | Alignment guidelines snapping distance in canvas-space pixels |
minResizeSize | number | 40 | Minimum width or height allowed when resizing a node wrapper |
enableSnapGuides | boolean | true | Enables drawing snapping alignment lines during drag gestures |
OverlayStyle
The full set of visual tokens controlling every aspect of the canvas overlay. All properties are optional when passed via Partial<OverlayStyle>.
interface OverlayStyle {
// ββ Selection βββββββββββββββββββββββββββ
selectionStroke: string // Selection border color (default: '#6366f1')
selectionWidth: number // Selection stroke width in px (default: 2)
selectionGlow: string // Glow shadow color (default: 'rgba(99,102,241,0.4)')
selectionGlowRadius: number // Glow blur radius (default: 12)
// ββ Hover βββββββββββββββββββββββββββββββ
hoverStroke: string // Hover outline color (default: 'rgba(99,102,241,0.6)')
hoverWidth: number // Hover stroke width (default: 1.5)
hoverDash: number[] // Hover dash pattern (default: [5, 5])
// ββ Resize Handles ββββββββββββββββββββββ
handleSize: number // Handle square size in px (default: 8)
handleFill: string // Handle fill color (default: '#ffffff')
handleStroke: string // Handle border color (default: '#6366f1')
handleStrokeWidth: number // Handle border width (default: 1.5)
handleRadius: number // Handle corner radius, 0 = square (default: 2)
handleHitRadius: number // Hit-test radius around handle center (default: 8)
handleActiveFill: string // Fill when actively dragging (default: '#6366f1')
// ββ Alignment Guides ββββββββββββββββββββ
guideStroke: string // Snap guide color (default: '#f43f5e')
guideWidth: number // Snap guide width (default: 1)
guideDash: number[] // Snap guide dash pattern (default: [4, 4])
// ββ Origin Crosshair ββββββββββββββββββββ
originStroke: string // Origin line color (default: 'rgba(99,102,241,0.12)')
originDash: number[] // Origin dash pattern (default: [6, 6])
// ββ Multi-Select ββββββββββββββββββββββββ
multiSelectStroke: string // Aggregate bounding box color (default: 'rgba(99,102,241,0.5)')
multiSelectDash: number[] // Aggregate box dash pattern (default: [6, 4])
// ββ Layout Badges βββββββββββββββββββββββ
layoutBadgeBg: string // Badge background (default: 'rgba(99,102,241,0.85)')
layoutBadgeText: string // Badge text color (default: '#ffffff')
layoutBadgeFont: string // Badge font (default: "600 9px 'Inter', system-ui")
// ββ Grid Tracks βββββββββββββββββββββββββ
gridTrackStroke: string // Grid track overlay color (default: 'rgba(99,102,241,0.2)')
gridTrackDash: number[] // Grid track dash pattern (default: [3, 3])
// ββ Scoped Selection ββββββββββββββββββββ
parentHighlightStroke: string // Parent outline when child is selected (default: 'rgba(99,102,241,0.35)')
childOutlineStroke: string // Available children outlines (default: 'rgba(99,102,241,0.18)')
// ββ Drag & Drop βββββββββββββββββββββββββ
dropZoneStroke: string // Drop container border (default: '#3b82f6')
dropZoneWidth: number // Drop zone stroke width (default: 2)
insertionLineStroke: string // Insertion line color (default: '#3b82f6')
insertionLineWidth: number // Insertion line width (default: 3)
}WorkspaceCallbacks
Hook callbacks triggered on workspace events. All callbacks are optional.
const ws = new Workspace(container, {
onHTMLCommit(id, html) { /* ... */ },
onNodeRectChange(id, rect) { /* ... */ },
onViewportChange(vp) { /* ... */ },
onSelectionChange(selectedIds) { /* ... */ },
onBreadcrumbChange(path) { /* ... */ },
onInteractionChange(mode) { /* ... */ },
onOperationsGenerated(ops) { /* ... */ },
onTextEditRequest(nodeId, element, commit) { /* ... */ },
})Callback Reference
onHTMLCommit
onHTMLCommit?: (id: string, html: string) => voidFlat String Bridge. Emits clean HTML string fragments (with wrappers stripped) after visual adjustments complete.
onNodeRectChange
onNodeRectChange?: (id: string, rect: Rect) => voidFired when a nodeβs bounding rect changes due to reflow or drag.
onViewportChange
onViewportChange?: (vp: Readonly<ViewportMatrix>) => voidFired when the workspace zoom level or pan offset shifts.
onSelectionChange
onSelectionChange?: (selectedIds: ReadonlySet<string>) => voidFired when the active selection is updated.
onBreadcrumbChange
onBreadcrumbChange?: (path: string[]) => voidFired when selection depth breadcrumbs are updated (drill-down navigation).
onInteractionChange
onInteractionChange?: (mode: string | null) => voidFired when the active drag state switches (e.g., "pan", "drag-node", "resize-node", null).
onOperationsGenerated
onOperationsGenerated?: (operations: Operation[]) => voidFired when a visual modification generates undoable history steps. See the Operations Guide for integration patterns.
onTextEditRequest
onTextEditRequest?: (
nodeId: string,
element: HTMLElement,
commit: (newHTML: string) => void
) => voidDouble-click escape hatch callback to mount custom rich text editor overlays. See the Custom Editor Guide for implementation examples.
onForcePseudoState
onForcePseudoState?: (
nodeId: string,
state: "hover" | "active" | "focus",
enabled: boolean
) => voidFired when a nodeβs pseudo-class state is modified via forceNodeState(). Use this to delegate pseudo-class forcing to the host β for example, via Chrome DevTools Protocol (CSS.forcePseudoState) in an Electron environment.
const ws = new Workspace(container, {
onForcePseudoState(nodeId, state, enabled) {
// e.g., Forward to CDP in Electron
cdp.send('CSS.forcePseudoState', {
nodeId: getDOMNodeId(nodeId),
forcedPseudoClasses: enabled ? [`:${state}`] : [],
})
},
})