@pixerate/editor 0.227.0 → 0.228.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/agent/index.cjs +3 -3
- package/dist/agent/index.js +2 -2
- package/dist/animation-editor/index.cjs +9 -9
- package/dist/animation-editor/index.js +1 -1
- package/dist/canvas/drawController.d.cts +6 -0
- package/dist/canvas/drawController.d.ts +6 -0
- package/dist/canvas/effects.d.cts +18 -0
- package/dist/canvas/effects.d.ts +18 -0
- package/dist/canvas/gestures.d.cts +87 -0
- package/dist/canvas/gestures.d.ts +87 -0
- package/dist/canvas/index.cjs +56 -9
- package/dist/canvas/index.d.cts +1 -0
- package/dist/canvas/index.d.ts +1 -0
- package/dist/canvas/index.js +50 -3
- package/dist/{chunk-ABQ2VGUB.cjs → chunk-5MQOBTNP.cjs} +13 -2
- package/dist/{chunk-53GOGBTM.cjs → chunk-CHAWTXBE.cjs} +243 -39
- package/dist/{chunk-C6CMQXMI.cjs → chunk-IGPEBXUD.cjs} +7 -7
- package/dist/{chunk-4PA6YS6W.cjs → chunk-K5GXW5TR.cjs} +14 -14
- package/dist/{chunk-7KZ2HKKC.js → chunk-LPFQHVCO.js} +244 -1
- package/dist/{chunk-56RFHF7O.js → chunk-LPTFDCJO.js} +1 -1
- package/dist/{chunk-4MDWEX44.js → chunk-PB6JV62G.js} +1 -1
- package/dist/{chunk-4EFNS2HV.cjs → chunk-T7QSEKDY.cjs} +248 -5
- package/dist/{chunk-7DZ55AIE.js → chunk-UGYUGZE2.js} +13 -2
- package/dist/{chunk-ZPJEH456.js → chunk-XVIK73LS.js} +206 -2
- package/dist/commands/agentTools.d.cts +14 -0
- package/dist/commands/agentTools.d.ts +14 -0
- package/dist/commands/builtins.d.cts +11 -1
- package/dist/commands/builtins.d.ts +11 -1
- package/dist/commands/index.cjs +23 -9
- package/dist/commands/index.js +17 -3
- package/dist/effects/index.cjs +44 -44
- package/dist/effects/index.js +2 -2
- package/dist/image-editor/index.cjs +13 -13
- package/dist/image-editor/index.js +1 -1
- package/dist/paint-editor/index.cjs +7 -7
- package/dist/paint-editor/index.js +2 -2
- package/dist/vector/index.cjs +6 -6
- package/dist/vector/index.js +1 -1
- package/dist/video-editor/index.cjs +309 -309
- package/dist/video-editor/index.js +3 -3
- package/package.json +1 -1
- package/skills/pixerate-agent-tools/SKILL.md +5 -0
- package/skills/pixerate-canvas/SKILL.md +41 -2
|
@@ -1,7 +1,16 @@
|
|
|
1
1
|
import {
|
|
2
2
|
DEFAULT_ARRANGE_SHORTCUTS,
|
|
3
|
-
ShortcutMap
|
|
4
|
-
|
|
3
|
+
ShortcutMap,
|
|
4
|
+
arrowGesture,
|
|
5
|
+
bracketGesture,
|
|
6
|
+
checkGesture,
|
|
7
|
+
circleGesture,
|
|
8
|
+
crossGesture,
|
|
9
|
+
gestureSeed,
|
|
10
|
+
gestureUnion,
|
|
11
|
+
strikeGesture,
|
|
12
|
+
underlineGesture
|
|
13
|
+
} from "./chunk-LPFQHVCO.js";
|
|
5
14
|
|
|
6
15
|
// src/commands/builtins.ts
|
|
7
16
|
var DEFAULT_HISTORY_SHORTCUTS = [
|
|
@@ -370,7 +379,202 @@ function createDrawCommands(target, options = {}) {
|
|
|
370
379
|
params: { type: "object", additionalProperties: false, properties: {} },
|
|
371
380
|
readOnly: true,
|
|
372
381
|
run: async () => ({ brushes: await target.listBrushes() })
|
|
382
|
+
},
|
|
383
|
+
...createGestureCommands(target, base, prefix, options)
|
|
384
|
+
];
|
|
385
|
+
}
|
|
386
|
+
var GESTURE_RECT_PARAM = {
|
|
387
|
+
type: "object",
|
|
388
|
+
additionalProperties: false,
|
|
389
|
+
required: ["x", "y", "width", "height"],
|
|
390
|
+
description: "A box in canvas units (top left x, y and its size), e.g. a node's bounds from get_editor_state or a stroke's `bounds`.",
|
|
391
|
+
properties: {
|
|
392
|
+
x: { type: "number", description: "Left edge, canvas units." },
|
|
393
|
+
y: { type: "number", description: "Top edge, canvas units." },
|
|
394
|
+
width: { type: "number", minimum: 0, description: "Width, canvas units." },
|
|
395
|
+
height: { type: "number", minimum: 0, description: "Height, canvas units." }
|
|
396
|
+
}
|
|
397
|
+
};
|
|
398
|
+
var GESTURE_NODE_PARAM = {
|
|
399
|
+
type: "object",
|
|
400
|
+
additionalProperties: false,
|
|
401
|
+
required: ["nodeId"],
|
|
402
|
+
description: "A node on the canvas by id; its current box is used, so you need not read its position first.",
|
|
403
|
+
properties: { nodeId: { type: "string", minLength: 1, description: "The node id (from get_editor_state or a result)." } }
|
|
404
|
+
};
|
|
405
|
+
var GESTURE_POINT_PARAM = {
|
|
406
|
+
type: "array",
|
|
407
|
+
minItems: 2,
|
|
408
|
+
maxItems: 2,
|
|
409
|
+
items: { type: "number" },
|
|
410
|
+
description: "A point as [x, y] in canvas units."
|
|
411
|
+
};
|
|
412
|
+
var gestureBox = (what) => ({ description: what, oneOf: [GESTURE_RECT_PARAM, GESTURE_NODE_PARAM] });
|
|
413
|
+
var gestureEnd = (what) => ({ description: what, oneOf: [GESTURE_RECT_PARAM, GESTURE_NODE_PARAM, GESTURE_POINT_PARAM] });
|
|
414
|
+
var gestureBoxes = (what) => ({
|
|
415
|
+
type: "array",
|
|
416
|
+
minItems: 1,
|
|
417
|
+
maxItems: 100,
|
|
418
|
+
items: { oneOf: [GESTURE_RECT_PARAM, GESTURE_NODE_PARAM] },
|
|
419
|
+
description: `${what} Each is a box { x, y, width, height } or a node { nodeId }; the gesture spans the box around all of them.`
|
|
420
|
+
});
|
|
421
|
+
var GESTURE_STYLE_PARAMS = {
|
|
422
|
+
tool: { type: "string", enum: ["pen", "highlighter"], description: "Pen (default: blue, width 3) or highlighter (yellow, width 24, opacity 0.35); sets the defaults below." },
|
|
423
|
+
color: { type: "string", description: "Stroke colour, any CSS colour (default from the tool)." },
|
|
424
|
+
width: { type: "number", exclusiveMinimum: 0, maximum: 2500, description: "Stroke width in canvas units (default from the tool; with a brush, the preset's own size)." },
|
|
425
|
+
opacity: { type: "number", minimum: 0, maximum: 1, description: "Stroke opacity 0..1 (default from the tool)." },
|
|
426
|
+
brush: {
|
|
427
|
+
description: 'Paint the mark with a dry paint brush: a preset id such as "ink-pen", "marker", "pencil-hb" or "brush-pen" (all ids: canvas.listBrushes), or tip settings. Brushed marks get an uneven hand pressure. Omit for a plain vector stroke.',
|
|
428
|
+
oneOf: [{ type: "string", minLength: 1 }, BRUSH_SETTINGS_PARAM]
|
|
429
|
+
},
|
|
430
|
+
seed: { type: "integer", minimum: 0, maximum: 4294967295, description: "Seed for the hand-drawn wobble (default: derived from the other params, so the same request draws the same mark). Change it for a different take." }
|
|
431
|
+
};
|
|
432
|
+
function createGestureCommands(target, base, prefix, options) {
|
|
433
|
+
const box = (value, name) => {
|
|
434
|
+
if (Array.isArray(value)) throw new Error(`${name} must be a box { x, y, width, height } or a node { nodeId }, not a point.`);
|
|
435
|
+
if ("nodeId" in value) {
|
|
436
|
+
if (!target.nodeBounds) throw new Error(`This canvas cannot look up nodes: pass ${name} as a box { x, y, width, height } (a node's bounds from get_editor_state).`);
|
|
437
|
+
const rect = target.nodeBounds(value.nodeId);
|
|
438
|
+
if (!rect) throw new Error(`Unknown node "${value.nodeId}" in ${name}: use an id from get_editor_state.`);
|
|
439
|
+
return rect;
|
|
373
440
|
}
|
|
441
|
+
return value;
|
|
442
|
+
};
|
|
443
|
+
const end = (value, name) => Array.isArray(value) ? [value[0], value[1]] : box(value, name);
|
|
444
|
+
const boxes = (values, name) => gestureUnion(values.map((v, i) => box(v, `${name}[${i}]`)));
|
|
445
|
+
const gesture = (spec) => {
|
|
446
|
+
const seedOf = (params) => params.seed ?? gestureSeed({ gesture: spec.name, ...params });
|
|
447
|
+
const generate = (params) => {
|
|
448
|
+
const seed = seedOf(params);
|
|
449
|
+
return { seed, stroke: spec.make(params, seed) };
|
|
450
|
+
};
|
|
451
|
+
return {
|
|
452
|
+
...base,
|
|
453
|
+
id: `${prefix}${spec.name}`,
|
|
454
|
+
label: spec.label,
|
|
455
|
+
keywords: ["annotate", "mark up", "hand-drawn", ...spec.keywords],
|
|
456
|
+
description: `${spec.description} Drawn as one hand-drawn pen or highlighter stroke node (one undo step), with a seeded wobble. Returns the new node \`id\`, its \`bounds\`, the stored \`brush\` (when brushed) and the \`seed\` used.`,
|
|
457
|
+
params: {
|
|
458
|
+
type: "object",
|
|
459
|
+
additionalProperties: false,
|
|
460
|
+
required: spec.required,
|
|
461
|
+
properties: { ...spec.properties, ...GESTURE_STYLE_PARAMS }
|
|
462
|
+
},
|
|
463
|
+
enabled: () => options.readOnlyReason?.() || true,
|
|
464
|
+
plan: (_ctx, params) => {
|
|
465
|
+
try {
|
|
466
|
+
return planFreehandPlayback(generate(params).stroke.points);
|
|
467
|
+
} catch {
|
|
468
|
+
return null;
|
|
469
|
+
}
|
|
470
|
+
},
|
|
471
|
+
run: async (_ctx, params) => {
|
|
472
|
+
const { seed, stroke } = generate(params);
|
|
473
|
+
const result = await target.drawStroke({
|
|
474
|
+
points: stroke.points,
|
|
475
|
+
...params.tool ? { tool: params.tool } : {},
|
|
476
|
+
style: {
|
|
477
|
+
...params.color !== void 0 ? { color: params.color } : {},
|
|
478
|
+
...params.width !== void 0 ? { width: params.width } : {},
|
|
479
|
+
...params.width !== void 0 && params.brush !== void 0 ? { brushSize: params.width } : {},
|
|
480
|
+
...params.opacity !== void 0 ? { opacity: params.opacity } : {},
|
|
481
|
+
...params.brush !== void 0 ? { brush: params.brush } : {}
|
|
482
|
+
},
|
|
483
|
+
...params.brush !== void 0 ? { pressure: stroke.pressure } : {}
|
|
484
|
+
});
|
|
485
|
+
return { ...result, seed };
|
|
486
|
+
}
|
|
487
|
+
};
|
|
488
|
+
};
|
|
489
|
+
return [
|
|
490
|
+
gesture({
|
|
491
|
+
name: "circle",
|
|
492
|
+
label: "Circle Around",
|
|
493
|
+
keywords: ["circle", "ring", "loop", "highlight", "pick", "ellipse"],
|
|
494
|
+
description: "Circles boxes or nodes with a loose, slightly open ellipse that never cuts into them: the way to point out a pick or the thing you are talking about.",
|
|
495
|
+
required: ["around"],
|
|
496
|
+
properties: {
|
|
497
|
+
around: gestureBoxes("What to circle."),
|
|
498
|
+
padding: { type: "number", minimum: 0, maximum: 500, description: "Space between them and the loop, canvas units (default 8)." }
|
|
499
|
+
},
|
|
500
|
+
make: (p, seed) => circleGesture(boxes(p.around, "around"), seed, { ...p.padding !== void 0 ? { padding: p.padding } : {} })
|
|
501
|
+
}),
|
|
502
|
+
gesture({
|
|
503
|
+
name: "underline",
|
|
504
|
+
label: "Underline",
|
|
505
|
+
keywords: ["underline", "emphasis", "line under", "squiggle"],
|
|
506
|
+
description: "Underlines a box or node with a stroke just below its bottom edge, a little longer or shorter than it: for stressing a line of text or a value.",
|
|
507
|
+
required: ["under"],
|
|
508
|
+
properties: {
|
|
509
|
+
under: gestureBox("What to underline: a box { x, y, width, height } or a node { nodeId }."),
|
|
510
|
+
offset: { type: "number", minimum: 0, maximum: 200, description: "Gap below the bottom edge, canvas units (default 4)." },
|
|
511
|
+
wave: { type: "boolean", description: "A wavy (squiggly) underline instead of a straight one (default false)." }
|
|
512
|
+
},
|
|
513
|
+
make: (p, seed) => underlineGesture(box(p.under, "under"), seed, { ...p.offset !== void 0 ? { offset: p.offset } : {}, ...p.wave ? { wave: true } : {} })
|
|
514
|
+
}),
|
|
515
|
+
gesture({
|
|
516
|
+
name: "arrow",
|
|
517
|
+
label: "Arrow",
|
|
518
|
+
keywords: ["arrow", "point", "connect", "from", "to", "pointer"],
|
|
519
|
+
description: "Draws a curved arrow with a hand-drawn head from one thing to another: a box or node is reached at its nearest edge, a point exactly. For linking a swatch to where it is used, or pointing from a note to its subject.",
|
|
520
|
+
required: ["from", "to"],
|
|
521
|
+
properties: {
|
|
522
|
+
from: gestureEnd("Where the arrow starts: a box, a node { nodeId } or a point [x, y]."),
|
|
523
|
+
to: gestureEnd("Where the arrow points: a box, a node { nodeId } or a point [x, y]."),
|
|
524
|
+
curve: { type: "number", minimum: -1, maximum: 1, description: "Bend of the shaft \u22121..1: how far its middle bulges, as a fraction of half its length; positive bends to the left of travel, 0 is straight (default: a gentle seeded bend, about 0.1)." },
|
|
525
|
+
gap: { type: "number", minimum: 0, maximum: 200, description: "Space between a box end and the arrow, canvas units (default 6)." }
|
|
526
|
+
},
|
|
527
|
+
make: (p, seed) => arrowGesture(end(p.from, "from"), end(p.to, "to"), seed, { ...p.curve !== void 0 ? { curve: p.curve } : {}, ...p.gap !== void 0 ? { gap: p.gap } : {} })
|
|
528
|
+
}),
|
|
529
|
+
gesture({
|
|
530
|
+
name: "bracket",
|
|
531
|
+
label: "Bracket",
|
|
532
|
+
keywords: ["bracket", "brace", "group", "curly", "span"],
|
|
533
|
+
description: "Brackets boxes or nodes on one side with a curly or square bracket spanning them end to end: for grouping a set of items or a range of lines, usually with a note beside it.",
|
|
534
|
+
required: ["around", "side"],
|
|
535
|
+
properties: {
|
|
536
|
+
around: gestureBoxes("What to bracket."),
|
|
537
|
+
side: { type: "string", enum: ["left", "right", "top", "bottom"], description: "Which side the bracket goes on." },
|
|
538
|
+
shape: { type: "string", enum: ["curly", "square"], description: "Curly brace (default) or square bracket." },
|
|
539
|
+
padding: { type: "number", minimum: 0, maximum: 500, description: "Gap between them and the bracket, canvas units (default 8)." },
|
|
540
|
+
depth: { type: "number", exclusiveMinimum: 0, maximum: 500, description: "How far the bracket reaches out, canvas units (default: from the span, 6..20)." }
|
|
541
|
+
},
|
|
542
|
+
make: (p, seed) => bracketGesture(boxes(p.around, "around"), p.side, seed, {
|
|
543
|
+
...p.shape ? { shape: p.shape } : {},
|
|
544
|
+
...p.padding !== void 0 ? { padding: p.padding } : {},
|
|
545
|
+
...p.depth !== void 0 ? { depth: p.depth } : {}
|
|
546
|
+
})
|
|
547
|
+
}),
|
|
548
|
+
gesture({
|
|
549
|
+
name: "strike",
|
|
550
|
+
label: "Strike Through",
|
|
551
|
+
keywords: ["strike", "strikethrough", "cross out", "line through", "delete"],
|
|
552
|
+
description: "Strikes a line through the middle of a box or node, a little past both ends: for text or a value to drop. It only marks it; nothing is deleted.",
|
|
553
|
+
required: ["over"],
|
|
554
|
+
properties: { over: gestureBox("What to strike through: a box { x, y, width, height } or a node { nodeId }.") },
|
|
555
|
+
make: (p, seed) => strikeGesture(box(p.over, "over"), seed)
|
|
556
|
+
}),
|
|
557
|
+
gesture({
|
|
558
|
+
name: "cross",
|
|
559
|
+
label: "Cross Out",
|
|
560
|
+
keywords: ["cross", "x", "reject", "no", "wrong", "cross out"],
|
|
561
|
+
description: "Crosses out a box or node with an X from corner to corner: for a rejected option. It only marks it; nothing is deleted. One stroke, so the pen runs back over part of the first diagonal before drawing the second.",
|
|
562
|
+
required: ["over"],
|
|
563
|
+
properties: { over: gestureBox("What to cross out: a box { x, y, width, height } or a node { nodeId }.") },
|
|
564
|
+
make: (p, seed) => crossGesture(box(p.over, "over"), seed)
|
|
565
|
+
}),
|
|
566
|
+
gesture({
|
|
567
|
+
name: "check",
|
|
568
|
+
label: "Check Mark",
|
|
569
|
+
keywords: ["check", "tick", "approve", "yes", "done", "ok"],
|
|
570
|
+
description: "Draws a tick mark in the middle of a box or node, or centred on a point: for an approved option or a done item.",
|
|
571
|
+
required: ["at"],
|
|
572
|
+
properties: {
|
|
573
|
+
at: gestureEnd("Where the tick goes: a box, a node { nodeId } (its centre) or a point [x, y]."),
|
|
574
|
+
size: { type: "number", exclusiveMinimum: 0, maximum: 2e3, description: "Height of the tick, canvas units (default: 60% of the box's smaller side, 12..48; 20 at a point)." }
|
|
575
|
+
},
|
|
576
|
+
make: (p, seed) => checkGesture(end(p.at, "at"), seed, { ...p.size !== void 0 ? { size: p.size } : {} })
|
|
577
|
+
})
|
|
374
578
|
];
|
|
375
579
|
}
|
|
376
580
|
function hasVariantCommands(controller) {
|
|
@@ -11,6 +11,17 @@ export interface CommandToolProviderOptions<TContext = any> {
|
|
|
11
11
|
scope?: string | readonly string[];
|
|
12
12
|
/** Commands agents may not see or run (e.g. ones that open dialogs). */
|
|
13
13
|
exclude?: (id: string) => boolean;
|
|
14
|
+
/**
|
|
15
|
+
* Commands also listed as tools of their own, beside `run_command` (ids, or a filter): the
|
|
16
|
+
* params schema is the tool's input schema, and the label, description, read-only flag and
|
|
17
|
+
* playback plan carry over. Agents then see them without calling `list_commands` first.
|
|
18
|
+
*/
|
|
19
|
+
tools?: readonly string[] | ((id: string) => boolean);
|
|
20
|
+
/**
|
|
21
|
+
* Name of a command's own tool (default: the id with every character other than letters,
|
|
22
|
+
* digits, `_` and `-` replaced by `_`, so `canvas.circle` is `canvas_circle`).
|
|
23
|
+
*/
|
|
24
|
+
toolName?: (id: string) => string;
|
|
14
25
|
}
|
|
15
26
|
/**
|
|
16
27
|
* Exposes a `CommandRegistry` to agents through a `ToolRegistry`:
|
|
@@ -26,6 +37,9 @@ export interface CommandToolProviderOptions<TContext = any> {
|
|
|
26
37
|
* registry with `history`) runs them as one undo step named `label` and takes everything
|
|
27
38
|
* back when one fails.
|
|
28
39
|
*
|
|
40
|
+
* With `tools`, chosen commands are also tools of their own (`canvas.circle` →
|
|
41
|
+
* `canvas_circle`, or `toolName`), taking the command's params as arguments.
|
|
42
|
+
*
|
|
29
43
|
* The id enum in `run_command`'s schema follows the registered commands, so the
|
|
30
44
|
* `ToolRegistry` announces `listChanged` when commands are added or removed.
|
|
31
45
|
*/
|
|
@@ -11,6 +11,17 @@ export interface CommandToolProviderOptions<TContext = any> {
|
|
|
11
11
|
scope?: string | readonly string[];
|
|
12
12
|
/** Commands agents may not see or run (e.g. ones that open dialogs). */
|
|
13
13
|
exclude?: (id: string) => boolean;
|
|
14
|
+
/**
|
|
15
|
+
* Commands also listed as tools of their own, beside `run_command` (ids, or a filter): the
|
|
16
|
+
* params schema is the tool's input schema, and the label, description, read-only flag and
|
|
17
|
+
* playback plan carry over. Agents then see them without calling `list_commands` first.
|
|
18
|
+
*/
|
|
19
|
+
tools?: readonly string[] | ((id: string) => boolean);
|
|
20
|
+
/**
|
|
21
|
+
* Name of a command's own tool (default: the id with every character other than letters,
|
|
22
|
+
* digits, `_` and `-` replaced by `_`, so `canvas.circle` is `canvas_circle`).
|
|
23
|
+
*/
|
|
24
|
+
toolName?: (id: string) => string;
|
|
14
25
|
}
|
|
15
26
|
/**
|
|
16
27
|
* Exposes a `CommandRegistry` to agents through a `ToolRegistry`:
|
|
@@ -26,6 +37,9 @@ export interface CommandToolProviderOptions<TContext = any> {
|
|
|
26
37
|
* registry with `history`) runs them as one undo step named `label` and takes everything
|
|
27
38
|
* back when one fails.
|
|
28
39
|
*
|
|
40
|
+
* With `tools`, chosen commands are also tools of their own (`canvas.circle` →
|
|
41
|
+
* `canvas_circle`, or `toolName`), taking the command's params as arguments.
|
|
42
|
+
*
|
|
29
43
|
* The id enum in `run_command`'s schema follows the registered commands, so the
|
|
30
44
|
* `ToolRegistry` announces `listChanged` when commands are added or removed.
|
|
31
45
|
*/
|
|
@@ -126,6 +126,13 @@ export interface DrawCommandTarget {
|
|
|
126
126
|
}>;
|
|
127
127
|
/** The dry paint presets a stroke can be brushed with (loads the paint engine). */
|
|
128
128
|
listBrushes(): Promise<CanvasBrushPreset[]>;
|
|
129
|
+
/** A node's box in canvas coordinates, so gestures can take `{ nodeId }` targets (without it they take boxes and points only). */
|
|
130
|
+
nodeBounds?(id: string): {
|
|
131
|
+
x: number;
|
|
132
|
+
y: number;
|
|
133
|
+
width: number;
|
|
134
|
+
height: number;
|
|
135
|
+
} | undefined;
|
|
129
136
|
}
|
|
130
137
|
export interface DrawCommandOptions {
|
|
131
138
|
/** Id prefix (default `canvas.`). */
|
|
@@ -144,7 +151,10 @@ export declare function planFreehandPlayback(points: unknown, max?: number): Pla
|
|
|
144
151
|
/**
|
|
145
152
|
* Agent / palette commands for freehand drawing: `canvas.drawFreehand` (a pen or highlighter
|
|
146
153
|
* stroke through given points, optionally brushed with a dry paint preset and a pressure / tilt
|
|
147
|
-
* profile; one undo step)
|
|
154
|
+
* profile; one undo step), the read-only `canvas.listBrushes` (the dry presets it accepts) and
|
|
155
|
+
* the annotation gestures `canvas.circle`, `canvas.underline`, `canvas.arrow`, `canvas.bracket`,
|
|
156
|
+
* `canvas.strike`, `canvas.cross` and `canvas.check` (hand-drawn marks around boxes, points or,
|
|
157
|
+
* when the target has `nodeBounds`, nodes).
|
|
148
158
|
*/
|
|
149
159
|
export declare function createDrawCommands(target: DrawCommandTarget, options?: DrawCommandOptions): CommandSpec[];
|
|
150
160
|
type ComponentActionResult = {
|
|
@@ -126,6 +126,13 @@ export interface DrawCommandTarget {
|
|
|
126
126
|
}>;
|
|
127
127
|
/** The dry paint presets a stroke can be brushed with (loads the paint engine). */
|
|
128
128
|
listBrushes(): Promise<CanvasBrushPreset[]>;
|
|
129
|
+
/** A node's box in canvas coordinates, so gestures can take `{ nodeId }` targets (without it they take boxes and points only). */
|
|
130
|
+
nodeBounds?(id: string): {
|
|
131
|
+
x: number;
|
|
132
|
+
y: number;
|
|
133
|
+
width: number;
|
|
134
|
+
height: number;
|
|
135
|
+
} | undefined;
|
|
129
136
|
}
|
|
130
137
|
export interface DrawCommandOptions {
|
|
131
138
|
/** Id prefix (default `canvas.`). */
|
|
@@ -144,7 +151,10 @@ export declare function planFreehandPlayback(points: unknown, max?: number): Pla
|
|
|
144
151
|
/**
|
|
145
152
|
* Agent / palette commands for freehand drawing: `canvas.drawFreehand` (a pen or highlighter
|
|
146
153
|
* stroke through given points, optionally brushed with a dry paint preset and a pressure / tilt
|
|
147
|
-
* profile; one undo step)
|
|
154
|
+
* profile; one undo step), the read-only `canvas.listBrushes` (the dry presets it accepts) and
|
|
155
|
+
* the annotation gestures `canvas.circle`, `canvas.underline`, `canvas.arrow`, `canvas.bracket`,
|
|
156
|
+
* `canvas.strike`, `canvas.cross` and `canvas.check` (hand-drawn marks around boxes, points or,
|
|
157
|
+
* when the target has `nodeBounds`, nodes).
|
|
148
158
|
*/
|
|
149
159
|
export declare function createDrawCommands(target: DrawCommandTarget, options?: DrawCommandOptions): CommandSpec[];
|
|
150
160
|
type ComponentActionResult = {
|
package/dist/commands/index.cjs
CHANGED
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
|
|
10
10
|
|
|
11
11
|
|
|
12
|
-
var
|
|
12
|
+
var _chunkCHAWTXBEcjs = require('../chunk-CHAWTXBE.cjs');
|
|
13
13
|
|
|
14
14
|
|
|
15
15
|
|
|
@@ -27,7 +27,7 @@ var _chunk53GOGBTMcjs = require('../chunk-53GOGBTM.cjs');
|
|
|
27
27
|
|
|
28
28
|
|
|
29
29
|
|
|
30
|
-
var
|
|
30
|
+
var _chunkT7QSEKDYcjs = require('../chunk-T7QSEKDY.cjs');
|
|
31
31
|
|
|
32
32
|
|
|
33
33
|
var _chunk3SLBXKAWcjs = require('../chunk-3SLBXKAW.cjs');
|
|
@@ -77,7 +77,7 @@ var CommandRegistry = (_class = class {
|
|
|
77
77
|
__init4() {this.muted = false}
|
|
78
78
|
constructor(options = {}) {;_class.prototype.__init.call(this);_class.prototype.__init2.call(this);_class.prototype.__init3.call(this);_class.prototype.__init4.call(this);
|
|
79
79
|
this.options = options;
|
|
80
|
-
this.shortcuts = new (0,
|
|
80
|
+
this.shortcuts = new (0, _chunkT7QSEKDYcjs.ShortcutMap)([], options.shortcuts);
|
|
81
81
|
this.shortcuts.subscribe(() => {
|
|
82
82
|
if (!this.muted) this.notify();
|
|
83
83
|
});
|
|
@@ -110,7 +110,7 @@ var CommandRegistry = (_class = class {
|
|
|
110
110
|
}
|
|
111
111
|
seen.add(s.id);
|
|
112
112
|
}
|
|
113
|
-
const bindings = specs.map((s) =>
|
|
113
|
+
const bindings = specs.map((s) => _chunkT7QSEKDYcjs.toShortcutBindings.call(void 0, s.id, s.shortcut, s.scope));
|
|
114
114
|
const unbinds = [];
|
|
115
115
|
this.muted = true;
|
|
116
116
|
try {
|
|
@@ -437,7 +437,7 @@ function createCommandPaletteController(registry, options = {}) {
|
|
|
437
437
|
id: ranked.entry.id,
|
|
438
438
|
label: ranked.entry.label,
|
|
439
439
|
...ranked.entry.group !== void 0 ? { group: ranked.entry.group } : {},
|
|
440
|
-
...ranked.entry.shortcuts[0] ? { shortcut:
|
|
440
|
+
...ranked.entry.shortcuts[0] ? { shortcut: _chunkT7QSEKDYcjs.formatShortcut.call(void 0, ranked.entry.shortcuts[0], platform) } : {},
|
|
441
441
|
enabled: ranked.entry.enabled,
|
|
442
442
|
...ranked.entry.disabledReason ? { disabledReason: ranked.entry.disabledReason } : {}
|
|
443
443
|
}));
|
|
@@ -556,7 +556,7 @@ function createCommandPaletteController(registry, options = {}) {
|
|
|
556
556
|
return controller;
|
|
557
557
|
}
|
|
558
558
|
function matchPaletteHotkey(event, hotkey, platform) {
|
|
559
|
-
const map = new (0,
|
|
559
|
+
const map = new (0, _chunkT7QSEKDYcjs.ShortcutMap)([{ command: "palette", chord: hotkey, allowInEditable: true }], platform ? { platform } : {});
|
|
560
560
|
return map.resolve(event) !== null;
|
|
561
561
|
}
|
|
562
562
|
|
|
@@ -806,13 +806,27 @@ function createCommandToolProvider(registry, options = {}) {
|
|
|
806
806
|
return failed > 0 ? { isError: true, content: [{ type: "text", text: JSON.stringify(summary) }], structuredContent: summary } : summary;
|
|
807
807
|
}
|
|
808
808
|
};
|
|
809
|
+
const picked = (id) => typeof options.tools === "function" ? options.tools(id) : !!_optionalChain([options, 'access', _26 => _26.tools, 'optionalAccess', _27 => _27.includes, 'call', _28 => _28(id)]);
|
|
810
|
+
const toolNameOf = (id) => _nullishCoalesce(_optionalChain([options, 'access', _29 => _29.toolName, 'optionalCall', _30 => _30(id)]), () => ( id.replace(/[^A-Za-z0-9_-]/g, "_")));
|
|
811
|
+
const commandTool = (entry) => ({
|
|
812
|
+
name: toolNameOf(entry.id),
|
|
813
|
+
title: entry.label,
|
|
814
|
+
description: `${_nullishCoalesce(entry.description, () => ( entry.label))}${entry.readOnly ? "" : ` (Runs the "${entry.id}" command; refused with the reason when it cannot run now.)`}`,
|
|
815
|
+
inputSchema: _nullishCoalesce(entry.params, () => ( { type: "object", properties: {}, additionalProperties: false })),
|
|
816
|
+
annotations: { title: entry.label, readOnlyHint: entry.readOnly, destructiveHint: !entry.readOnly, idempotentHint: entry.readOnly, openWorldHint: false },
|
|
817
|
+
plan: (args) => planOne(entry.id, args),
|
|
818
|
+
handler: async (args) => {
|
|
819
|
+
const result = await runOne(entry.id, args);
|
|
820
|
+
return result.ok ? toJson(result.result) : errorResult(result);
|
|
821
|
+
}
|
|
822
|
+
});
|
|
809
823
|
return {
|
|
810
824
|
id: _nullishCoalesce(options.id, () => ( "commands")),
|
|
811
825
|
namespace: options.namespace,
|
|
812
826
|
title: "Commands",
|
|
813
827
|
description: "The app's commands (menu and keyboard actions) with their params schemas: list them, run one, or run several as one undo step.",
|
|
814
828
|
skill: "pixerate-agent-tools",
|
|
815
|
-
tools: () => [listCommands, runCommandTool(), runCommands],
|
|
829
|
+
tools: () => [listCommands, runCommandTool(), runCommands, ...options.tools ? visible().filter((e) => picked(e.id)).map(commandTool) : []],
|
|
816
830
|
subscribe: (notify) => registry.subscribe(notify)
|
|
817
831
|
};
|
|
818
832
|
}
|
|
@@ -895,7 +909,7 @@ function createCanvasAnimationCommands(controller, options = {}) {
|
|
|
895
909
|
time: { type: "number", minimum: 0, description: "Time in ms (default: the playhead)." }
|
|
896
910
|
}
|
|
897
911
|
},
|
|
898
|
-
run: (_ctx, params) => controller.addKeyframe(_optionalChain([params, 'optionalAccess',
|
|
912
|
+
run: (_ctx, params) => controller.addKeyframe(_optionalChain([params, 'optionalAccess', _31 => _31.ids]), _optionalChain([params, 'optionalAccess', _32 => _32.properties]), _optionalChain([params, 'optionalAccess', _33 => _33.time]))
|
|
899
913
|
},
|
|
900
914
|
{
|
|
901
915
|
...base,
|
|
@@ -1029,4 +1043,4 @@ function createCanvasAnimationCommands(controller, options = {}) {
|
|
|
1029
1043
|
|
|
1030
1044
|
|
|
1031
1045
|
|
|
1032
|
-
exports.CommandRegistry = CommandRegistry; exports.CommandRegistryError = CommandRegistryError; exports.DEFAULT_HISTORY_SHORTCUTS =
|
|
1046
|
+
exports.CommandRegistry = CommandRegistry; exports.CommandRegistryError = CommandRegistryError; exports.DEFAULT_HISTORY_SHORTCUTS = _chunkCHAWTXBEcjs.DEFAULT_HISTORY_SHORTCUTS; exports.DEFAULT_RECENT_LIMIT = DEFAULT_RECENT_LIMIT; exports.PLATFORMS = _chunkT7QSEKDYcjs.PLATFORMS; exports.ShortcutMap = _chunkT7QSEKDYcjs.ShortcutMap; exports.chordToString = _chunkT7QSEKDYcjs.chordToString; exports.codeFromKey = _chunkT7QSEKDYcjs.codeFromKey; exports.codeToKeyText = _chunkT7QSEKDYcjs.codeToKeyText; exports.createArrangeCommands = _chunkCHAWTXBEcjs.createArrangeCommands; exports.createCanvasAnimationCommands = createCanvasAnimationCommands; exports.createCommandPaletteController = createCommandPaletteController; exports.createCommandRegistry = createCommandRegistry; exports.createCommandToolProvider = createCommandToolProvider; exports.createComponentCommands = _chunkCHAWTXBEcjs.createComponentCommands; exports.createDrawCommands = _chunkCHAWTXBEcjs.createDrawCommands; exports.createFormatCommands = _chunkVCL7CB56cjs.createFormatCommands; exports.createHistoryCommands = _chunkCHAWTXBEcjs.createHistoryCommands; exports.createShapeCommands = _chunkCHAWTXBEcjs.createShapeCommands; exports.createSpreadsheetCommands = _chunkCHAWTXBEcjs.createSpreadsheetCommands; exports.defineCommand = defineCommand; exports.detectPlatform = _chunkT7QSEKDYcjs.detectPlatform; exports.effectiveChord = _chunkT7QSEKDYcjs.effectiveChord; exports.effectiveChordKey = _chunkT7QSEKDYcjs.effectiveChordKey; exports.eventCode = _chunkT7QSEKDYcjs.eventCode; exports.exactBonus = exactBonus; exports.formatCommandsFor = _chunkVCL7CB56cjs.formatCommandsFor; exports.formatShortcut = _chunkT7QSEKDYcjs.formatShortcut; exports.fuzzyMatch = fuzzyMatch; exports.fuzzyScore = fuzzyScore; exports.hasVariantCommands = _chunkCHAWTXBEcjs.hasVariantCommands; exports.isEditableEventTarget = _chunkT7QSEKDYcjs.isEditableEventTarget; exports.keyToCode = _chunkT7QSEKDYcjs.keyToCode; exports.matchHistoryShortcut = _chunkCHAWTXBEcjs.matchHistoryShortcut; exports.matchPaletteHotkey = matchPaletteHotkey; exports.normalizeChord = _chunkT7QSEKDYcjs.normalizeChord; exports.parseChord = _chunkT7QSEKDYcjs.parseChord; exports.planFreehandPlayback = _chunkCHAWTXBEcjs.planFreehandPlayback; exports.pushRecent = pushRecent; exports.rankCommands = rankCommands; exports.shortcutCode = _chunkT7QSEKDYcjs.shortcutCode; exports.toShortcutBindings = _chunkT7QSEKDYcjs.toShortcutBindings;
|
package/dist/commands/index.js
CHANGED
|
@@ -9,7 +9,7 @@ import {
|
|
|
9
9
|
hasVariantCommands,
|
|
10
10
|
matchHistoryShortcut,
|
|
11
11
|
planFreehandPlayback
|
|
12
|
-
} from "../chunk-
|
|
12
|
+
} from "../chunk-XVIK73LS.js";
|
|
13
13
|
import {
|
|
14
14
|
PLATFORMS,
|
|
15
15
|
ShortcutMap,
|
|
@@ -27,7 +27,7 @@ import {
|
|
|
27
27
|
parseChord,
|
|
28
28
|
shortcutCode,
|
|
29
29
|
toShortcutBindings
|
|
30
|
-
} from "../chunk-
|
|
30
|
+
} from "../chunk-LPFQHVCO.js";
|
|
31
31
|
import {
|
|
32
32
|
derivePlaybackSteps
|
|
33
33
|
} from "../chunk-EHTX34RE.js";
|
|
@@ -806,13 +806,27 @@ function createCommandToolProvider(registry, options = {}) {
|
|
|
806
806
|
return failed > 0 ? { isError: true, content: [{ type: "text", text: JSON.stringify(summary) }], structuredContent: summary } : summary;
|
|
807
807
|
}
|
|
808
808
|
};
|
|
809
|
+
const picked = (id) => typeof options.tools === "function" ? options.tools(id) : !!options.tools?.includes(id);
|
|
810
|
+
const toolNameOf = (id) => options.toolName?.(id) ?? id.replace(/[^A-Za-z0-9_-]/g, "_");
|
|
811
|
+
const commandTool = (entry) => ({
|
|
812
|
+
name: toolNameOf(entry.id),
|
|
813
|
+
title: entry.label,
|
|
814
|
+
description: `${entry.description ?? entry.label}${entry.readOnly ? "" : ` (Runs the "${entry.id}" command; refused with the reason when it cannot run now.)`}`,
|
|
815
|
+
inputSchema: entry.params ?? { type: "object", properties: {}, additionalProperties: false },
|
|
816
|
+
annotations: { title: entry.label, readOnlyHint: entry.readOnly, destructiveHint: !entry.readOnly, idempotentHint: entry.readOnly, openWorldHint: false },
|
|
817
|
+
plan: (args) => planOne(entry.id, args),
|
|
818
|
+
handler: async (args) => {
|
|
819
|
+
const result = await runOne(entry.id, args);
|
|
820
|
+
return result.ok ? toJson(result.result) : errorResult(result);
|
|
821
|
+
}
|
|
822
|
+
});
|
|
809
823
|
return {
|
|
810
824
|
id: options.id ?? "commands",
|
|
811
825
|
namespace: options.namespace,
|
|
812
826
|
title: "Commands",
|
|
813
827
|
description: "The app's commands (menu and keyboard actions) with their params schemas: list them, run one, or run several as one undo step.",
|
|
814
828
|
skill: "pixerate-agent-tools",
|
|
815
|
-
tools: () => [listCommands, runCommandTool(), runCommands],
|
|
829
|
+
tools: () => [listCommands, runCommandTool(), runCommands, ...options.tools ? visible().filter((e) => picked(e.id)).map(commandTool) : []],
|
|
816
830
|
subscribe: (notify) => registry.subscribe(notify)
|
|
817
831
|
};
|
|
818
832
|
}
|