Design State Subscriptions
Use kittl.designStore.subscribe() to react to real-time changes in the design state — object properties, board configuration, group structures, and more.
Subscribing to a Single Property
Pass an array with one path and a callback that receives the current value.
const unsub = await kittl.designStore.subscribe(
['objects.obj-id.width'],
(width) => {
console.log('width:', width);
}
);
Subscribing to Multiple Properties
Pass multiple paths in the array. The callback receives one argument per path, in the same order.
const unsub = await kittl.designStore.subscribe(
[
'objects.obj-id.left',
'objects.obj-id.top',
'objects.obj-id.fill',
],
(left, top, fill) => {
console.log('position:', left, top);
console.log('fill:', fill);
}
);
The callback fires whenever any of the subscribed values changes.
Unsubscribing
subscribe() returns an unsubscribe function. Call it when you no longer need updates.
const unsub = await kittl.designStore.subscribe(
['objects.obj-id.width'],
(width) => console.log(width)
);
// Later, when done:
unsub();
Valid Paths
Each path is a dot-separated string. The first segment must be one of the top-level design state keys:
| Key | Description |
|---|---|
objects | All design objects (shapes, text, images, etc.) |
boards | Artboards and board-like containers |
boardsIndices | Board ordering indices |
groupStructures | Group/layer hierarchy |
groupStructuresIndices | Group ordering indices |
config | Design-level configuration (title, DPI, etc.) |
You can drill into nested properties using dot notation:
objects.obj-id.width
objects.obj-id.fill
config.title
boards.board-id.floating
Invalid paths — empty segments, unknown top-level keys — throw an error.
Handling undefined
A callback argument is undefined when the path doesn't resolve to a value. This happens when an object is deleted, hasn't been created yet, or the path is deeper than the current state tree. Always account for undefined.
const unsub = await kittl.designStore.subscribe(
['objects.obj-id.width'],
(width) => {
if (width === undefined) {
console.log('Object does not exist (yet)');
return;
}
console.log('width:', width);
}
);
Example: Sync a UI Panel with Object Size
function watchObjectSize(objectId: string) {
return kittl.designStore.subscribe(
[`objects.${objectId}.width`, `objects.${objectId}.height`],
(width, height) => {
if (width === undefined || height === undefined) return;
updateSizePanel(width, height);
}
);
}
const unsub = await watchObjectSize('shape-123');
// Tear down when the panel closes
unsub();