@codefluss/base-types 0.0.2-alpha.1 → 0.0.2-alpha.2
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/common-types.d.ts +253 -26
- package/dist/common-types.d.ts.map +1 -1
- package/dist/common-types.js +8 -1
- package/dist/common-types.js.map +1 -1
- package/dist/dependencies.d.ts +545 -106
- package/dist/dependencies.d.ts.map +1 -1
- package/dist/dependencies.js +12 -2
- package/dist/dependencies.js.map +1 -1
- package/dist/plugin-system.d.ts +809 -204
- package/dist/plugin-system.d.ts.map +1 -1
- package/dist/plugin-system.js +8 -0
- package/dist/plugin-system.js.map +1 -1
- package/package.json +1 -1
- package/src/common-types.ts +286 -30
- package/src/dependencies.ts +770 -180
- package/src/plugin-system.ts +935 -263
package/src/plugin-system.ts
CHANGED
|
@@ -4,454 +4,1030 @@
|
|
|
4
4
|
* Core types for the headless plugin architecture.
|
|
5
5
|
* These types define the contract between plugins and the Context Panel UI.
|
|
6
6
|
*
|
|
7
|
+
* The plugin system uses a **headless** approach: plugins declare metadata
|
|
8
|
+
* (properties, capabilities, UI config) and the host application renders
|
|
9
|
+
* appropriate controls automatically in the Context Panel.
|
|
10
|
+
*
|
|
11
|
+
* @see {@link PluginConfig} — Top-level plugin definition
|
|
12
|
+
* @see {@link PropertyDefinition} — How plugins declare editable properties
|
|
13
|
+
* @see {@link PluginCapabilities} — How plugins declare structural behavior
|
|
14
|
+
*
|
|
7
15
|
* @package @codefluss/base-types
|
|
8
16
|
* @version 1.0.0
|
|
9
17
|
*/
|
|
10
18
|
|
|
11
|
-
import type { ComponentType } from
|
|
12
|
-
import type { PluginDesignSystem, PluginUtils } from
|
|
19
|
+
import type { ComponentType } from 'react';
|
|
20
|
+
import type { PluginDesignSystem, PluginUtils } from './dependencies';
|
|
13
21
|
|
|
14
22
|
/**
|
|
15
|
-
* Property control type
|
|
16
|
-
*
|
|
23
|
+
* Property control type — determines which UI widget the Context Panel
|
|
24
|
+
* renders for a given property.
|
|
25
|
+
*
|
|
26
|
+
* Each value maps to a specific editor control component.
|
|
27
|
+
* The control's behavior is further configured via the corresponding
|
|
28
|
+
* field in {@link PropertyUIConfig}.
|
|
29
|
+
*
|
|
30
|
+
* @see {@link PropertyUIConfig} for per-control configuration
|
|
31
|
+
*
|
|
32
|
+
* @example
|
|
33
|
+
* ```typescript
|
|
34
|
+
* // A slider control for font size
|
|
35
|
+
* const property: PropertyDefinition = {
|
|
36
|
+
* key: 'style.fontSize',
|
|
37
|
+
* type: 'range',
|
|
38
|
+
* label: 'Font Size',
|
|
39
|
+
* default: 16,
|
|
40
|
+
* ui: {
|
|
41
|
+
* control: 'slider',
|
|
42
|
+
* slider: { min: 8, max: 72, step: 1, unit: 'px' },
|
|
43
|
+
* },
|
|
44
|
+
* };
|
|
45
|
+
* ```
|
|
17
46
|
*/
|
|
18
47
|
export type PropertyControlType =
|
|
19
|
-
|
|
|
20
|
-
|
|
|
21
|
-
|
|
|
22
|
-
|
|
|
23
|
-
|
|
|
24
|
-
|
|
|
25
|
-
|
|
|
26
|
-
|
|
|
27
|
-
|
|
|
28
|
-
|
|
|
29
|
-
|
|
|
30
|
-
|
|
|
31
|
-
|
|
|
32
|
-
|
|
|
33
|
-
|
|
|
34
|
-
|
|
|
35
|
-
|
|
|
36
|
-
|
|
|
37
|
-
|
|
|
38
|
-
|
|
39
|
-
/**
|
|
40
|
-
*
|
|
41
|
-
*
|
|
48
|
+
| 'input'
|
|
49
|
+
| 'slider'
|
|
50
|
+
| 'select'
|
|
51
|
+
| 'color-picker'
|
|
52
|
+
| 'toggle'
|
|
53
|
+
| 'textarea'
|
|
54
|
+
| 'number-input'
|
|
55
|
+
| 'number-with-unit' // Container-specific
|
|
56
|
+
| 'box-model'
|
|
57
|
+
| 'spacing' // Combined margin + padding control
|
|
58
|
+
| 'spacing-combined' // Combined margin + padding control (UI variant)
|
|
59
|
+
| 'grid' // Container-specific
|
|
60
|
+
| 'typography-toolbar'
|
|
61
|
+
| 'gradient-editor'
|
|
62
|
+
| 'border-editor'
|
|
63
|
+
| 'font-preset-select' // Design System font presets
|
|
64
|
+
| 'color-preset-select' // Design System color presets
|
|
65
|
+
| 'text-align-toggle' // Horizontal text alignment toggle buttons
|
|
66
|
+
| 'vertical-align-toggle'; // Vertical alignment toggle buttons (align-self)
|
|
67
|
+
|
|
68
|
+
/**
|
|
69
|
+
* Semantic type of a property value.
|
|
70
|
+
*
|
|
71
|
+
* While {@link PropertyControlType} determines the *UI widget*,
|
|
72
|
+
* `PropertyType` describes the *semantic meaning* of the stored value.
|
|
73
|
+
* A single `PropertyType` may be rendered by different controls depending
|
|
74
|
+
* on the plugin's UI configuration.
|
|
75
|
+
*
|
|
76
|
+
* @see {@link PropertyControlType} for the UI control counterpart
|
|
77
|
+
* @see {@link PropertyDefinition.type}
|
|
42
78
|
*/
|
|
43
79
|
export type PropertyType =
|
|
44
|
-
|
|
|
45
|
-
|
|
|
46
|
-
|
|
|
47
|
-
|
|
|
48
|
-
|
|
|
49
|
-
|
|
|
50
|
-
|
|
|
51
|
-
|
|
|
52
|
-
|
|
|
53
|
-
|
|
|
54
|
-
|
|
|
55
|
-
|
|
|
56
|
-
|
|
|
57
|
-
|
|
|
58
|
-
|
|
|
80
|
+
| 'text'
|
|
81
|
+
| 'number'
|
|
82
|
+
| 'range'
|
|
83
|
+
| 'select'
|
|
84
|
+
| 'color'
|
|
85
|
+
| 'toggle'
|
|
86
|
+
| 'multiLangText'
|
|
87
|
+
| 'boxModel'
|
|
88
|
+
| 'box-model'
|
|
89
|
+
| 'spacing' // Combined margin + padding
|
|
90
|
+
| 'spacing-combined' // Combined margin + padding (UI variant)
|
|
91
|
+
| 'grid'
|
|
92
|
+
| 'toolbar'
|
|
93
|
+
| 'gradient'
|
|
94
|
+
| 'border';
|
|
59
95
|
|
|
60
96
|
/**
|
|
61
|
-
*
|
|
97
|
+
* Organizational category for properties in the Context Panel.
|
|
98
|
+
*
|
|
99
|
+
* Properties are grouped into collapsible sections by category,
|
|
100
|
+
* providing a consistent editing experience across all plugins.
|
|
101
|
+
*
|
|
102
|
+
* - `'content'` — Text, media, and data properties (shown first)
|
|
103
|
+
* - `'style'` — Visual appearance: colors, typography, backgrounds
|
|
104
|
+
* - `'layout'` — Spacing, positioning, grid/flexbox settings
|
|
105
|
+
* - `'advanced'` — CSS classes, ARIA labels, HTML tags, z-index
|
|
106
|
+
*
|
|
107
|
+
* @see {@link PropertyDefinition.category}
|
|
62
108
|
*/
|
|
63
|
-
export type PropertyCategory =
|
|
109
|
+
export type PropertyCategory = 'content' | 'style' | 'layout' | 'advanced';
|
|
64
110
|
|
|
65
111
|
/**
|
|
66
|
-
*
|
|
112
|
+
* Configuration for slider UI controls.
|
|
113
|
+
*
|
|
114
|
+
* @see {@link PropertyUIConfig.slider}
|
|
115
|
+
*
|
|
116
|
+
* @example
|
|
117
|
+
* ```typescript
|
|
118
|
+
* const sliderConfig: SliderConfig = {
|
|
119
|
+
* min: 0,
|
|
120
|
+
* max: 100,
|
|
121
|
+
* step: 1,
|
|
122
|
+
* showValue: true,
|
|
123
|
+
* unit: 'px',
|
|
124
|
+
* };
|
|
125
|
+
* ```
|
|
67
126
|
*/
|
|
68
127
|
export interface SliderConfig {
|
|
128
|
+
/** Minimum allowed value */
|
|
69
129
|
min: number;
|
|
130
|
+
|
|
131
|
+
/** Maximum allowed value */
|
|
70
132
|
max: number;
|
|
133
|
+
|
|
134
|
+
/** Increment step between values */
|
|
71
135
|
step: number;
|
|
136
|
+
|
|
137
|
+
/**
|
|
138
|
+
* Whether to display the current numeric value next to the slider
|
|
139
|
+
* @default false
|
|
140
|
+
*/
|
|
72
141
|
showValue?: boolean;
|
|
142
|
+
|
|
143
|
+
/**
|
|
144
|
+
* Unit label displayed after the value (e.g., `'px'`, `'%'`, `'em'`)
|
|
145
|
+
* @default undefined
|
|
146
|
+
*/
|
|
73
147
|
unit?: string; // 'px', '%', 'em', etc.
|
|
148
|
+
|
|
149
|
+
/**
|
|
150
|
+
* Discrete labeled positions on the slider track
|
|
151
|
+
* @default undefined
|
|
152
|
+
*/
|
|
74
153
|
marks?: Array<{ value: number; label: string }>;
|
|
75
154
|
}
|
|
76
155
|
|
|
77
156
|
/**
|
|
78
|
-
*
|
|
157
|
+
* Configuration for numeric input controls.
|
|
158
|
+
*
|
|
159
|
+
* All fields are optional — unset fields inherit sensible browser defaults.
|
|
160
|
+
*
|
|
161
|
+
* @see {@link PropertyUIConfig.number}
|
|
162
|
+
*
|
|
163
|
+
* @example
|
|
164
|
+
* ```typescript
|
|
165
|
+
* const numberConfig: NumberConfig = {
|
|
166
|
+
* min: 0,
|
|
167
|
+
* max: 9999,
|
|
168
|
+
* step: 1,
|
|
169
|
+
* unit: 'px',
|
|
170
|
+
* };
|
|
171
|
+
* ```
|
|
79
172
|
*/
|
|
80
173
|
export interface NumberConfig {
|
|
174
|
+
/** Minimum allowed value */
|
|
81
175
|
min?: number;
|
|
176
|
+
|
|
177
|
+
/** Maximum allowed value */
|
|
82
178
|
max?: number;
|
|
179
|
+
|
|
180
|
+
/** Increment step */
|
|
83
181
|
step?: number;
|
|
182
|
+
|
|
183
|
+
/**
|
|
184
|
+
* Unit label displayed after the value (e.g., `'px'`, `'%'`, `'em'`)
|
|
185
|
+
* @default undefined
|
|
186
|
+
*/
|
|
84
187
|
unit?: string; // 'px', '%', 'em', etc.
|
|
85
188
|
}
|
|
86
189
|
|
|
87
190
|
/**
|
|
88
|
-
*
|
|
191
|
+
* Configuration for number-with-unit controls (primarily used by containers).
|
|
192
|
+
*
|
|
193
|
+
* Unlike {@link NumberConfig}, this control lets the user **switch between
|
|
194
|
+
* multiple CSS units** via a dropdown alongside the numeric input.
|
|
195
|
+
*
|
|
196
|
+
* @see {@link PropertyUIConfig.numberWithUnit}
|
|
197
|
+
*
|
|
198
|
+
* @example
|
|
199
|
+
* ```typescript
|
|
200
|
+
* // Container max-width control
|
|
201
|
+
* const config: NumberWithUnitConfig = {
|
|
202
|
+
* min: 0,
|
|
203
|
+
* max: 9999,
|
|
204
|
+
* step: 10,
|
|
205
|
+
* units: ['px', '%', 'rem', 'ch', 'vw', 'auto'],
|
|
206
|
+
* defaultUnit: 'px',
|
|
207
|
+
* allowEmpty: true,
|
|
208
|
+
* };
|
|
209
|
+
* ```
|
|
89
210
|
*/
|
|
90
211
|
export interface NumberWithUnitConfig {
|
|
212
|
+
/** Minimum allowed value */
|
|
91
213
|
min?: number;
|
|
214
|
+
|
|
215
|
+
/** Maximum allowed value */
|
|
92
216
|
max?: number;
|
|
217
|
+
|
|
218
|
+
/** Increment step */
|
|
93
219
|
step?: number;
|
|
220
|
+
|
|
221
|
+
/**
|
|
222
|
+
* Available CSS units the user can select
|
|
223
|
+
* @default undefined
|
|
224
|
+
* @example ['px', '%', 'em', 'rem', 'vw', 'vh']
|
|
225
|
+
*/
|
|
94
226
|
units?: string[]; // ['px', '%', 'em', 'rem', 'vw', 'vh']
|
|
227
|
+
|
|
228
|
+
/**
|
|
229
|
+
* Initially selected unit
|
|
230
|
+
* @default undefined
|
|
231
|
+
*/
|
|
95
232
|
defaultUnit?: string;
|
|
233
|
+
|
|
234
|
+
/**
|
|
235
|
+
* Whether the field accepts empty / null values.
|
|
236
|
+
* Typically `true` for container properties like `minHeight` or `maxWidth`
|
|
237
|
+
* where "auto" or no value is meaningful.
|
|
238
|
+
* @default undefined
|
|
239
|
+
*/
|
|
96
240
|
allowEmpty?: boolean; // Allow empty/null values (container-specific)
|
|
97
241
|
}
|
|
98
242
|
|
|
99
243
|
/**
|
|
100
|
-
*
|
|
244
|
+
* Configuration for select / dropdown controls.
|
|
245
|
+
*
|
|
246
|
+
* @see {@link PropertyUIConfig.select}
|
|
247
|
+
*
|
|
248
|
+
* @example
|
|
249
|
+
* ```typescript
|
|
250
|
+
* const selectConfig: SelectConfig = {
|
|
251
|
+
* options: [
|
|
252
|
+
* { value: 'flexbox', label: 'Flexbox' },
|
|
253
|
+
* { value: 'grid', label: 'Grid' },
|
|
254
|
+
* ],
|
|
255
|
+
* searchable: false,
|
|
256
|
+
* };
|
|
257
|
+
* ```
|
|
101
258
|
*/
|
|
102
259
|
export interface SelectConfig {
|
|
260
|
+
/** Available options for the dropdown */
|
|
103
261
|
options: Array<{ value: string; label: string; icon?: ComponentType }>;
|
|
262
|
+
|
|
263
|
+
/**
|
|
264
|
+
* Enable type-ahead search filtering for long option lists
|
|
265
|
+
* @default false
|
|
266
|
+
*/
|
|
104
267
|
searchable?: boolean;
|
|
105
268
|
}
|
|
106
269
|
|
|
107
270
|
/**
|
|
108
|
-
*
|
|
271
|
+
* Configuration for single-line text input controls.
|
|
272
|
+
*
|
|
273
|
+
* @see {@link PropertyUIConfig.input}
|
|
109
274
|
*/
|
|
110
275
|
export interface InputConfig {
|
|
276
|
+
/**
|
|
277
|
+
* Placeholder text shown when the input is empty
|
|
278
|
+
* @example 'e.g., custom-class my-style'
|
|
279
|
+
*/
|
|
111
280
|
placeholder?: string;
|
|
281
|
+
|
|
282
|
+
/** Regex pattern for client-side validation */
|
|
112
283
|
pattern?: RegExp;
|
|
284
|
+
|
|
285
|
+
/** Message shown when validation fails */
|
|
113
286
|
validationMessage?: string;
|
|
114
287
|
}
|
|
115
288
|
|
|
116
289
|
/**
|
|
117
|
-
*
|
|
290
|
+
* Configuration for color picker controls.
|
|
291
|
+
*
|
|
292
|
+
* @see {@link PropertyUIConfig.colorPicker}
|
|
293
|
+
*
|
|
294
|
+
* @example
|
|
295
|
+
* ```typescript
|
|
296
|
+
* const colorConfig: ColorPickerConfig = {
|
|
297
|
+
* format: 'hex',
|
|
298
|
+
* alpha: true,
|
|
299
|
+
* presets: ['#ff0000', '#00ff00', '#0000ff'],
|
|
300
|
+
* };
|
|
301
|
+
* ```
|
|
118
302
|
*/
|
|
119
303
|
export interface ColorPickerConfig {
|
|
120
|
-
|
|
304
|
+
/**
|
|
305
|
+
* Output color format
|
|
306
|
+
* @default 'hex'
|
|
307
|
+
*/
|
|
308
|
+
format?: 'hex' | 'rgb' | 'hsl';
|
|
309
|
+
|
|
310
|
+
/**
|
|
311
|
+
* Whether to allow alpha (transparency) channel
|
|
312
|
+
* @default false
|
|
313
|
+
*/
|
|
121
314
|
alpha?: boolean;
|
|
315
|
+
|
|
316
|
+
/** Preset color swatches shown for quick selection */
|
|
122
317
|
presets?: string[];
|
|
123
318
|
}
|
|
124
319
|
|
|
125
320
|
/**
|
|
126
|
-
*
|
|
321
|
+
* Configuration for multi-line textarea controls.
|
|
322
|
+
*
|
|
323
|
+
* @see {@link PropertyUIConfig.textarea}
|
|
324
|
+
*
|
|
325
|
+
* @example
|
|
326
|
+
* ```typescript
|
|
327
|
+
* const textareaConfig: TextareaConfig = {
|
|
328
|
+
* rows: 1,
|
|
329
|
+
* autoResize: true,
|
|
330
|
+
* };
|
|
331
|
+
* ```
|
|
127
332
|
*/
|
|
128
333
|
export interface TextareaConfig {
|
|
334
|
+
/**
|
|
335
|
+
* Initial number of visible text rows
|
|
336
|
+
* @default 3
|
|
337
|
+
*/
|
|
129
338
|
rows?: number;
|
|
339
|
+
|
|
340
|
+
/**
|
|
341
|
+
* Automatically grow the textarea height to fit content
|
|
342
|
+
* @default false
|
|
343
|
+
*/
|
|
130
344
|
autoResize?: boolean;
|
|
345
|
+
|
|
346
|
+
/** Placeholder text shown when empty */
|
|
131
347
|
placeholder?: string;
|
|
132
348
|
}
|
|
133
349
|
|
|
134
350
|
/**
|
|
135
|
-
*
|
|
351
|
+
* Configuration for box-model (margin/padding) controls.
|
|
352
|
+
*
|
|
353
|
+
* Renders a four-sided input (top, right, bottom, left) with
|
|
354
|
+
* optional linked-sides mode.
|
|
355
|
+
*
|
|
356
|
+
* @see {@link PropertyUIConfig.boxModel}
|
|
357
|
+
* @see {@link SpacingConfig} for the combined margin + padding variant
|
|
136
358
|
*/
|
|
137
359
|
export interface BoxModelConfig {
|
|
360
|
+
/** Minimum value per side */
|
|
138
361
|
min?: number;
|
|
362
|
+
|
|
363
|
+
/** Maximum value per side */
|
|
139
364
|
max?: number;
|
|
365
|
+
|
|
366
|
+
/**
|
|
367
|
+
* CSS unit for all sides
|
|
368
|
+
* @default 'px'
|
|
369
|
+
*/
|
|
140
370
|
unit?: string;
|
|
371
|
+
|
|
372
|
+
/**
|
|
373
|
+
* Whether all four sides are linked (same value) by default
|
|
374
|
+
* @default false
|
|
375
|
+
*/
|
|
141
376
|
linkedByDefault?: boolean;
|
|
142
377
|
}
|
|
143
378
|
|
|
144
379
|
/**
|
|
145
|
-
*
|
|
380
|
+
* Configuration for the combined spacing control (margin + padding in one UI).
|
|
381
|
+
*
|
|
382
|
+
* @see {@link PropertyUIConfig.spacing}
|
|
383
|
+
* @see {@link BoxModelConfig} for individual margin or padding controls
|
|
146
384
|
*/
|
|
147
385
|
export interface SpacingConfig {
|
|
386
|
+
/** Minimum padding value per side */
|
|
148
387
|
paddingMin?: number;
|
|
388
|
+
|
|
389
|
+
/** Maximum padding value per side */
|
|
149
390
|
paddingMax?: number;
|
|
391
|
+
|
|
392
|
+
/** Minimum margin value per side (can be negative) */
|
|
150
393
|
marginMin?: number;
|
|
394
|
+
|
|
395
|
+
/** Maximum margin value per side */
|
|
151
396
|
marginMax?: number;
|
|
397
|
+
|
|
398
|
+
/**
|
|
399
|
+
* CSS unit for all values
|
|
400
|
+
* @default 'px'
|
|
401
|
+
*/
|
|
152
402
|
unit?: string;
|
|
153
403
|
}
|
|
154
404
|
|
|
155
405
|
/**
|
|
156
|
-
*
|
|
406
|
+
* Configuration for the typography toolbar control.
|
|
407
|
+
*
|
|
408
|
+
* Toggles visibility of individual formatting buttons (bold, italic, etc.).
|
|
409
|
+
*
|
|
410
|
+
* @see {@link PropertyUIConfig.typographyToolbar}
|
|
157
411
|
*/
|
|
158
412
|
export interface TypographyToolbarConfig {
|
|
413
|
+
/** Show bold toggle button @default true */
|
|
159
414
|
showBold?: boolean;
|
|
415
|
+
|
|
416
|
+
/** Show italic toggle button @default true */
|
|
160
417
|
showItalic?: boolean;
|
|
418
|
+
|
|
419
|
+
/** Show underline toggle button @default true */
|
|
161
420
|
showUnderline?: boolean;
|
|
421
|
+
|
|
422
|
+
/** Show text alignment buttons @default true */
|
|
162
423
|
showAlignment?: boolean;
|
|
424
|
+
|
|
425
|
+
/** Show font size control @default true */
|
|
163
426
|
showFontSize?: boolean;
|
|
427
|
+
|
|
428
|
+
/** Show color picker @default true */
|
|
164
429
|
showColor?: boolean;
|
|
165
430
|
}
|
|
166
431
|
|
|
167
432
|
/**
|
|
168
|
-
*
|
|
433
|
+
* Configuration for gradient editor controls.
|
|
434
|
+
*
|
|
435
|
+
* @see {@link PropertyUIConfig.gradientEditor}
|
|
436
|
+
*
|
|
437
|
+
* @example
|
|
438
|
+
* ```typescript
|
|
439
|
+
* const gradientConfig: GradientEditorConfig = {
|
|
440
|
+
* allowLinear: true,
|
|
441
|
+
* allowRadial: true,
|
|
442
|
+
* maxStops: 5,
|
|
443
|
+
* colorFormat: 'hex',
|
|
444
|
+
* };
|
|
445
|
+
* ```
|
|
169
446
|
*/
|
|
170
447
|
export interface GradientEditorConfig {
|
|
448
|
+
/**
|
|
449
|
+
* Allow linear gradient type
|
|
450
|
+
* @default true
|
|
451
|
+
*/
|
|
171
452
|
allowLinear?: boolean;
|
|
453
|
+
|
|
454
|
+
/**
|
|
455
|
+
* Allow radial gradient type
|
|
456
|
+
* @default true
|
|
457
|
+
*/
|
|
172
458
|
allowRadial?: boolean;
|
|
459
|
+
|
|
460
|
+
/**
|
|
461
|
+
* Maximum number of color stops
|
|
462
|
+
* @default undefined (unlimited)
|
|
463
|
+
*/
|
|
173
464
|
maxStops?: number;
|
|
174
|
-
|
|
465
|
+
|
|
466
|
+
/**
|
|
467
|
+
* Output color format for gradient stops
|
|
468
|
+
* @default 'hex'
|
|
469
|
+
*/
|
|
470
|
+
colorFormat?: 'hex' | 'rgb' | 'hsl';
|
|
175
471
|
}
|
|
176
472
|
|
|
177
473
|
/**
|
|
178
|
-
*
|
|
474
|
+
* Configuration for border editor controls.
|
|
475
|
+
*
|
|
476
|
+
* @see {@link PropertyUIConfig.borderEditor}
|
|
179
477
|
*/
|
|
180
478
|
export interface BorderEditorConfig {
|
|
479
|
+
/**
|
|
480
|
+
* Allow editing each border side independently
|
|
481
|
+
* @default false
|
|
482
|
+
*/
|
|
181
483
|
allowIndividualSides?: boolean;
|
|
484
|
+
|
|
485
|
+
/**
|
|
486
|
+
* Show border-radius control
|
|
487
|
+
* @default true
|
|
488
|
+
*/
|
|
182
489
|
allowRadius?: boolean;
|
|
490
|
+
|
|
491
|
+
/**
|
|
492
|
+
* Maximum border width in pixels
|
|
493
|
+
* @default 20
|
|
494
|
+
*/
|
|
183
495
|
maxWidth?: number;
|
|
184
496
|
}
|
|
185
497
|
|
|
186
498
|
/**
|
|
187
|
-
*
|
|
188
|
-
*
|
|
499
|
+
* Configuration for the font preset select control.
|
|
500
|
+
*
|
|
501
|
+
* Displays typography presets from the Design System as a dropdown.
|
|
502
|
+
* The presets are sourced from {@link PluginDesignSystem.fonts}.
|
|
503
|
+
*
|
|
504
|
+
* @see {@link PropertyUIConfig.fontPresetSelect}
|
|
189
505
|
*/
|
|
190
506
|
export interface FontPresetSelectConfig {
|
|
191
|
-
/**
|
|
507
|
+
/**
|
|
508
|
+
* Filter fonts by category (e.g., `"heading"`, `"body"`)
|
|
509
|
+
* @default undefined (show all fonts)
|
|
510
|
+
*/
|
|
192
511
|
category?: string;
|
|
193
|
-
|
|
512
|
+
|
|
513
|
+
/** Placeholder text when no preset is selected */
|
|
194
514
|
placeholder?: string;
|
|
195
515
|
}
|
|
196
516
|
|
|
197
517
|
/**
|
|
198
|
-
*
|
|
199
|
-
*
|
|
518
|
+
* Configuration for the color preset select control.
|
|
519
|
+
*
|
|
520
|
+
* Displays color presets from the Design System as a dropdown with
|
|
521
|
+
* optional color swatches. Unlike `color-picker`, this control only
|
|
522
|
+
* allows preset selection — no free-form color input.
|
|
523
|
+
*
|
|
524
|
+
* @see {@link PropertyUIConfig.colorPresetSelect}
|
|
200
525
|
*/
|
|
201
526
|
export interface ColorPresetSelectConfig {
|
|
202
|
-
/**
|
|
527
|
+
/**
|
|
528
|
+
* Filter colors by category
|
|
529
|
+
* @default undefined (show all colors)
|
|
530
|
+
*/
|
|
203
531
|
category?: string;
|
|
204
|
-
|
|
532
|
+
|
|
533
|
+
/** Placeholder text when no preset is selected */
|
|
205
534
|
placeholder?: string;
|
|
206
|
-
|
|
535
|
+
|
|
536
|
+
/**
|
|
537
|
+
* Show a colored swatch preview next to each option
|
|
538
|
+
* @default true
|
|
539
|
+
*/
|
|
207
540
|
showSwatch?: boolean;
|
|
208
|
-
|
|
541
|
+
|
|
542
|
+
/**
|
|
543
|
+
* Allow a "None" option for transparent / no color
|
|
544
|
+
* @default false
|
|
545
|
+
*/
|
|
209
546
|
allowNone?: boolean;
|
|
210
547
|
}
|
|
211
548
|
|
|
212
549
|
/**
|
|
213
|
-
*
|
|
214
|
-
*
|
|
550
|
+
* Configuration for icon-based alignment toggle buttons.
|
|
551
|
+
*
|
|
552
|
+
* Used for both horizontal text alignment (`text-align-toggle`)
|
|
553
|
+
* and vertical alignment (`vertical-align-toggle`).
|
|
554
|
+
*
|
|
555
|
+
* @see {@link PropertyUIConfig.alignmentToggle}
|
|
215
556
|
*/
|
|
216
557
|
export interface AlignmentToggleConfig {
|
|
217
|
-
/**
|
|
558
|
+
/**
|
|
559
|
+
* Include "justify" option (horizontal alignment only)
|
|
560
|
+
* @default false
|
|
561
|
+
*/
|
|
218
562
|
includeJustify?: boolean;
|
|
219
|
-
|
|
563
|
+
|
|
564
|
+
/**
|
|
565
|
+
* Include "stretch" option (vertical alignment only)
|
|
566
|
+
* @default false
|
|
567
|
+
*/
|
|
220
568
|
includeStretch?: boolean;
|
|
221
|
-
|
|
569
|
+
|
|
570
|
+
/**
|
|
571
|
+
* Include "auto" / "inherit" option
|
|
572
|
+
* @default false
|
|
573
|
+
*/
|
|
222
574
|
includeAuto?: boolean;
|
|
223
575
|
}
|
|
224
576
|
|
|
225
577
|
/**
|
|
226
|
-
* Display
|
|
578
|
+
* Display and layout configuration for a property control in the Context Panel.
|
|
579
|
+
*
|
|
580
|
+
* Controls how and when a property is visible, its layout arrangement,
|
|
581
|
+
* and conditional visibility based on sibling property values.
|
|
582
|
+
*
|
|
583
|
+
* @see {@link PropertyUIConfig.display}
|
|
584
|
+
*
|
|
585
|
+
* @example
|
|
586
|
+
* ```typescript
|
|
587
|
+
* // Show this property only when layout mode is 'flexbox'
|
|
588
|
+
* const display: DisplayConfig = {
|
|
589
|
+
* layout: 'grid-2',
|
|
590
|
+
* condition: {
|
|
591
|
+
* when: 'layout.mode',
|
|
592
|
+
* equals: 'flexbox',
|
|
593
|
+
* },
|
|
594
|
+
* };
|
|
595
|
+
* ```
|
|
227
596
|
*/
|
|
228
597
|
export interface DisplayConfig {
|
|
229
598
|
/**
|
|
230
|
-
*
|
|
599
|
+
* Where this property's control is rendered
|
|
600
|
+
* @default 'panel'
|
|
231
601
|
*/
|
|
232
|
-
mode?:
|
|
602
|
+
mode?: 'tooltip' | 'panel' | 'both';
|
|
233
603
|
|
|
234
604
|
/**
|
|
235
|
-
*
|
|
605
|
+
* Whether this property section can be collapsed
|
|
606
|
+
* @default false
|
|
236
607
|
*/
|
|
237
608
|
collapsible?: boolean;
|
|
238
609
|
|
|
239
610
|
/**
|
|
240
|
-
*
|
|
611
|
+
* Initial collapsed state (only relevant when `collapsible` is `true`)
|
|
612
|
+
* @default false
|
|
241
613
|
*/
|
|
242
614
|
defaultCollapsed?: boolean;
|
|
243
615
|
|
|
244
616
|
/**
|
|
245
|
-
* Layout
|
|
246
|
-
*
|
|
617
|
+
* Layout arrangement for controls within the panel section.
|
|
618
|
+
* - `'single'` — one control per row (default)
|
|
619
|
+
* - `'grid-2'` — two controls side by side
|
|
620
|
+
* - `'grid-3'` — three controls per row
|
|
621
|
+
*
|
|
622
|
+
* Primarily used by container plugins to create compact property grids.
|
|
247
623
|
*/
|
|
248
|
-
layout?:
|
|
624
|
+
layout?: 'grid-2' | 'grid-3' | 'single' | string;
|
|
249
625
|
|
|
250
626
|
/**
|
|
251
|
-
* Conditional visibility based on
|
|
252
|
-
*
|
|
627
|
+
* Conditional visibility: show/hide this property based on another
|
|
628
|
+
* property's current value.
|
|
629
|
+
*
|
|
630
|
+
* @example
|
|
631
|
+
* ```typescript
|
|
632
|
+
* // Show only when layout mode is 'grid'
|
|
633
|
+
* { when: 'layout.mode', equals: 'grid' }
|
|
634
|
+
*
|
|
635
|
+
* // Show only when border style is NOT 'none'
|
|
636
|
+
* { when: 'border.style', notEquals: 'none' }
|
|
637
|
+
* ```
|
|
253
638
|
*/
|
|
254
639
|
condition?: {
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
640
|
+
/** Property key (dot-notation) to observe */
|
|
641
|
+
when: string;
|
|
642
|
+
/** Show this control when the observed property equals this value */
|
|
643
|
+
equals?: unknown;
|
|
644
|
+
/** Show this control when the observed property does NOT equal this value */
|
|
645
|
+
notEquals?: unknown;
|
|
258
646
|
};
|
|
259
647
|
}
|
|
260
648
|
|
|
261
649
|
/**
|
|
262
|
-
* UI configuration for property
|
|
263
|
-
*
|
|
650
|
+
* UI configuration metadata for a property.
|
|
651
|
+
*
|
|
652
|
+
* Tells the Context Panel **how** to render a property's editor control.
|
|
653
|
+
* Each property specifies a `control` type and then provides the
|
|
654
|
+
* matching configuration object (e.g., `slider` config for a `'slider'` control).
|
|
655
|
+
*
|
|
656
|
+
* @see {@link PropertyDefinition.ui}
|
|
657
|
+
* @see {@link PropertyControlType} for the list of available controls
|
|
658
|
+
*
|
|
659
|
+
* @example
|
|
660
|
+
* ```typescript
|
|
661
|
+
* const ui: PropertyUIConfig = {
|
|
662
|
+
* control: 'slider',
|
|
663
|
+
* slider: { min: 0, max: 100, step: 1, unit: 'px' },
|
|
664
|
+
* display: { layout: 'grid-2' },
|
|
665
|
+
* };
|
|
666
|
+
* ```
|
|
264
667
|
*/
|
|
265
668
|
export interface PropertyUIConfig {
|
|
669
|
+
/** Which UI control widget to render in the Context Panel */
|
|
266
670
|
control: PropertyControlType;
|
|
671
|
+
|
|
672
|
+
/** Configuration when `control` is `'slider'` @see {@link SliderConfig} */
|
|
267
673
|
slider?: SliderConfig;
|
|
674
|
+
|
|
675
|
+
/** Configuration when `control` is `'number-input'` @see {@link NumberConfig} */
|
|
268
676
|
number?: NumberConfig;
|
|
677
|
+
|
|
678
|
+
/** Configuration when `control` is `'number-with-unit'` @see {@link NumberWithUnitConfig} */
|
|
269
679
|
numberWithUnit?: NumberWithUnitConfig; // Container-specific
|
|
680
|
+
|
|
681
|
+
/** Configuration when `control` is `'select'` @see {@link SelectConfig} */
|
|
270
682
|
select?: SelectConfig;
|
|
683
|
+
|
|
684
|
+
/** Configuration when `control` is `'input'` @see {@link InputConfig} */
|
|
271
685
|
input?: InputConfig;
|
|
686
|
+
|
|
687
|
+
/** Configuration when `control` is `'textarea'` @see {@link TextareaConfig} */
|
|
272
688
|
textarea?: TextareaConfig;
|
|
689
|
+
|
|
690
|
+
/** Configuration when `control` is `'color-picker'` @see {@link ColorPickerConfig} */
|
|
273
691
|
colorPicker?: ColorPickerConfig;
|
|
692
|
+
|
|
693
|
+
/** Configuration when `control` is `'box-model'` @see {@link BoxModelConfig} */
|
|
274
694
|
boxModel?: BoxModelConfig;
|
|
695
|
+
|
|
696
|
+
/** Configuration when `control` is `'spacing'` or `'spacing-combined'` @see {@link SpacingConfig} */
|
|
275
697
|
spacing?: SpacingConfig; // Combined margin + padding control
|
|
698
|
+
|
|
699
|
+
/** Configuration when `control` is `'typography-toolbar'` @see {@link TypographyToolbarConfig} */
|
|
276
700
|
typographyToolbar?: TypographyToolbarConfig;
|
|
701
|
+
|
|
702
|
+
/** Configuration when `control` is `'gradient-editor'` @see {@link GradientEditorConfig} */
|
|
277
703
|
gradientEditor?: GradientEditorConfig;
|
|
704
|
+
|
|
705
|
+
/** Configuration when `control` is `'border-editor'` @see {@link BorderEditorConfig} */
|
|
278
706
|
borderEditor?: BorderEditorConfig;
|
|
707
|
+
|
|
708
|
+
/** Configuration when `control` is `'font-preset-select'` @see {@link FontPresetSelectConfig} */
|
|
279
709
|
fontPresetSelect?: FontPresetSelectConfig; // Design System font presets
|
|
710
|
+
|
|
711
|
+
/** Configuration when `control` is `'color-preset-select'` @see {@link ColorPresetSelectConfig} */
|
|
280
712
|
colorPresetSelect?: ColorPresetSelectConfig; // Design System color presets
|
|
713
|
+
|
|
714
|
+
/** Configuration when `control` is `'text-align-toggle'` or `'vertical-align-toggle'` @see {@link AlignmentToggleConfig} */
|
|
281
715
|
alignmentToggle?: AlignmentToggleConfig; // Alignment toggle buttons
|
|
716
|
+
|
|
717
|
+
/** Layout, visibility, and conditional display settings @see {@link DisplayConfig} */
|
|
282
718
|
display?: DisplayConfig;
|
|
283
719
|
}
|
|
284
720
|
|
|
285
721
|
/**
|
|
286
|
-
*
|
|
722
|
+
* Validation rules for a property value.
|
|
723
|
+
*
|
|
724
|
+
* Applied client-side when the user edits properties in the Context Panel.
|
|
725
|
+
*
|
|
726
|
+
* @see {@link PropertyDefinition.validation}
|
|
727
|
+
*
|
|
728
|
+
* @example
|
|
729
|
+
* ```typescript
|
|
730
|
+
* const validation: PropertyValidation = {
|
|
731
|
+
* min: 0,
|
|
732
|
+
* max: 100,
|
|
733
|
+
* message: 'Value must be between 0 and 100',
|
|
734
|
+
* };
|
|
735
|
+
* ```
|
|
287
736
|
*/
|
|
288
737
|
export interface PropertyValidation {
|
|
738
|
+
/** Regex pattern the string value must match */
|
|
289
739
|
pattern?: RegExp;
|
|
740
|
+
|
|
741
|
+
/** Minimum numeric value */
|
|
290
742
|
min?: number;
|
|
743
|
+
|
|
744
|
+
/** Maximum numeric value */
|
|
291
745
|
max?: number;
|
|
746
|
+
|
|
747
|
+
/** Error message shown when validation fails */
|
|
292
748
|
message?: string;
|
|
749
|
+
|
|
750
|
+
/**
|
|
751
|
+
* Custom validation function.
|
|
752
|
+
* Return `true` for valid, or a string error message for invalid.
|
|
753
|
+
*/
|
|
293
754
|
custom?: (value: unknown) => boolean | string;
|
|
294
755
|
}
|
|
295
756
|
|
|
296
757
|
/**
|
|
297
|
-
* Property priority for progressive disclosure
|
|
298
|
-
*
|
|
758
|
+
* Property priority for progressive disclosure in the Context Panel.
|
|
759
|
+
*
|
|
760
|
+
* Controls visual hierarchy and default visibility:
|
|
761
|
+
* - `'quick'` — Always visible at the top, no accordion (most important properties)
|
|
762
|
+
* - `'common'` — Collapsible section, expanded by default (frequently used)
|
|
763
|
+
* - `'advanced'` — Collapsible section, collapsed by default (rarely used)
|
|
764
|
+
*
|
|
765
|
+
* @default 'common'
|
|
766
|
+
* @see {@link PropertyDefinition.priority}
|
|
299
767
|
*/
|
|
300
|
-
export type PropertyPriority =
|
|
768
|
+
export type PropertyPriority = 'quick' | 'common' | 'advanced';
|
|
301
769
|
|
|
302
770
|
/**
|
|
303
|
-
* Property definition
|
|
771
|
+
* Property definition — the core metadata interface for plugin properties.
|
|
772
|
+
*
|
|
773
|
+
* Each plugin declares an array of `PropertyDefinition` objects that describe
|
|
774
|
+
* its editable properties. The Context Panel reads these definitions and
|
|
775
|
+
* auto-generates the appropriate editor controls.
|
|
776
|
+
*
|
|
777
|
+
* Properties support:
|
|
778
|
+
* - **Dot-notation keys** for nested data structures (`'style.fontSize'`)
|
|
779
|
+
* - **Design System integration** via `useGlobal` / `globalKey`
|
|
780
|
+
* - **Progressive disclosure** via `priority`
|
|
781
|
+
* - **Conditional visibility** via `ui.display.condition`
|
|
782
|
+
*
|
|
783
|
+
* @see {@link PluginConfig.properties}
|
|
784
|
+
* @see {@link PropertyUIConfig} for UI control configuration
|
|
785
|
+
* @see {@link PropertyCategory} for organizational grouping
|
|
304
786
|
*
|
|
305
|
-
*
|
|
306
|
-
*
|
|
787
|
+
* @example
|
|
788
|
+
* ```typescript
|
|
789
|
+
* const fontSizeProperty: PropertyDefinition = {
|
|
790
|
+
* key: 'style.fontSize',
|
|
791
|
+
* type: 'range',
|
|
792
|
+
* label: 'Font Size',
|
|
793
|
+
* default: 16,
|
|
794
|
+
* category: 'style',
|
|
795
|
+
* priority: 'quick',
|
|
796
|
+
* useGlobal: true,
|
|
797
|
+
* globalKey: 'fonts.body.size',
|
|
798
|
+
* ui: {
|
|
799
|
+
* control: 'slider',
|
|
800
|
+
* slider: { min: 8, max: 72, step: 1, unit: 'px', showValue: true },
|
|
801
|
+
* },
|
|
802
|
+
* };
|
|
803
|
+
* ```
|
|
307
804
|
*/
|
|
308
805
|
export interface PropertyDefinition {
|
|
309
806
|
/**
|
|
310
|
-
* Property key
|
|
311
|
-
*
|
|
807
|
+
* Property key using dot notation for nested data structures.
|
|
808
|
+
*
|
|
809
|
+
* This key maps directly to the path in the plugin's `data` object.
|
|
810
|
+
*
|
|
811
|
+
* @example 'style.fontSize', 'layout.padding.top', 'contentI18n'
|
|
312
812
|
*/
|
|
313
813
|
key: string;
|
|
314
814
|
|
|
315
815
|
/**
|
|
316
|
-
*
|
|
816
|
+
* Semantic type of the property value.
|
|
817
|
+
* @see {@link PropertyType}
|
|
317
818
|
*/
|
|
318
819
|
type: PropertyType;
|
|
319
820
|
|
|
320
821
|
/**
|
|
321
|
-
*
|
|
822
|
+
* Human-readable label displayed in the Context Panel
|
|
322
823
|
*/
|
|
323
824
|
label: string;
|
|
324
825
|
|
|
325
826
|
/**
|
|
326
|
-
* Default value
|
|
827
|
+
* Default value for new plugin instances.
|
|
828
|
+
* Set to `null` to inherit from the Design System global default
|
|
829
|
+
* (when `useGlobal` is `true`).
|
|
327
830
|
*/
|
|
328
831
|
default: unknown;
|
|
329
832
|
|
|
330
833
|
/**
|
|
331
|
-
*
|
|
834
|
+
* Help text / tooltip shown below or beside the control in the UI
|
|
332
835
|
*/
|
|
333
836
|
description?: string;
|
|
334
837
|
|
|
335
838
|
/**
|
|
336
|
-
*
|
|
839
|
+
* Organizational category — determines which panel section this property
|
|
840
|
+
* appears in.
|
|
841
|
+
*
|
|
842
|
+
* @default 'style'
|
|
843
|
+
* @see {@link PropertyCategory}
|
|
337
844
|
*/
|
|
338
845
|
category?: PropertyCategory;
|
|
339
846
|
|
|
340
847
|
/**
|
|
341
|
-
* Whether
|
|
848
|
+
* Whether a value is required before the element can be saved
|
|
849
|
+
* @default false
|
|
342
850
|
*/
|
|
343
851
|
required?: boolean;
|
|
344
852
|
|
|
345
853
|
/**
|
|
346
|
-
*
|
|
347
|
-
*
|
|
348
|
-
*
|
|
349
|
-
*
|
|
350
|
-
* Defaults to 'common' if not specified
|
|
854
|
+
* Controls progressive disclosure and default visibility.
|
|
855
|
+
*
|
|
856
|
+
* @default 'common'
|
|
857
|
+
* @see {@link PropertyPriority}
|
|
351
858
|
*/
|
|
352
859
|
priority?: PropertyPriority;
|
|
353
860
|
|
|
354
861
|
/**
|
|
355
|
-
* Design System integration
|
|
356
|
-
*
|
|
862
|
+
* Enable Design System integration for this property.
|
|
863
|
+
* When `true`, the UI shows a "Use Global Default" toggle that
|
|
864
|
+
* lets the user fall back to the design system value specified
|
|
865
|
+
* by {@link globalKey}.
|
|
866
|
+
*
|
|
867
|
+
* @default false
|
|
357
868
|
*/
|
|
358
869
|
useGlobal?: boolean;
|
|
359
870
|
|
|
360
871
|
/**
|
|
361
|
-
* Design System
|
|
872
|
+
* Dot-notation path into the Design System to read the global default.
|
|
873
|
+
* Only used when `useGlobal` is `true`.
|
|
874
|
+
*
|
|
362
875
|
* @example 'fonts.body.size', 'colors.text-primary'
|
|
363
876
|
*/
|
|
364
877
|
globalKey?: string;
|
|
365
878
|
|
|
366
879
|
/**
|
|
367
|
-
* UI control configuration
|
|
880
|
+
* UI control configuration — tells the Context Panel which widget
|
|
881
|
+
* to render and how to configure it.
|
|
882
|
+
*
|
|
883
|
+
* @see {@link PropertyUIConfig}
|
|
368
884
|
*/
|
|
369
885
|
ui?: PropertyUIConfig;
|
|
370
886
|
|
|
371
887
|
/**
|
|
372
|
-
*
|
|
888
|
+
* Client-side validation rules applied when the user edits this property.
|
|
889
|
+
* @see {@link PropertyValidation}
|
|
373
890
|
*/
|
|
374
891
|
validation?: PropertyValidation;
|
|
375
892
|
}
|
|
376
893
|
|
|
377
894
|
/**
|
|
378
|
-
*
|
|
895
|
+
* Optional metadata about a plugin, shown in plugin listings and documentation.
|
|
896
|
+
*
|
|
897
|
+
* @see {@link PluginConfig.meta}
|
|
898
|
+
*
|
|
899
|
+
* @example
|
|
900
|
+
* ```typescript
|
|
901
|
+
* const meta: PluginMeta = {
|
|
902
|
+
* description: 'Semantic heading component (h1-h6) for page structure and SEO',
|
|
903
|
+
* tags: ['heading', 'h1', 'title', 'semantic', 'seo'],
|
|
904
|
+
* thumbnail: '/plugins/base-heading/thumbnail.png',
|
|
905
|
+
* documentation: 'https://docs.codefluss.com/plugins/base-heading',
|
|
906
|
+
* };
|
|
907
|
+
* ```
|
|
379
908
|
*/
|
|
380
909
|
export interface PluginMeta {
|
|
910
|
+
/** Short description of what the plugin does */
|
|
381
911
|
description?: string;
|
|
912
|
+
|
|
913
|
+
/** Search / filter tags for plugin discovery in the editor toolbar */
|
|
382
914
|
tags?: string[];
|
|
915
|
+
|
|
916
|
+
/** Path or URL to a thumbnail image for the plugin browser */
|
|
383
917
|
thumbnail?: string;
|
|
918
|
+
|
|
919
|
+
/** URL to external documentation */
|
|
384
920
|
documentation?: string;
|
|
385
921
|
}
|
|
386
922
|
|
|
387
923
|
/**
|
|
388
|
-
* Plugin
|
|
924
|
+
* Plugin capabilities — declares **what** a plugin can do structurally.
|
|
925
|
+
*
|
|
926
|
+
* This is the core of the **plugin-driven architecture**: each plugin
|
|
927
|
+
* declares its own capabilities (container vs leaf, allowed children, etc.)
|
|
928
|
+
* and the application reads these to determine valid operations (drag-drop
|
|
929
|
+
* constraints, nesting rules, toolbar options).
|
|
930
|
+
*
|
|
931
|
+
* @see {@link PluginConfig.capabilities}
|
|
932
|
+
*
|
|
933
|
+
* @example
|
|
934
|
+
* ```typescript
|
|
935
|
+
* // Container plugin (e.g., base-container)
|
|
936
|
+
* const containerCaps: PluginCapabilities = {
|
|
937
|
+
* supportsChildren: true,
|
|
938
|
+
* isRootComponent: true,
|
|
939
|
+
* requiresParent: false,
|
|
940
|
+
* childrenType: 'nested',
|
|
941
|
+
* allowedChildPlugins: [], // any child allowed
|
|
942
|
+
* maxChildren: null, // unlimited
|
|
943
|
+
* minChildren: 0,
|
|
944
|
+
* };
|
|
389
945
|
*
|
|
390
|
-
*
|
|
391
|
-
*
|
|
392
|
-
*
|
|
946
|
+
* // Leaf plugin (e.g., base-heading)
|
|
947
|
+
* const headingCaps: PluginCapabilities = {
|
|
948
|
+
* supportsChildren: false,
|
|
949
|
+
* isRootComponent: false,
|
|
950
|
+
* requiresParent: true,
|
|
951
|
+
* childrenType: null,
|
|
952
|
+
* allowedChildPlugins: [],
|
|
953
|
+
* maxChildren: null,
|
|
954
|
+
* minChildren: 0,
|
|
955
|
+
* };
|
|
956
|
+
* ```
|
|
393
957
|
*/
|
|
394
958
|
export interface PluginCapabilities {
|
|
395
959
|
/**
|
|
396
|
-
*
|
|
397
|
-
*
|
|
398
|
-
*
|
|
960
|
+
* Whether this plugin can contain child components.
|
|
961
|
+
*
|
|
962
|
+
* - `true` — container/layout component (e.g., `base-container`, `form-container`)
|
|
963
|
+
* - `false` — leaf component (e.g., `base-heading`, `base-image`, `base-button`)
|
|
399
964
|
*/
|
|
400
965
|
supportsChildren: boolean;
|
|
401
966
|
|
|
402
967
|
/**
|
|
403
|
-
*
|
|
404
|
-
*
|
|
405
|
-
*
|
|
968
|
+
* Whether this plugin can be placed at the canvas / section root level.
|
|
969
|
+
*
|
|
970
|
+
* - `true` — can be placed directly on the canvas (containers, sections)
|
|
971
|
+
* - `false` — must be inside another component (text, buttons, images)
|
|
406
972
|
*/
|
|
407
973
|
isRootComponent: boolean;
|
|
408
974
|
|
|
409
975
|
/**
|
|
410
|
-
*
|
|
411
|
-
* true = cannot exist at top level, must be inside a container
|
|
412
|
-
* false = can be placed directly on canvas
|
|
976
|
+
* Whether this plugin must be nested inside a parent container.
|
|
413
977
|
*
|
|
414
|
-
*
|
|
415
|
-
*
|
|
978
|
+
* - `true` — cannot exist at top level, must be inside a container
|
|
979
|
+
* - `false` — can be placed directly on the canvas
|
|
980
|
+
*
|
|
981
|
+
* @example
|
|
982
|
+
* // Text: requiresParent = true (must be in a container)
|
|
983
|
+
* // Container: requiresParent = false (can be at top level)
|
|
416
984
|
*/
|
|
417
985
|
requiresParent: boolean;
|
|
418
986
|
|
|
419
987
|
/**
|
|
420
|
-
* Children architecture type
|
|
421
|
-
*
|
|
422
|
-
* '
|
|
423
|
-
*
|
|
988
|
+
* Children architecture type (only relevant when `supportsChildren` is `true`).
|
|
989
|
+
*
|
|
990
|
+
* - `'nested'` — Children stored as direct arrays in the parent's data (**recommended**)
|
|
991
|
+
* - `'flat'` — Children reference parent via `parentId` (**deprecated**)
|
|
992
|
+
* - `null` — Does not support children
|
|
424
993
|
*/
|
|
425
|
-
childrenType:
|
|
994
|
+
childrenType: 'nested' | 'flat' | null;
|
|
426
995
|
|
|
427
996
|
/**
|
|
428
|
-
*
|
|
429
|
-
*
|
|
430
|
-
* [
|
|
431
|
-
*
|
|
997
|
+
* Restricts which plugins may be added as children.
|
|
998
|
+
*
|
|
999
|
+
* - Empty array `[]` — all plugins allowed as children
|
|
1000
|
+
* - `['base-text', 'base-image']` — only listed plugin IDs allowed
|
|
1001
|
+
*
|
|
1002
|
+
* Only applicable when `supportsChildren` is `true`.
|
|
432
1003
|
*/
|
|
433
1004
|
allowedChildPlugins: string[];
|
|
434
1005
|
|
|
435
1006
|
/**
|
|
436
|
-
*
|
|
437
|
-
*
|
|
438
|
-
* [
|
|
439
|
-
*
|
|
1007
|
+
* Restricts which container plugins this plugin may be placed inside.
|
|
1008
|
+
*
|
|
1009
|
+
* - `undefined` or empty array `[]` — can be a child of any container
|
|
1010
|
+
* - `['base-container']` — can only be inside the listed containers
|
|
1011
|
+
*
|
|
1012
|
+
* Only applicable when `requiresParent` is `true`.
|
|
440
1013
|
*/
|
|
441
1014
|
allowedParentPlugins?: string[];
|
|
442
1015
|
|
|
443
1016
|
/**
|
|
444
|
-
* Maximum number of children
|
|
445
|
-
*
|
|
446
|
-
*
|
|
447
|
-
*
|
|
1017
|
+
* Maximum number of children this container can hold.
|
|
1018
|
+
*
|
|
1019
|
+
* - `null` — unlimited children
|
|
1020
|
+
* - A positive number — enforced limit
|
|
1021
|
+
*
|
|
1022
|
+
* Only applicable when `supportsChildren` is `true`.
|
|
448
1023
|
*/
|
|
449
1024
|
maxChildren: number | null;
|
|
450
1025
|
|
|
451
1026
|
/**
|
|
452
|
-
* Minimum number of children required
|
|
453
|
-
*
|
|
454
|
-
* Only applicable
|
|
1027
|
+
* Minimum number of children required by this container.
|
|
1028
|
+
*
|
|
1029
|
+
* Only applicable when `supportsChildren` is `true`.
|
|
1030
|
+
* @default 0
|
|
455
1031
|
*/
|
|
456
1032
|
minChildren: number;
|
|
457
1033
|
}
|
|
@@ -472,48 +1048,72 @@ export interface PluginCapabilities {
|
|
|
472
1048
|
*/
|
|
473
1049
|
|
|
474
1050
|
/**
|
|
475
|
-
*
|
|
1051
|
+
* External dependencies injected into plugin components by the host application.
|
|
1052
|
+
*
|
|
1053
|
+
* Provides access to the Design System, utility functions, and optional
|
|
1054
|
+
* editor callbacks. These are passed via the `dependencies` prop.
|
|
1055
|
+
*
|
|
1056
|
+
* **Note:** This is the simplified dependency interface used in `plugin-system.ts`.
|
|
1057
|
+
* The full dependency interface (including `PluginRenderer` component and
|
|
1058
|
+
* `callbacks`) is defined in `dependencies.ts`.
|
|
476
1059
|
*
|
|
477
|
-
*
|
|
478
|
-
*
|
|
479
|
-
*
|
|
1060
|
+
* @see {@link BasePluginProps.dependencies}
|
|
1061
|
+
* @see {@link PluginDesignSystem} for design token access
|
|
1062
|
+
* @see {@link PluginUtils} for utility functions
|
|
480
1063
|
*/
|
|
481
1064
|
export interface PluginDependencies {
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
|
|
485
|
-
|
|
486
|
-
|
|
487
|
-
|
|
488
|
-
|
|
489
|
-
|
|
490
|
-
|
|
491
|
-
|
|
492
|
-
|
|
493
|
-
|
|
494
|
-
|
|
495
|
-
|
|
496
|
-
|
|
497
|
-
|
|
498
|
-
|
|
499
|
-
|
|
500
|
-
|
|
501
|
-
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
|
|
1065
|
+
/**
|
|
1066
|
+
* Design System instance providing access to fonts, colors, spacing,
|
|
1067
|
+
* breakpoints, and other design tokens.
|
|
1068
|
+
*
|
|
1069
|
+
* @see {@link PluginDesignSystem}
|
|
1070
|
+
*/
|
|
1071
|
+
designSystem: PluginDesignSystem;
|
|
1072
|
+
|
|
1073
|
+
/**
|
|
1074
|
+
* Utility functions (e.g., `cn` for class name merging)
|
|
1075
|
+
* @see {@link PluginUtils}
|
|
1076
|
+
*/
|
|
1077
|
+
utils: PluginUtils;
|
|
1078
|
+
|
|
1079
|
+
/**
|
|
1080
|
+
* Callback invoked when the user edits text content (Editor mode only).
|
|
1081
|
+
*
|
|
1082
|
+
* @param elementId - Unique ID of the element being edited
|
|
1083
|
+
* @param language - ISO language code of the content being changed
|
|
1084
|
+
* @param content - New content value
|
|
1085
|
+
*/
|
|
1086
|
+
onContentChange?: (
|
|
1087
|
+
elementId: string,
|
|
1088
|
+
language: string,
|
|
1089
|
+
content: unknown
|
|
1090
|
+
) => void;
|
|
1091
|
+
|
|
1092
|
+
/**
|
|
1093
|
+
* Callback invoked when a property value changes via the Context Panel
|
|
1094
|
+
* (Editor mode only).
|
|
1095
|
+
*
|
|
1096
|
+
* @param elementId - Unique ID of the element being edited
|
|
1097
|
+
* @param property - Dot-notation property path (e.g., `'style.fontSize'`)
|
|
1098
|
+
* @param value - New property value
|
|
1099
|
+
*/
|
|
1100
|
+
onPropertyChange?: (
|
|
1101
|
+
elementId: string,
|
|
1102
|
+
property: string,
|
|
1103
|
+
value: unknown
|
|
1104
|
+
) => void;
|
|
508
1105
|
}
|
|
509
1106
|
|
|
510
1107
|
/**
|
|
511
|
-
* Base
|
|
1108
|
+
* Base props required by **every** plugin component.
|
|
512
1109
|
*
|
|
513
|
-
*
|
|
514
|
-
*
|
|
1110
|
+
* Both Editor Components and Renderers must accept these props.
|
|
1111
|
+
* Use the generic parameter `TData` to specify the plugin's data shape.
|
|
515
1112
|
*
|
|
516
|
-
* @template TData - Plugin-specific data type
|
|
1113
|
+
* @template TData - Plugin-specific data type (defaults to `unknown`)
|
|
1114
|
+
*
|
|
1115
|
+
* @see {@link EditorModeProps} for additional editor-only props
|
|
1116
|
+
* @see {@link RendererProps} for the minimal SSR variant
|
|
517
1117
|
*
|
|
518
1118
|
* @example
|
|
519
1119
|
* ```typescript
|
|
@@ -523,40 +1123,40 @@ export interface PluginDependencies {
|
|
|
523
1123
|
*/
|
|
524
1124
|
export interface BasePluginProps<TData = unknown> {
|
|
525
1125
|
/**
|
|
526
|
-
* Unique element ID
|
|
527
|
-
*
|
|
1126
|
+
* Unique element ID — used for data attributes, callbacks, and DOM references.
|
|
1127
|
+
* @example 'heading-abc123'
|
|
528
1128
|
*/
|
|
529
1129
|
elementId: string;
|
|
530
1130
|
|
|
531
1131
|
/**
|
|
532
|
-
* Plugin-specific data
|
|
533
|
-
*
|
|
1132
|
+
* Plugin-specific data object containing all configurable properties and content.
|
|
1133
|
+
* The shape is defined by the plugin's type parameter `TData`.
|
|
534
1134
|
*/
|
|
535
1135
|
data: TData;
|
|
536
1136
|
|
|
537
1137
|
/**
|
|
538
|
-
* Current language
|
|
539
|
-
* Used for multi-language content
|
|
1138
|
+
* Current language as an ISO code.
|
|
1139
|
+
* Used for resolving multi-language content (`MultiLangContent`).
|
|
540
1140
|
* @example 'de', 'en', 'fr', 'es', 'it'
|
|
541
1141
|
*/
|
|
542
1142
|
language: string;
|
|
543
1143
|
|
|
544
1144
|
/**
|
|
545
|
-
* Injected dependencies
|
|
546
|
-
*
|
|
1145
|
+
* Injected dependencies from the host application.
|
|
1146
|
+
* @see {@link PluginDependencies}
|
|
547
1147
|
*/
|
|
548
1148
|
dependencies: PluginDependencies;
|
|
549
1149
|
}
|
|
550
1150
|
|
|
551
1151
|
/**
|
|
552
|
-
* Editor
|
|
1152
|
+
* Additional props for Editor Components only (`'use client'`).
|
|
553
1153
|
*
|
|
554
|
-
*
|
|
555
|
-
*
|
|
1154
|
+
* These enable interactive editing: selection highlighting, click handling,
|
|
1155
|
+
* content editing, and property changes. Combine with {@link BasePluginProps}
|
|
1156
|
+
* to form the full editor component props.
|
|
556
1157
|
*
|
|
557
|
-
*
|
|
558
|
-
*
|
|
559
|
-
* - EditorModeProps (editor-specific features)
|
|
1158
|
+
* @see {@link BasePluginProps}
|
|
1159
|
+
* @see {@link ContainerProps} for additional container-specific props
|
|
560
1160
|
*
|
|
561
1161
|
* @example
|
|
562
1162
|
* ```typescript
|
|
@@ -567,52 +1167,66 @@ export interface BasePluginProps<TData = unknown> {
|
|
|
567
1167
|
*/
|
|
568
1168
|
export interface EditorModeProps {
|
|
569
1169
|
/**
|
|
570
|
-
*
|
|
571
|
-
* Used for visual feedback
|
|
1170
|
+
* Whether this component is currently selected in the editor.
|
|
1171
|
+
* Used for visual feedback (selection border, handles, etc.).
|
|
1172
|
+
* @default false
|
|
572
1173
|
*/
|
|
573
1174
|
isSelected?: boolean;
|
|
574
1175
|
|
|
575
1176
|
/**
|
|
576
|
-
* Click handler for component selection
|
|
577
|
-
*
|
|
1177
|
+
* Click handler for component selection in the editor.
|
|
1178
|
+
* @param elementId - ID of the clicked element
|
|
578
1179
|
*/
|
|
579
1180
|
onClick?: (elementId: string) => void;
|
|
580
1181
|
|
|
581
1182
|
/**
|
|
582
|
-
*
|
|
583
|
-
*
|
|
584
|
-
* @
|
|
1183
|
+
* Callback for inline content editing (e.g., `contentEditable` text).
|
|
1184
|
+
*
|
|
1185
|
+
* @param elementId - ID of the element being edited
|
|
1186
|
+
* @param language - ISO language code
|
|
1187
|
+
* @param content - New content value
|
|
1188
|
+
*
|
|
1189
|
+
* @example
|
|
1190
|
+
* ```typescript
|
|
1191
|
+
* onContentChange('heading-1', 'de', 'Neuer Titel')
|
|
1192
|
+
* ```
|
|
585
1193
|
*/
|
|
586
1194
|
onContentChange?: (
|
|
587
1195
|
elementId: string,
|
|
588
1196
|
language: string,
|
|
589
|
-
content: unknown
|
|
1197
|
+
content: unknown
|
|
590
1198
|
) => void;
|
|
591
1199
|
|
|
592
1200
|
/**
|
|
593
|
-
*
|
|
594
|
-
*
|
|
595
|
-
* @
|
|
1201
|
+
* Callback for property changes via the Context Panel.
|
|
1202
|
+
*
|
|
1203
|
+
* @param elementId - ID of the element being edited
|
|
1204
|
+
* @param property - Dot-notation property path
|
|
1205
|
+
* @param value - New property value
|
|
1206
|
+
*
|
|
1207
|
+
* @example
|
|
1208
|
+
* ```typescript
|
|
1209
|
+
* onPropertyChange('heading-1', 'style.fontSize', '32px')
|
|
1210
|
+
* ```
|
|
596
1211
|
*/
|
|
597
1212
|
onPropertyChange?: (
|
|
598
1213
|
elementId: string,
|
|
599
1214
|
property: string,
|
|
600
|
-
value: unknown
|
|
1215
|
+
value: unknown
|
|
601
1216
|
) => void;
|
|
602
1217
|
}
|
|
603
1218
|
|
|
604
1219
|
/**
|
|
605
|
-
* Renderer
|
|
1220
|
+
* Props for Renderer (SSR / view-mode) components.
|
|
606
1221
|
*
|
|
607
|
-
*
|
|
608
|
-
*
|
|
1222
|
+
* Renderers are **server-safe**: they do NOT use `'use client'`, contain
|
|
1223
|
+
* no React hooks, and receive no editor callbacks. Only the Design System
|
|
1224
|
+
* and utility functions are injected as dependencies.
|
|
609
1225
|
*
|
|
610
|
-
*
|
|
611
|
-
* - No callbacks (onContentChange, onPropertyChange)
|
|
612
|
-
* - Minimal dependencies (only designSystem and utils, no callbacks)
|
|
613
|
-
* - Should use pure functions, no React hooks
|
|
1226
|
+
* @template TData - Plugin-specific data type (defaults to `unknown`)
|
|
614
1227
|
*
|
|
615
|
-
* @
|
|
1228
|
+
* @see {@link BasePluginProps} for the full editor variant
|
|
1229
|
+
* @see {@link ContainerProps} for container children
|
|
616
1230
|
*
|
|
617
1231
|
* @example
|
|
618
1232
|
* ```typescript
|
|
@@ -628,35 +1242,34 @@ export interface EditorModeProps {
|
|
|
628
1242
|
*/
|
|
629
1243
|
export interface RendererProps<TData = unknown> {
|
|
630
1244
|
/**
|
|
631
|
-
* Unique element ID
|
|
632
|
-
* Used for data attributes and DOM references
|
|
1245
|
+
* Unique element ID for data attributes and DOM references
|
|
633
1246
|
*/
|
|
634
1247
|
elementId: string;
|
|
635
1248
|
|
|
636
1249
|
/**
|
|
637
|
-
* Plugin-specific data
|
|
638
|
-
* Contains all configurable properties and content
|
|
1250
|
+
* Plugin-specific data containing all properties and content
|
|
639
1251
|
*/
|
|
640
1252
|
data: TData;
|
|
641
1253
|
|
|
642
1254
|
/**
|
|
643
|
-
* Current language (ISO code)
|
|
644
|
-
* Used for multi-language content resolution
|
|
1255
|
+
* Current language (ISO code) for multi-language content resolution
|
|
645
1256
|
*/
|
|
646
1257
|
language: string;
|
|
647
1258
|
|
|
648
1259
|
/**
|
|
649
|
-
* Minimal dependencies
|
|
650
|
-
* No callbacks since renderers are read-only
|
|
1260
|
+
* Minimal dependencies — design system and utilities only.
|
|
1261
|
+
* No callbacks since renderers are read-only.
|
|
651
1262
|
*/
|
|
652
|
-
dependencies: Pick<PluginDependencies,
|
|
1263
|
+
dependencies: Pick<PluginDependencies, 'designSystem' | 'utils'>;
|
|
653
1264
|
}
|
|
654
1265
|
|
|
655
1266
|
/**
|
|
656
|
-
*
|
|
1267
|
+
* Props for plugins that support children (containers / layout components).
|
|
657
1268
|
*
|
|
658
|
-
*
|
|
659
|
-
*
|
|
1269
|
+
* Used by both Editor Components and Renderers when the plugin has
|
|
1270
|
+
* `capabilities.supportsChildren = true`.
|
|
1271
|
+
*
|
|
1272
|
+
* @see {@link PluginCapabilities.supportsChildren}
|
|
660
1273
|
*
|
|
661
1274
|
* @example
|
|
662
1275
|
* ```typescript
|
|
@@ -674,112 +1287,171 @@ export interface RendererProps<TData = unknown> {
|
|
|
674
1287
|
*/
|
|
675
1288
|
export interface ContainerProps {
|
|
676
1289
|
/**
|
|
677
|
-
* Child components
|
|
678
|
-
* React nodes
|
|
1290
|
+
* Child components to render inside this container.
|
|
1291
|
+
* Provided as React nodes by the recursive element renderer.
|
|
679
1292
|
*/
|
|
680
1293
|
children?: React.ReactNode;
|
|
681
1294
|
|
|
682
1295
|
/**
|
|
683
|
-
* Drop event handler (Editor only)
|
|
684
|
-
* Called when user drops an element into this container
|
|
1296
|
+
* Drop event handler (Editor mode only).
|
|
1297
|
+
* Called when the user drags and drops an element into this container.
|
|
685
1298
|
*
|
|
686
|
-
* @param targetId - Container element ID
|
|
687
|
-
* @param droppedId -
|
|
688
|
-
* @param position -
|
|
1299
|
+
* @param targetId - Container element ID receiving the drop
|
|
1300
|
+
* @param droppedId - ID of the element being dropped
|
|
1301
|
+
* @param position - Where to insert relative to existing children
|
|
689
1302
|
*/
|
|
690
1303
|
onDrop?: (
|
|
691
1304
|
targetId: string,
|
|
692
1305
|
droppedId: string,
|
|
693
|
-
position:
|
|
1306
|
+
position: 'before' | 'after' | 'inside'
|
|
694
1307
|
) => void;
|
|
695
1308
|
}
|
|
696
1309
|
|
|
697
1310
|
/**
|
|
698
|
-
*
|
|
1311
|
+
* Complete plugin configuration — the top-level definition object.
|
|
1312
|
+
*
|
|
1313
|
+
* Every plugin registers a `PluginConfig` that describes its component,
|
|
1314
|
+
* editable properties, capabilities, defaults, and metadata. The editor
|
|
1315
|
+
* and runtime use this to render, configure, and constrain plugin instances.
|
|
699
1316
|
*
|
|
700
|
-
*
|
|
1317
|
+
* @see {@link PropertyDefinition} for how properties are declared
|
|
1318
|
+
* @see {@link PluginCapabilities} for structural capabilities
|
|
1319
|
+
* @see {@link PluginMeta} for optional metadata
|
|
1320
|
+
*
|
|
1321
|
+
* @example
|
|
1322
|
+
* ```typescript
|
|
1323
|
+
* const headingConfig: PluginConfig = {
|
|
1324
|
+
* id: 'base-heading',
|
|
1325
|
+
* name: 'Heading',
|
|
1326
|
+
* version: '0.1.0',
|
|
1327
|
+
* category: 'basic',
|
|
1328
|
+
* icon: Heading1,
|
|
1329
|
+
* component: HeadingComponent,
|
|
1330
|
+
* properties: [ ... ],
|
|
1331
|
+
* defaults: { contentI18n: { en: 'Heading Text', de: 'Überschrift' } },
|
|
1332
|
+
* locales: headingLocales,
|
|
1333
|
+
* ssr: true,
|
|
1334
|
+
* responsive: true,
|
|
1335
|
+
* capabilities: {
|
|
1336
|
+
* supportsChildren: false,
|
|
1337
|
+
* isRootComponent: false,
|
|
1338
|
+
* requiresParent: true,
|
|
1339
|
+
* childrenType: null,
|
|
1340
|
+
* allowedChildPlugins: [],
|
|
1341
|
+
* maxChildren: null,
|
|
1342
|
+
* minChildren: 0,
|
|
1343
|
+
* },
|
|
1344
|
+
* meta: { description: 'Semantic heading (h1-h6)', tags: ['heading'] },
|
|
1345
|
+
* };
|
|
1346
|
+
* ```
|
|
701
1347
|
*/
|
|
702
1348
|
export interface PluginConfig {
|
|
703
1349
|
/**
|
|
704
|
-
* Unique plugin identifier
|
|
1350
|
+
* Unique plugin identifier used for registration and lookups.
|
|
1351
|
+
* Convention: `'base-heading'`, `'form-input'`, `'blog-title'`.
|
|
705
1352
|
*/
|
|
706
1353
|
id: string;
|
|
707
1354
|
|
|
708
1355
|
/**
|
|
709
|
-
*
|
|
1356
|
+
* Human-readable display name shown in the editor toolbar and plugin browser.
|
|
1357
|
+
* @example 'Heading', 'Container', 'Form Input'
|
|
710
1358
|
*/
|
|
711
1359
|
name: string;
|
|
712
1360
|
|
|
713
1361
|
/**
|
|
714
|
-
* Semantic version
|
|
1362
|
+
* Semantic version string
|
|
1363
|
+
* @example '0.1.0'
|
|
715
1364
|
*/
|
|
716
1365
|
version: string;
|
|
717
1366
|
|
|
718
1367
|
/**
|
|
719
|
-
* Plugin category
|
|
1368
|
+
* Plugin category — determines which toolbar section the plugin appears in.
|
|
1369
|
+
*
|
|
1370
|
+
* - `'basic'` — Common components (text, heading, image, button, container)
|
|
1371
|
+
* - `'layout'` — Layout-focused components
|
|
1372
|
+
* - `'forms'` — Form-related components (inputs, selects, form container)
|
|
1373
|
+
* - `'advanced'` — Specialized or complex components
|
|
720
1374
|
*/
|
|
721
|
-
category:
|
|
1375
|
+
category: 'basic' | 'layout' | 'forms' | 'advanced';
|
|
722
1376
|
|
|
723
1377
|
/**
|
|
724
|
-
*
|
|
725
|
-
*
|
|
726
|
-
* - [
|
|
727
|
-
* - ['
|
|
728
|
-
* - ['
|
|
1378
|
+
* Restricts which project types can use this plugin.
|
|
1379
|
+
*
|
|
1380
|
+
* - `undefined` or `[]` — available for ALL project types (default, backward-compatible)
|
|
1381
|
+
* - `['landing']` — only landing page projects
|
|
1382
|
+
* - `['blog']` — only blog projects
|
|
1383
|
+
* - `['landing', 'blog']` — both types
|
|
1384
|
+
*
|
|
1385
|
+
* @default undefined
|
|
729
1386
|
*/
|
|
730
1387
|
projectTypes?: string[];
|
|
731
1388
|
|
|
732
1389
|
/**
|
|
733
1390
|
* Semantic context for dynamic data binding.
|
|
734
|
-
*
|
|
735
|
-
* - '
|
|
1391
|
+
*
|
|
1392
|
+
* - `'static'` — Content defined at design time (default for most plugins)
|
|
1393
|
+
* - `'dynamic'` — Content bound to a collection entry at runtime (blog posts, shop items)
|
|
1394
|
+
*
|
|
1395
|
+
* @default 'static'
|
|
736
1396
|
*/
|
|
737
|
-
contentBinding?:
|
|
1397
|
+
contentBinding?: 'static' | 'dynamic';
|
|
738
1398
|
|
|
739
1399
|
/**
|
|
740
|
-
* Icon component
|
|
1400
|
+
* Icon component rendered in the editor toolbar and plugin browser.
|
|
1401
|
+
* Typically a Lucide icon.
|
|
741
1402
|
*/
|
|
742
1403
|
icon?: ComponentType;
|
|
743
1404
|
|
|
744
1405
|
/**
|
|
745
|
-
* React component to render
|
|
1406
|
+
* React component to render for this plugin.
|
|
1407
|
+
* Must accept props compatible with {@link BasePluginProps}.
|
|
746
1408
|
*/
|
|
747
1409
|
component: ComponentType<any>;
|
|
748
1410
|
|
|
749
1411
|
/**
|
|
750
|
-
*
|
|
1412
|
+
* Array of property definitions describing editable properties.
|
|
1413
|
+
* The Context Panel auto-generates UI controls from these definitions.
|
|
1414
|
+
*
|
|
1415
|
+
* @see {@link PropertyDefinition}
|
|
751
1416
|
*/
|
|
752
1417
|
properties: PropertyDefinition[];
|
|
753
1418
|
|
|
754
1419
|
/**
|
|
755
|
-
* Default values
|
|
1420
|
+
* Default values applied when creating a new instance of this plugin.
|
|
1421
|
+
* Keys correspond to top-level data paths; nested objects are supported.
|
|
756
1422
|
*/
|
|
757
1423
|
defaults: Record<string, unknown>;
|
|
758
1424
|
|
|
759
1425
|
/**
|
|
760
|
-
* Localized strings
|
|
1426
|
+
* Localized UI strings keyed by locale code (e.g., `{ de: {...}, en: {...} }`).
|
|
1427
|
+
* Used for translating property labels and descriptions in the Context Panel.
|
|
761
1428
|
*/
|
|
762
1429
|
locales: Record<string, unknown>;
|
|
763
1430
|
|
|
764
1431
|
/**
|
|
765
|
-
*
|
|
1432
|
+
* Whether this plugin supports server-side rendering.
|
|
1433
|
+
* When `true`, the plugin should provide a Renderer component
|
|
1434
|
+
* that works without `'use client'`.
|
|
766
1435
|
*/
|
|
767
1436
|
ssr: boolean;
|
|
768
1437
|
|
|
769
1438
|
/**
|
|
770
|
-
*
|
|
1439
|
+
* Whether this plugin adapts to different viewport sizes.
|
|
1440
|
+
* When `true`, the plugin uses responsive values from the Design System.
|
|
771
1441
|
*/
|
|
772
1442
|
responsive: boolean;
|
|
773
1443
|
|
|
774
1444
|
/**
|
|
775
|
-
*
|
|
776
|
-
*
|
|
777
|
-
*
|
|
1445
|
+
* Structural capabilities of this plugin — determines nesting rules,
|
|
1446
|
+
* container behavior, and allowed children.
|
|
1447
|
+
*
|
|
1448
|
+
* @see {@link PluginCapabilities}
|
|
778
1449
|
*/
|
|
779
1450
|
capabilities: PluginCapabilities;
|
|
780
1451
|
|
|
781
1452
|
/**
|
|
782
|
-
*
|
|
1453
|
+
* Optional metadata for plugin listings and documentation.
|
|
1454
|
+
* @see {@link PluginMeta}
|
|
783
1455
|
*/
|
|
784
1456
|
meta?: PluginMeta;
|
|
785
1457
|
}
|