@unofficialbox/box-open-elements 0.32.0 → 0.34.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.
@@ -31,6 +31,12 @@ export interface ProcessBox<N = unknown> {
31
31
  /** Show the loop mark in a repeating frame without inferring host semantics from its kind name. */
32
32
  loopMark?: boolean;
33
33
  parentId?: string;
34
+ /** Present (including []) when this host supports variables local to this step/frame. */
35
+ localVariables?: readonly ProcessLocalVariable[];
36
+ /** Explicit opt-in to host-owned local edit requests; absent collections are readonly. */
37
+ localVariablesEditable?: boolean;
38
+ /** Host-owned saved output name, displayed in the variable usage summary. */
39
+ savedResult?: string;
34
40
  }
35
41
  export interface ProcessLine {
36
42
  id: string;
@@ -63,6 +69,29 @@ export interface ProcessVariable {
63
69
  startingValue?: string;
64
70
  problem?: string;
65
71
  }
72
+ export interface ProcessLocalVariable {
73
+ name: string;
74
+ startingValue?: string;
75
+ /** Plain-text host validation; BOE does not evaluate expressions. */
76
+ problem?: string;
77
+ }
78
+ export type ProcessLocalVariableEdit = {
79
+ type: 'add';
80
+ } | {
81
+ type: 'remove';
82
+ index: number;
83
+ name: string;
84
+ } | {
85
+ type: 'rename' | 'starting-value';
86
+ index: number;
87
+ name: string;
88
+ value: string;
89
+ };
90
+ export interface ProcessLocalVariableEditRequest {
91
+ boxId: string;
92
+ path?: NodePath;
93
+ edit: ProcessLocalVariableEdit;
94
+ }
66
95
  /** Host-owned variable edits; the host echoes the updated variables property. */
67
96
  export type ProcessVariableEdit = {
68
97
  type: 'add';
@@ -73,6 +102,10 @@ export type ProcessVariableEdit = {
73
102
  type: 'rename';
74
103
  name: string;
75
104
  value: string;
105
+ } | {
106
+ type: 'description';
107
+ name: string;
108
+ value: string;
76
109
  } | {
77
110
  type: 'scope';
78
111
  name: string;
@@ -85,6 +118,32 @@ export interface ProcessOutlineItem {
85
118
  boxId?: string;
86
119
  children?: readonly ProcessOutlineItem[];
87
120
  }
121
+ /** Host-authored expression presentation; BOE does not infer scope or evaluate CEL. */
122
+ export interface ProcessExpressionField {
123
+ /** Complete ordered scope; [] suppresses legacy global-variable chips. */
124
+ variables?: readonly {
125
+ name: string;
126
+ description?: string;
127
+ }[];
128
+ /** Values greater than one render a textarea. */
129
+ rows?: number;
130
+ /** Error feedback uses ProcessField.problem and takes precedence. */
131
+ feedback?: {
132
+ message: string;
133
+ tone?: 'neutral' | 'success';
134
+ };
135
+ help?: {
136
+ summary: string;
137
+ examples: readonly {
138
+ expression: string;
139
+ description: string;
140
+ segments?: readonly {
141
+ text: string;
142
+ format?: 'code' | 'text';
143
+ }[];
144
+ }[];
145
+ };
146
+ }
88
147
  /** Host-supplied field values; the modeler draws controls and requests edits. */
89
148
  export interface ProcessField {
90
149
  key: string;
@@ -101,6 +160,7 @@ export interface ProcessField {
101
160
  required?: boolean;
102
161
  disabled?: boolean;
103
162
  problem?: string;
163
+ expression?: ProcessExpressionField;
104
164
  }
105
165
  export interface ProcessPositionSnapshot {
106
166
  path?: NodePath;
@@ -153,6 +213,9 @@ export interface ProcessModel<D = unknown, N = unknown> {
153
213
  /** Pure synchronous host rule: a nonempty reason rejects preview and commit.
154
214
  * Returning null permits an edit request; the host must still accept it. */
155
215
  connectionProblem?(document: D, proposal: ProcessConnectionProposal, projection: ProcessProjection<N>): string | null;
216
+ /** Optional synchronous host transaction for Tidy/section semantics.
217
+ * A capable host accepts or refuses; BOE does not fall back to local edits. */
218
+ layoutEdit?(document: D, request: ProcessLayoutEditRequest, projection: ProcessProjection<N>): void;
156
219
  /** Optional host arrangement, used by Tidy up and for missing positions. */
157
220
  arrange?(projection: ProcessProjection<N>): ProcessLayout;
158
221
  /**
@@ -197,8 +260,41 @@ export interface ProcessCheck {
197
260
  boxId?: string;
198
261
  path?: NodePath;
199
262
  }
263
+ /** Insertion intent; explicit centers use canvas world coordinates, not top-left positions. */
264
+ export type ProcessInsertionPlacement = {
265
+ readonly source: 'direction';
266
+ readonly side: ProcessSide;
267
+ } | {
268
+ readonly source: 'next';
269
+ } | {
270
+ readonly source: 'line';
271
+ readonly center: Readonly<{
272
+ x: number;
273
+ y: number;
274
+ }>;
275
+ } | {
276
+ readonly source: 'point';
277
+ readonly center: Readonly<{
278
+ x: number;
279
+ y: number;
280
+ }>;
281
+ };
282
+ /** IDs are scoped by kind; layout notes are separate from projected boxes. */
283
+ export type ProcessSelectionItem = {
284
+ readonly type: 'box';
285
+ readonly id: string;
286
+ } | {
287
+ readonly type: 'line';
288
+ readonly id: string;
289
+ } | {
290
+ readonly type: 'note';
291
+ readonly id: string;
292
+ };
200
293
  export interface ProcessEdit {
201
- type: "add" | "delete" | "duplicate" | "connect" | "disconnect" | "reattach" | "insert" | "reparent" | "reset-line";
294
+ type: "add" | "delete" | "duplicate" | "connect" | "disconnect" | "reattach" | "insert" | "reparent" | "reset-line" | "tidy" | "make-section" | "delete-selection";
295
+ /** One atomic mixed deletion; the host owns protected roots, descendants,
296
+ * incident edges and notes. Unsupported hosts must leave it unapplied. */
297
+ selection?: readonly ProcessSelectionItem[];
202
298
  boxId?: string;
203
299
  sourceId?: string;
204
300
  /** Duplicate these roots and descendants/internal edges in one host transaction.
@@ -214,6 +310,8 @@ export interface ProcessEdit {
214
310
  lineId?: string;
215
311
  kind?: FlowKind;
216
312
  position?: BoxPosition;
313
+ /** Optional for existing hosts; all built-in insertion producers supply intent. */
314
+ placement?: ProcessInsertionPlacement;
217
315
  parentId?: string;
218
316
  fromSide?: ProcessSide;
219
317
  toSide?: ProcessSide;
@@ -228,11 +326,27 @@ export interface ReversibleProcessEdit {
228
326
  layout?: ProcessLayout;
229
327
  /** Selection after acceptance; recorded with layout for undo and redo. */
230
328
  selectionIds?: readonly string[];
329
+ /** Full mixed selection after acceptance; takes precedence over selectionIds. */
330
+ selection?: readonly ProcessSelectionItem[];
231
331
  }
232
332
  /** Host applies the edit, then calls accept with its inverse and replay. */
233
333
  export interface ProcessEditRequest extends ProcessEdit {
234
334
  accept(command: ReversibleProcessEdit): void;
235
335
  }
336
+ /** Host-owned document/layout operation. Null sourceIds means whole-process Tidy.
337
+ * The host owns eligibility, section membership, route cleanup and related notes. */
338
+ export interface ProcessLayoutEditRequest {
339
+ readonly type: 'tidy' | 'make-section';
340
+ readonly sourceIds: readonly string[] | null;
341
+ readonly title?: string;
342
+ /** Detached current layout; a host may use it to preserve unrelated data. */
343
+ readonly layout: ProcessLayout;
344
+ /** Host has already applied the document edit; full layout is required. */
345
+ accept(command: ReversibleProcessEdit & {
346
+ layout: ProcessLayout;
347
+ }): void;
348
+ refuse(message?: string): void;
349
+ }
236
350
  /** Host-owned immutable capture; BOE never serializes the captured graph. */
237
351
  export interface ProcessClipboard {
238
352
  readonly itemCount: number;
@@ -241,6 +355,9 @@ export interface ProcessClipboard {
241
355
  }
242
356
  /** Copy capture is synchronous and once-only. Unsupported hosts leave it unhandled. */
243
357
  export interface ProcessCopyRequest {
358
+ /** Full immutable selection, including notes and explicit edges. Hosts own
359
+ * descendant/internal-edge capture and must refuse unsupported mixed capture. */
360
+ readonly selection?: readonly ProcessSelectionItem[];
244
361
  readonly sourceIds: readonly string[];
245
362
  capture(clipboard: ProcessClipboard): void;
246
363
  refuse(message?: string): void;
@@ -1,7 +1,44 @@
1
1
  import { BaseElement } from "../../core/index.js";
2
2
  import type { NodePath } from "../flow-builder/model.js";
3
3
  import type { ProcessConnection, ProcessVariable, ProcessLoadOptions, ProcessKind, ProcessLastRun, ProcessOutlineItem, ProcessField } from "./model.js";
4
- import { ProcessHistory, type ProcessBox, type ProcessCheck, type ProcessEdit, type ProcessLayout, type ProcessModel, type ProcessProjection } from "./model.js";
4
+ import { ProcessHistory, type ProcessBox, type ProcessCheck, type ProcessEdit, type ProcessSelectionItem, type ProcessCopyRequest, type ProcessLayout, type ProcessModel, type ProcessProjection } from "./model.js";
5
+ /** Source-owned contracts for notifications forwarded through the acceptance queue. */
6
+ export interface ProcessModelerEventDetails {
7
+ 'note-move-request': {
8
+ noteIds: readonly string[];
9
+ notes: readonly NonNullable<ProcessLayout['notes']>[number][];
10
+ };
11
+ 'process-copy-request': ProcessCopyRequest;
12
+ 'process-selection-copy-request': ProcessCopyRequest;
13
+ 'layout-changed': {
14
+ layout: ProcessLayout;
15
+ };
16
+ 'positions-changed': {
17
+ positions: readonly import('./model.js').ProcessPositionSnapshot[];
18
+ version: string | number;
19
+ };
20
+ 'projection-changed': {
21
+ projection: ProcessProjection;
22
+ version: string | number;
23
+ checks: readonly ProcessCheck[];
24
+ };
25
+ 'readable-projection-changed': {
26
+ projection: ProcessProjection;
27
+ version: string | number;
28
+ };
29
+ 'selection-changed': {
30
+ selection?: readonly ProcessSelectionItem[];
31
+ box: ProcessBox | null;
32
+ boxes: readonly ProcessBox[];
33
+ path: NodePath | null;
34
+ } | {
35
+ selection?: readonly ProcessSelectionItem[];
36
+ box: null;
37
+ boxes: never[];
38
+ line: import('./model.js').ProcessLine | null;
39
+ path: null;
40
+ };
41
+ }
5
42
  /** Projects host documents without owning workflow schemas or persistence. */
6
43
  export declare class ProcessModeler<D = ProcessProjection, N = unknown> extends BaseElement {
7
44
  static readonly tagName = "box-process-modeler";
@@ -16,6 +53,9 @@ export declare class ProcessModeler<D = ProcessProjection, N = unknown> extends
16
53
  private showLastRunValue;
17
54
  private selectedId;
18
55
  private selectedLineId;
56
+ private selectedLineIds;
57
+ private selectedNoteIds;
58
+ private graphSelection;
19
59
  private connecting;
20
60
  private checks;
21
61
  private renderer?;
@@ -23,6 +63,8 @@ export declare class ProcessModeler<D = ProcessProjection, N = unknown> extends
23
63
  private inspected?;
24
64
  private inspectedId?;
25
65
  private inspectedControls;
66
+ private localEchoRevision;
67
+ private pendingLocalRename?;
26
68
  private historyValue;
27
69
  private viewport;
28
70
  private pointers;
@@ -39,6 +81,11 @@ export declare class ProcessModeler<D = ProcessProjection, N = unknown> extends
39
81
  private selectedIds;
40
82
  private clipboard;
41
83
  private clipboardSession;
84
+ private layoutEditSession;
85
+ private acceptanceNotifications;
86
+ private deferredNotifications;
87
+ private notify;
88
+ private flushAcceptanceNotifications;
42
89
  private restoringBoxFocus;
43
90
  private selectionToolbarKey;
44
91
  private sectionSequence;
@@ -114,6 +161,10 @@ export declare class ProcessModeler<D = ProcessProjection, N = unknown> extends
114
161
  }>;
115
162
  load(document: D, options?: ProcessLoadOptions): void;
116
163
  selectMany(ids: readonly string[]): void;
164
+ /** Detached mixed selection. Invalid and duplicate IDs are ignored by selectItems. */
165
+ get selection(): readonly ProcessSelectionItem[];
166
+ selectItems(items: readonly ProcessSelectionItem[]): void;
167
+ private clearMixedSelection;
117
168
  get headingLevel(): number;
118
169
  set headingLevel(value: number);
119
170
  get disableConnections(): boolean;
@@ -158,6 +209,7 @@ export declare class ProcessModeler<D = ProcessProjection, N = unknown> extends
158
209
  private editAcceptance;
159
210
  undo(): void;
160
211
  redo(): void;
212
+ private requestLayoutEdit;
161
213
  private commitLayout;
162
214
  move(id: string, x: number, y: number): void;
163
215
  private emitPositions;
@@ -180,6 +232,9 @@ export declare class ProcessModeler<D = ProcessProjection, N = unknown> extends
180
232
  private minimapBounds;
181
233
  private bounds;
182
234
  protected renderTemplate(): void;
235
+ private viewMenuDocument?;
236
+ private syncViewMenuDismissal;
237
+ private dismissViewMenuOutside;
183
238
  private setupPanes;
184
239
  private openDrawer;
185
240
  private closeDrawer;
@@ -237,6 +292,8 @@ export declare class ProcessModeler<D = ProcessProjection, N = unknown> extends
237
292
  private renderChecks;
238
293
  private renderField;
239
294
  private renderSelection;
295
+ private renderLocalVariables;
296
+ private requestLocalVariableEdit;
240
297
  private renderSelectionToolbar;
241
298
  private updateToolbar;
242
299
  private paintViewport;