@jbpark/live-editor 5.0.0 → 6.1.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.
Files changed (69) hide show
  1. package/README.ko.md +34 -32
  2. package/README.md +34 -32
  3. package/dist/{boundary-6_nTsWxP.js → boundary-CySnDUs2.js} +5 -4
  4. package/dist/boundary-CySnDUs2.js.map +1 -0
  5. package/dist/{compile-DwOyWrmI.js → compile-my0AjsCw.js} +3 -3
  6. package/dist/{compile-DwOyWrmI.js.map → compile-my0AjsCw.js.map} +1 -1
  7. package/dist/{constants-D-XKuEY2.js → constants-st9gnJ5g.js} +1 -4
  8. package/dist/{constants-D-XKuEY2.js.map → constants-st9gnJ5g.js.map} +1 -1
  9. package/dist/{context-DDR1xVKo.js → context-Bjq0CvBE.js} +3 -3
  10. package/dist/{context-DDR1xVKo.js.map → context-Bjq0CvBE.js.map} +1 -1
  11. package/dist/{core-CKazr4tT.js → core-BNVuH8-l.js} +51 -14
  12. package/dist/core-BNVuH8-l.js.map +1 -0
  13. package/dist/{detect-typescript-CoAO-QUJ.js → detect-typescript-CMF0FVKD.js} +2 -2
  14. package/dist/{detect-typescript-CoAO-QUJ.js.map → detect-typescript-CMF0FVKD.js.map} +1 -1
  15. package/dist/dnd/index.d.ts +2 -1
  16. package/dist/dnd/index.js +2 -1
  17. package/dist/{dnd-BlC1gqUy.js → dnd-COjjjuD7.js} +1242 -1459
  18. package/dist/dnd-COjjjuD7.js.map +1 -0
  19. package/dist/{document-DcwIEHRV.js → document-BkGWDZGc.js} +685 -531
  20. package/dist/document-BkGWDZGc.js.map +1 -0
  21. package/dist/edit-options-C_r9aCz4.d.ts +100 -0
  22. package/dist/editor/index.d.ts +1 -1
  23. package/dist/editor/index.js +2 -2
  24. package/dist/{editor-Bty5XzpV.js → editor-CvnzrM9J.js} +2 -2
  25. package/dist/{editor-Bty5XzpV.js.map → editor-CvnzrM9J.js.map} +1 -1
  26. package/dist/error/index.d.ts +1 -1
  27. package/dist/error/index.js +2 -2
  28. package/dist/{error-DyYx2NQ2.js → error-CFzvnLCf.js} +4 -4
  29. package/dist/error-CFzvnLCf.js.map +1 -0
  30. package/dist/{index-tAiuHZsC.d.ts → index-BZpZwrxT.d.ts} +2 -2
  31. package/dist/{index-13BDSrQc.d.ts → index-C93npmTU.d.ts} +4 -6
  32. package/dist/{index-Cl79M7ZJ.d.ts → index-CqsS207F.d.ts} +2 -10
  33. package/dist/{index-0VB5C3Jk.d.ts → index-DQcdHg_V.d.ts} +4 -100
  34. package/dist/{index-kKUjo9lr.d.ts → index-DfIvkht8.d.ts} +3 -3
  35. package/dist/index.d.ts +8 -7
  36. package/dist/index.js +6 -6
  37. package/dist/{messages-Yb3b7YJt.d.ts → messages-BpN3QIhj.d.ts} +4 -1
  38. package/dist/{messages-Bt5WXKTE.js → messages-DrINcRdG.js} +4 -1
  39. package/dist/messages-DrINcRdG.js.map +1 -0
  40. package/dist/preview/index.d.ts +2 -2
  41. package/dist/preview/index.js +2 -3
  42. package/dist/{preview-DC0pyOdu.js → preview-8ejC5VP2.js} +16 -13
  43. package/dist/preview-8ejC5VP2.js.map +1 -0
  44. package/dist/provider/index.d.ts +2 -2
  45. package/dist/provider/index.js +2 -2
  46. package/dist/{sections-4uirsXRU.js → sections-rD8NuRI8.js} +3 -3
  47. package/dist/{sections-4uirsXRU.js.map → sections-rD8NuRI8.js.map} +1 -1
  48. package/dist/style.css +801 -5372
  49. package/dist/ui-kit/index.d.ts +22 -0
  50. package/dist/ui-kit/index.js +1552 -0
  51. package/dist/ui-kit/index.js.map +1 -0
  52. package/dist/ui-kit/style.css +5039 -0
  53. package/dist/{update-DNInQSM7.js → update-DyFnX8yE.js} +3 -3
  54. package/dist/{update-DNInQSM7.js.map → update-DyFnX8yE.js.map} +1 -1
  55. package/dist/{use-dynamic-tailwind-CSYKXDmX.js → use-dynamic-tailwind-0nuRN57N.js} +30 -34
  56. package/dist/use-dynamic-tailwind-0nuRN57N.js.map +1 -0
  57. package/dist/use-field-state-iQGW0vc6.js +131 -0
  58. package/dist/use-field-state-iQGW0vc6.js.map +1 -0
  59. package/dist/utils/ast/index.js +2 -2
  60. package/dist/utils/index.js +2 -2
  61. package/package.json +14 -4
  62. package/dist/boundary-6_nTsWxP.js.map +0 -1
  63. package/dist/core-CKazr4tT.js.map +0 -1
  64. package/dist/dnd-BlC1gqUy.js.map +0 -1
  65. package/dist/document-DcwIEHRV.js.map +0 -1
  66. package/dist/error-DyYx2NQ2.js.map +0 -1
  67. package/dist/messages-Bt5WXKTE.js.map +0 -1
  68. package/dist/preview-DC0pyOdu.js.map +0 -1
  69. package/dist/use-dynamic-tailwind-CSYKXDmX.js.map +0 -1
@@ -0,0 +1,1552 @@
1
+ import { n as createDocument } from "../sections-rD8NuRI8.js";
2
+ import { i as getFieldKind, o as FieldError, t as useFieldState } from "../use-field-state-iQGW0vc6.js";
3
+ import { useEffect, useRef, useState } from "react";
4
+ import { jsx, jsxs } from "react/jsx-runtime";
5
+ import { useDebounce } from "@jbpark/use-hooks";
6
+ import * as ui from "@jbpark/ui-kit";
7
+ import { Checkbox, ColorPicker, DatePicker, RichTextEditor, Select, TimePicker } from "@jbpark/ui-kit";
8
+ import * as utils from "@jbpark/ui-kit/utils";
9
+ //#region src/components/ui-kit/document.ts
10
+ const UI_KIT_IMPORTS = `
11
+ import * as ui from 'ui-kit';
12
+ import { cn } from 'ui-kit/utils';
13
+ `;
14
+ const createUiKitDocument = (options) => UI_KIT_IMPORTS + createDocument(options);
15
+ //#endregion
16
+ //#region src/components/ui-kit/modules.ts
17
+ const uiKitModules = {
18
+ "ui-kit": ui,
19
+ "ui-kit/utils": utils
20
+ };
21
+ //#endregion
22
+ //#region src/components/ui-kit/palette-sections.ts
23
+ const uiKitPaletteSections = [
24
+ {
25
+ id: "hero",
26
+ name: "Hero",
27
+ code: `
28
+ <section
29
+ data-name="Hero"
30
+ className={cn(
31
+ 'text-center text-white',
32
+ //
33
+ )}
34
+ >
35
+ <ui.Space
36
+ data-id=""
37
+ data-binding={[
38
+ {
39
+ label: 'Background Style',
40
+ property: 'style',
41
+ type: 'object',
42
+ // Types the keys inside the object value; a leaf takes the same
43
+ // fields as a top-level binding.
44
+ render: {
45
+ backgroundColor: { type: 'color', label: 'Background Color' },
46
+ },
47
+ // Not a library field, so it arrives as meta.group.
48
+ group: 'layout',
49
+ },
50
+ {
51
+ label: 'Content Spacing',
52
+ property: 'size',
53
+ type: 'number',
54
+ // Constraints the library validates with or without a widget.
55
+ min: 0,
56
+ max: 40,
57
+ // Presentation only: the built-in panel ignores it and shows a
58
+ // number input; a custom panel can switch on widget.type.
59
+ widget: { type: 'slider', step: 4, unit: 'px' },
60
+ group: 'layout',
61
+ },
62
+ ]}
63
+ style={{
64
+ backgroundColor: '#6366f1',
65
+ }}
66
+ orientation="vertical"
67
+ size={16}
68
+ align="center"
69
+ className={cn(
70
+ 'px-5 py-15',
71
+ //
72
+ )}
73
+ >
74
+ <h1
75
+ data-id=""
76
+ data-binding={[
77
+ {
78
+ label: 'Title',
79
+ property: 'innerText',
80
+ type: 'string',
81
+ required: true,
82
+ },
83
+ ]}
84
+ className={cn(
85
+ 'text-5xl font-bold',
86
+ //
87
+ )}
88
+ >
89
+ Welcome to Live Editor
90
+ </h1>
91
+ <p
92
+ data-id=""
93
+ data-binding={[
94
+ {
95
+ label: 'Description',
96
+ type: 'richtext',
97
+ },
98
+ ]}
99
+ className={cn(
100
+ 'text-xl',
101
+ //
102
+ )}
103
+ >
104
+ Build <strong>dynamic components</strong> with drag & drop
105
+ </p>
106
+ <ui.Button
107
+ data-id=""
108
+ data-binding={[
109
+ {
110
+ label: 'Button Text',
111
+ property: 'innerText',
112
+ },
113
+ {
114
+ label: 'Button Icon',
115
+ property: 'icon',
116
+ type: 'jsx',
117
+ },
118
+ {
119
+ label: 'Button Size',
120
+ property: 'size',
121
+ options: [
122
+ { label: 'Small', value: 'small' },
123
+ { label: 'Middle', value: 'middle' },
124
+ { label: 'Large', value: 'large' },
125
+ ],
126
+ },
127
+ {
128
+ label: 'Button Variant',
129
+ property: 'variant',
130
+ options: [
131
+ { label: 'Solid', value: 'solid' },
132
+ { label: 'Outlined', value: 'outlined' },
133
+ { label: 'Filled', value: 'filled' },
134
+ ],
135
+ },
136
+ ]}
137
+ icon={<span>🚀</span>}
138
+ size="large"
139
+ variant="solid"
140
+ className={cn(
141
+ 'bg-white text-indigo-500',
142
+ 'hover:bg-gray-50',
143
+ //
144
+ )}
145
+ >
146
+ Get Started
147
+ </ui.Button>
148
+ </ui.Space>
149
+ </section>
150
+ `
151
+ },
152
+ {
153
+ id: "features",
154
+ name: "Features",
155
+ code: `
156
+ <section
157
+ data-name="Features"
158
+ className={cn(
159
+ 'px-5 py-10',
160
+ //
161
+ )}
162
+ >
163
+ <ui.Space
164
+ data-id=""
165
+ data-binding={[
166
+ {
167
+ label: 'Feature Cards',
168
+ property: 'children',
169
+ },
170
+ ]}
171
+ className={cn(
172
+ 'mx-auto max-w-7xl',
173
+ //
174
+ )}
175
+ size="large"
176
+ wrap
177
+ >
178
+ <ui.Card
179
+ className={cn(
180
+ 'min-w-70 flex-1 text-center',
181
+ //
182
+ )}
183
+ >
184
+ <ui.Space orientation="vertical" size="middle" align="center">
185
+ <div
186
+ data-id=""
187
+ data-binding={[
188
+ {
189
+ label: 'Icon',
190
+ property: 'innerText',
191
+ },
192
+ ]}
193
+ className={cn(
194
+ 'text-5xl',
195
+ //
196
+ )}
197
+ >
198
+ 🚀
199
+ </div>
200
+ <h3
201
+ data-id=""
202
+ data-binding={[
203
+ {
204
+ label: 'Title',
205
+ property: 'innerText',
206
+ },
207
+ ]}
208
+ className={cn(
209
+ 'text-2xl text-gray-800',
210
+ //
211
+ )}
212
+ >
213
+ Feature 1
214
+ </h3>
215
+ <p
216
+ data-id=""
217
+ data-binding={[
218
+ {
219
+ label: 'Description',
220
+ property: 'innerText',
221
+ },
222
+ ]}
223
+ className={cn(
224
+ 'text-gray-600',
225
+ //
226
+ )}
227
+ >
228
+ Amazing feature description
229
+ </p>
230
+ </ui.Space>
231
+ </ui.Card>
232
+ <ui.Card
233
+ className={cn(
234
+ 'min-w-70 flex-1 text-center',
235
+ //
236
+ )}
237
+ >
238
+ <ui.Space orientation="vertical" size="middle" align="center">
239
+ <div
240
+ data-id=""
241
+ data-binding={[
242
+ {
243
+ label: 'Icon',
244
+ property: 'innerText',
245
+ },
246
+ ]}
247
+ className={cn(
248
+ 'text-5xl',
249
+ //
250
+ )}
251
+ >
252
+ ⚡
253
+ </div>
254
+ <h3
255
+ data-id=""
256
+ data-binding={[
257
+ {
258
+ label: 'Title',
259
+ property: 'innerText',
260
+ },
261
+ ]}
262
+ className={cn(
263
+ 'text-2xl text-gray-800',
264
+ //
265
+ )}
266
+ >
267
+ Feature 2
268
+ </h3>
269
+ <p
270
+ data-id=""
271
+ data-binding={[
272
+ {
273
+ label: 'Description',
274
+ property: 'innerText',
275
+ },
276
+ ]}
277
+ className={cn(
278
+ 'text-gray-600',
279
+ //
280
+ )}
281
+ >
282
+ Another great feature
283
+ </p>
284
+ </ui.Space>
285
+ </ui.Card>
286
+ <ui.Card
287
+ className={cn(
288
+ 'min-w-70 flex-1 text-center',
289
+ //
290
+ )}
291
+ >
292
+ <ui.Space orientation="vertical" size="middle" align="center">
293
+ <div
294
+ data-id=""
295
+ data-binding={[
296
+ {
297
+ label: 'Icon',
298
+ property: 'innerText',
299
+ },
300
+ ]}
301
+ className={cn(
302
+ 'text-5xl',
303
+ //
304
+ )}
305
+ >
306
+ ✨
307
+ </div>
308
+ <h3
309
+ data-id=""
310
+ data-binding={[
311
+ {
312
+ label: 'Title',
313
+ property: 'innerText',
314
+ },
315
+ ]}
316
+ className={cn(
317
+ 'text-2xl text-gray-800',
318
+ //
319
+ )}
320
+ >
321
+ Feature 3
322
+ </h3>
323
+ <p
324
+ data-id=""
325
+ data-binding={[
326
+ {
327
+ label: 'Description',
328
+ property: 'innerText',
329
+ },
330
+ ]}
331
+ className={cn(
332
+ 'text-gray-600',
333
+ //
334
+ )}
335
+ >
336
+ One more awesome thing
337
+ </p>
338
+ </ui.Space>
339
+ </ui.Card>
340
+ </ui.Space>
341
+ </section>
342
+ `
343
+ },
344
+ {
345
+ id: "about",
346
+ name: "About",
347
+ code: `
348
+ <section
349
+ data-name="About"
350
+ className={cn(
351
+ 'mx-auto max-w-3xl px-5 py-10',
352
+ //
353
+ )}
354
+ >
355
+ <ui.Typography.Title
356
+ data-id=""
357
+ data-binding={[{ label: 'Title', property: 'innerText' }]}
358
+ level={2}
359
+ className={cn(
360
+ 'mb-5 text-4xl text-gray-800',
361
+ //
362
+ )}
363
+ >
364
+ About Live Editor
365
+ </ui.Typography.Title>
366
+ <ui.Typography.Paragraph
367
+ data-id=""
368
+ data-binding={[
369
+ {
370
+ label: 'Description 1',
371
+ type: 'richtext',
372
+ },
373
+ ]}
374
+ className={cn(
375
+ 'mb-4 text-lg leading-relaxed text-gray-600',
376
+ //
377
+ )}
378
+ >
379
+ Live Editor is a powerful visual development tool that enables you to
380
+ create stunning web interfaces through an intuitive drag-and-drop
381
+ experience. Built with modern web technologies, it streamlines your
382
+ workflow and accelerates development cycles.
383
+ </ui.Typography.Paragraph>
384
+ <ui.Typography.Paragraph
385
+ data-id=""
386
+ data-binding={[
387
+ {
388
+ label: 'Description 2',
389
+ type: 'richtext',
390
+ },
391
+ ]}
392
+ className={cn(
393
+ 'text-lg leading-relaxed text-gray-600',
394
+ //
395
+ )}
396
+ >
397
+ Whether you&apos;re a seasoned developer or just starting out, Live
398
+ Editor provides the flexibility and control you need to bring your
399
+ creative vision to life. Focus on what matters most - building great
400
+ products.
401
+ </ui.Typography.Paragraph>
402
+ </section>
403
+ `
404
+ },
405
+ {
406
+ id: "cta",
407
+ name: "CTA",
408
+ code: `
409
+ <section
410
+ data-name="CTA"
411
+ className={cn(
412
+ 'bg-gray-50 px-5 py-12 text-center',
413
+ //
414
+ )}
415
+ >
416
+ <div
417
+ className={cn(
418
+ 'mx-auto max-w-xl',
419
+ //
420
+ )}
421
+ >
422
+ <ui.Typography.Title
423
+ data-id=""
424
+ data-binding={[{ label: 'Title', property: 'innerText' }]}
425
+ level={2}
426
+ className={cn(
427
+ 'mb-4 text-3xl text-gray-800',
428
+ //
429
+ )}
430
+ >
431
+ Ready to get started?
432
+ </ui.Typography.Title>
433
+ <ui.Typography.Paragraph
434
+ data-id=""
435
+ data-binding={[
436
+ {
437
+ label: 'Description',
438
+ property: 'innerText',
439
+ },
440
+ ]}
441
+ className={cn(
442
+ 'mb-6 text-lg text-gray-600',
443
+ //
444
+ )}
445
+ >
446
+ Start exploring what Live Editor can do for your projects
447
+ </ui.Typography.Paragraph>
448
+ <ui.Space
449
+ data-id=""
450
+ data-binding={[{ label: 'Buttons', property: 'children' }]}
451
+ className={cn(
452
+ 'flex flex-wrap justify-center gap-4',
453
+ //
454
+ )}
455
+ >
456
+ <ui.Button
457
+ data-id=""
458
+ data-binding={[
459
+ {
460
+ label: 'Button 1 Text',
461
+ property: 'innerText',
462
+ },
463
+ ]}
464
+ size="large"
465
+ className={cn(
466
+ 'bg-indigo-500 px-8 text-base text-white',
467
+ 'hover:bg-indigo-600',
468
+ //
469
+ )}
470
+ >
471
+ View Documentation
472
+ </ui.Button>
473
+ <ui.Button
474
+ data-id=""
475
+ data-binding={[
476
+ {
477
+ label: 'Button 2 Text',
478
+ property: 'innerText',
479
+ },
480
+ ]}
481
+ variant="outlined"
482
+ size="large"
483
+ className={cn(
484
+ 'border-2 border-indigo-500 px-8 text-base text-indigo-500',
485
+ 'hover:bg-indigo-50',
486
+ //
487
+ )}
488
+ >
489
+ View Examples
490
+ </ui.Button>
491
+ </ui.Space>
492
+ </div>
493
+ </section>
494
+ `
495
+ },
496
+ {
497
+ id: "getting-started",
498
+ name: "Getting Started",
499
+ code: `
500
+ <section
501
+ data-name="Getting Started"
502
+ className={cn(
503
+ 'px-5 py-16',
504
+ //
505
+ )}
506
+ >
507
+ <div
508
+ className={cn(
509
+ 'mx-auto max-w-5xl',
510
+ //
511
+ )}
512
+ >
513
+ <ui.Typography.Title
514
+ data-id=""
515
+ data-binding={[{ label: 'Title', property: 'innerText' }]}
516
+ level={2}
517
+ className={cn(
518
+ 'mb-12 text-center text-4xl font-bold text-gray-800',
519
+ //
520
+ )}
521
+ >
522
+ How to Get Started
523
+ </ui.Typography.Title>
524
+ <div
525
+ className={cn(
526
+ 'grid gap-8 md:grid-cols-3',
527
+ //
528
+ )}
529
+ >
530
+ <ui.Card
531
+ data-id=""
532
+ data-binding={[
533
+ {
534
+ label: 'Card 1 Content',
535
+ property: 'children',
536
+ },
537
+ ]}
538
+ className={cn(
539
+ 'rounded-lg border-2 border-gray-200 bg-white p-8',
540
+ //
541
+ )}
542
+ >
543
+ <ui.Typography.Title
544
+ data-id=""
545
+ data-binding={[
546
+ {
547
+ label: 'Card 1 Title',
548
+ property: 'innerText',
549
+ },
550
+ ]}
551
+ level={3}
552
+ className={cn(
553
+ 'mb-2 text-2xl font-bold text-gray-800',
554
+ //
555
+ )}
556
+ >
557
+ Explore
558
+ </ui.Typography.Title>
559
+ <ui.Typography.Paragraph
560
+ data-id=""
561
+ data-binding={[
562
+ {
563
+ label: 'Card 1 Icon',
564
+ property: 'innerText',
565
+ },
566
+ ]}
567
+ className={cn(
568
+ 'mb-6 text-4xl font-bold text-indigo-600',
569
+ //
570
+ )}
571
+ >
572
+ 📚
573
+ </ui.Typography.Paragraph>
574
+ <ul
575
+ className={cn(
576
+ 'mb-8 space-y-3 text-gray-600',
577
+ //
578
+ )}
579
+ >
580
+ <li>✓ Read documentation</li>
581
+ <li>✓ Browse examples</li>
582
+ <li>✓ Try the demo</li>
583
+ </ul>
584
+ <ui.Button
585
+ data-id=""
586
+ data-binding={[
587
+ {
588
+ label: 'Card 1 Button',
589
+ property: 'innerText',
590
+ },
591
+ ]}
592
+ variant="outlined"
593
+ size="large"
594
+ block
595
+ className={cn(
596
+ 'border-2 border-indigo-500 text-indigo-500',
597
+ 'hover:bg-indigo-50',
598
+ //
599
+ )}
600
+ >
601
+ View Docs
602
+ </ui.Button>
603
+ </ui.Card>
604
+ <ui.Card
605
+ data-id=""
606
+ data-binding={[
607
+ {
608
+ label: 'Card 2 Content',
609
+ property: 'children',
610
+ },
611
+ ]}
612
+ className={cn(
613
+ 'relative rounded-lg border-2 border-indigo-500 bg-white p-8',
614
+ //
615
+ )}
616
+ >
617
+ <div
618
+ className={cn(
619
+ 'absolute -top-4 left-1/2 -translate-x-1/2',
620
+ 'rounded-full bg-indigo-500 px-4 py-1 text-sm text-white',
621
+ //
622
+ )}
623
+ >
624
+ Recommended
625
+ </div>
626
+ <ui.Typography.Title
627
+ data-id=""
628
+ data-binding={[
629
+ {
630
+ label: 'Card 2 Title',
631
+ property: 'innerText',
632
+ },
633
+ ]}
634
+ level={3}
635
+ className={cn(
636
+ 'mb-2 text-2xl font-bold text-gray-800',
637
+ //
638
+ )}
639
+ >
640
+ Practice
641
+ </ui.Typography.Title>
642
+ <ui.Typography.Paragraph
643
+ data-id=""
644
+ data-binding={[
645
+ {
646
+ label: 'Card 2 Icon',
647
+ property: 'innerText',
648
+ },
649
+ ]}
650
+ className={cn(
651
+ 'mb-6 text-4xl font-bold text-indigo-600',
652
+ //
653
+ )}
654
+ >
655
+ 💻
656
+ </ui.Typography.Paragraph>
657
+ <ul
658
+ className={cn(
659
+ 'mb-8 space-y-3 text-gray-600',
660
+ //
661
+ )}
662
+ >
663
+ <li>✓ Interactive playground</li>
664
+ <li>✓ Experiment freely</li>
665
+ <li>✓ Build your own</li>
666
+ </ul>
667
+ <ui.Button
668
+ data-id=""
669
+ data-binding={[
670
+ {
671
+ label: 'Card 2 Button',
672
+ property: 'innerText',
673
+ },
674
+ ]}
675
+ size="large"
676
+ block
677
+ className={cn(
678
+ 'bg-indigo-500 text-white',
679
+ 'hover:bg-indigo-600',
680
+ //
681
+ )}
682
+ >
683
+ Start Building
684
+ </ui.Button>
685
+ </ui.Card>
686
+ <ui.Card
687
+ data-id=""
688
+ data-binding={[
689
+ {
690
+ label: 'Card 3 Content',
691
+ property: 'children',
692
+ },
693
+ ]}
694
+ className={cn(
695
+ 'rounded-lg border-2 border-gray-200 bg-white p-8',
696
+ //
697
+ )}
698
+ >
699
+ <ui.Typography.Title
700
+ data-id=""
701
+ data-binding={[
702
+ {
703
+ label: 'Card 3 Title',
704
+ property: 'innerText',
705
+ },
706
+ ]}
707
+ level={3}
708
+ className={cn(
709
+ 'mb-2 text-2xl font-bold text-gray-800',
710
+ //
711
+ )}
712
+ >
713
+ Contribute
714
+ </ui.Typography.Title>
715
+ <ui.Typography.Paragraph
716
+ data-id=""
717
+ data-binding={[
718
+ {
719
+ label: 'Card 3 Icon',
720
+ property: 'innerText',
721
+ },
722
+ ]}
723
+ className={cn(
724
+ 'mb-6 text-4xl font-bold text-indigo-600',
725
+ //
726
+ )}
727
+ >
728
+ 🤝
729
+ </ui.Typography.Paragraph>
730
+ <ul
731
+ className={cn(
732
+ 'mb-8 space-y-3 text-gray-600',
733
+ //
734
+ )}
735
+ >
736
+ <li>✓ Report issues</li>
737
+ <li>✓ Suggest features</li>
738
+ <li>✓ Submit pull requests</li>
739
+ </ul>
740
+ <ui.Button
741
+ data-id=""
742
+ data-binding={[
743
+ {
744
+ label: 'Card 3 Button',
745
+ property: 'innerText',
746
+ },
747
+ ]}
748
+ variant="outlined"
749
+ size="large"
750
+ block
751
+ className={cn(
752
+ 'border-2 border-indigo-500 text-indigo-500',
753
+ 'hover:bg-indigo-50',
754
+ //
755
+ )}
756
+ >
757
+ View on GitHub
758
+ </ui.Button>
759
+ </ui.Card>
760
+ </div>
761
+ </div>
762
+ </section>
763
+ `
764
+ },
765
+ {
766
+ id: "key-features",
767
+ name: "Key Features",
768
+ code: `
769
+ <section
770
+ data-name="Key Features"
771
+ className={cn(
772
+ 'bg-indigo-50 px-5 py-16',
773
+ //
774
+ )}
775
+ >
776
+ <div
777
+ className={cn(
778
+ 'mx-auto max-w-6xl',
779
+ //
780
+ )}
781
+ >
782
+ <h2
783
+ data-id=""
784
+ data-binding={[{ label: 'Title', property: 'innerText' }]}
785
+ className={cn(
786
+ 'mb-12 text-center text-4xl font-bold text-gray-800',
787
+ //
788
+ )}
789
+ >
790
+ Key Features
791
+ </h2>
792
+ <div
793
+ className={cn(
794
+ 'grid gap-8 md:grid-cols-2',
795
+ //
796
+ )}
797
+ >
798
+ <div
799
+ className={cn(
800
+ 'rounded-lg bg-white p-8 shadow-md',
801
+ //
802
+ )}
803
+ >
804
+ <div
805
+ className={cn(
806
+ 'mb-4 text-4xl',
807
+ //
808
+ )}
809
+ >
810
+ 🎨
811
+ </div>
812
+ <h3
813
+ className={cn(
814
+ 'mb-4 text-2xl font-bold text-gray-800',
815
+ //
816
+ )}
817
+ >
818
+ Visual Editing
819
+ </h3>
820
+ <p
821
+ className={cn(
822
+ 'text-gray-600',
823
+ //
824
+ )}
825
+ >
826
+ See your changes in real-time as you build. Live Editor provides
827
+ instant visual feedback, making it easier to understand how code
828
+ affects your interface.
829
+ </p>
830
+ </div>
831
+ <div
832
+ className={cn(
833
+ 'rounded-lg bg-white p-8 shadow-md',
834
+ //
835
+ )}
836
+ >
837
+ <div
838
+ className={cn(
839
+ 'mb-4 text-4xl',
840
+ //
841
+ )}
842
+ >
843
+ 🧩
844
+ </div>
845
+ <h3
846
+ className={cn(
847
+ 'mb-4 text-2xl font-bold text-gray-800',
848
+ //
849
+ )}
850
+ >
851
+ Component-Based
852
+ </h3>
853
+ <p
854
+ className={cn(
855
+ 'text-gray-600',
856
+ //
857
+ )}
858
+ >
859
+ Build with reusable components that you can drag, drop, and
860
+ customize. Learn modern development patterns while creating your
861
+ interface.
862
+ </p>
863
+ </div>
864
+ </div>
865
+ </div>
866
+ </section>
867
+ `
868
+ },
869
+ {
870
+ id: "stats",
871
+ name: "Stats",
872
+ code: `
873
+ <section
874
+ data-name="Stats"
875
+ className={cn(
876
+ 'bg-indigo-600 text-white',
877
+ //
878
+ )}
879
+ >
880
+ <ui.Marquees
881
+ data-id=""
882
+ data-binding={[
883
+ { label: 'Stats Items', property: 'items' },
884
+ {
885
+ label: 'Scroll Speed',
886
+ property: 'speed',
887
+ type: 'number',
888
+ min: 20,
889
+ max: 300,
890
+ // The bare-string form; it arrives as { type: 'slider' }.
891
+ widget: 'slider',
892
+ },
893
+ { label: 'Pause On Hover', property: 'pauseOnHover', type: 'boolean' },
894
+ ]}
895
+ speed={100}
896
+ pauseOnHover={true}
897
+ autoFill={true}
898
+ className="px-5 py-16"
899
+ items={[
900
+ {
901
+ key: 'stats-row',
902
+ children: (
903
+ <div
904
+ data-id=""
905
+ data-binding={[
906
+ {
907
+ label: 'Stats Cards',
908
+ property: 'children',
909
+ },
910
+ ]}
911
+ className={cn('flex gap-20')}
912
+ >
913
+ <div
914
+ className={cn(
915
+ 'min-w-60 text-center',
916
+ //
917
+ )}
918
+ >
919
+ <p
920
+ data-id=""
921
+ data-binding={[
922
+ {
923
+ label: 'Title',
924
+ property: 'innerText',
925
+ },
926
+ ]}
927
+ className={cn(
928
+ 'mb-2 text-5xl font-bold',
929
+ //
930
+ )}
931
+ >
932
+ Open
933
+ </p>
934
+ <p
935
+ data-id=""
936
+ data-binding={[
937
+ {
938
+ label: 'Description',
939
+ property: 'innerText',
940
+ },
941
+ ]}
942
+ className={cn(
943
+ 'text-indigo-200',
944
+ //
945
+ )}
946
+ >
947
+ Source Project
948
+ </p>
949
+ </div>
950
+ <div
951
+ className={cn(
952
+ 'min-w-60 text-center',
953
+ //
954
+ )}
955
+ >
956
+ <p
957
+ data-id=""
958
+ data-binding={[
959
+ {
960
+ label: 'Title',
961
+ property: 'innerText',
962
+ },
963
+ ]}
964
+ className={cn(
965
+ 'mb-2 text-5xl font-bold',
966
+ //
967
+ )}
968
+ >
969
+ Free
970
+ </p>
971
+ <p
972
+ data-id=""
973
+ data-binding={[
974
+ {
975
+ label: 'Description',
976
+ property: 'innerText',
977
+ },
978
+ ]}
979
+ className={cn(
980
+ 'text-indigo-200',
981
+ //
982
+ )}
983
+ >
984
+ For Everyone
985
+ </p>
986
+ </div>
987
+ <div
988
+ className={cn(
989
+ 'min-w-60 text-center',
990
+ //
991
+ )}
992
+ >
993
+ <p
994
+ data-id=""
995
+ data-binding={[
996
+ {
997
+ label: 'Title',
998
+ property: 'innerText',
999
+ },
1000
+ ]}
1001
+ className={cn(
1002
+ 'mb-2 text-5xl font-bold',
1003
+ //
1004
+ )}
1005
+ >
1006
+ Active
1007
+ </p>
1008
+ <p
1009
+ data-id=""
1010
+ data-binding={[
1011
+ {
1012
+ label: 'Description',
1013
+ property: 'innerText',
1014
+ },
1015
+ ]}
1016
+ className={cn(
1017
+ 'text-indigo-200',
1018
+ //
1019
+ )}
1020
+ >
1021
+ Community
1022
+ </p>
1023
+ </div>
1024
+ <div
1025
+ className={cn(
1026
+ 'min-w-60 text-center',
1027
+ //
1028
+ )}
1029
+ >
1030
+ <p
1031
+ data-id=""
1032
+ data-binding={[
1033
+ {
1034
+ label: 'Title',
1035
+ property: 'innerText',
1036
+ },
1037
+ ]}
1038
+ className={cn(
1039
+ 'mb-2 text-5xl font-bold',
1040
+ //
1041
+ )}
1042
+ >
1043
+ Learn
1044
+ </p>
1045
+ <p
1046
+ data-id=""
1047
+ data-binding={[
1048
+ {
1049
+ label: 'Description',
1050
+ property: 'innerText',
1051
+ },
1052
+ ]}
1053
+ className={cn(
1054
+ 'text-indigo-200',
1055
+ //
1056
+ )}
1057
+ >
1058
+ By Doing
1059
+ </p>
1060
+ </div>
1061
+ </div>
1062
+ ),
1063
+ },
1064
+ ]}
1065
+ />
1066
+ </section>
1067
+ `
1068
+ },
1069
+ {
1070
+ id: "roadmap",
1071
+ name: "Roadmap",
1072
+ code: `
1073
+ <section
1074
+ data-name="Roadmap"
1075
+ className={cn(
1076
+ 'px-5 py-16',
1077
+ //
1078
+ )}
1079
+ >
1080
+ <div
1081
+ className={cn(
1082
+ 'mx-auto max-w-3xl',
1083
+ //
1084
+ )}
1085
+ >
1086
+ <h2
1087
+ data-id=""
1088
+ data-binding={[
1089
+ { label: 'Title', property: 'innerText', required: true },
1090
+ ]}
1091
+ className={cn(
1092
+ 'mb-8 text-center text-4xl font-bold text-gray-800',
1093
+ //
1094
+ )}
1095
+ >
1096
+ Roadmap
1097
+ </h2>
1098
+ <ui.List
1099
+ data-id=""
1100
+ data-binding={[
1101
+ {
1102
+ label: 'Milestones',
1103
+ property: 'data',
1104
+ type: 'array',
1105
+ // One leaf per item key. Each leaf takes the same fields as a
1106
+ // top-level binding, and label falls back to the key.
1107
+ render: {
1108
+ title: {
1109
+ type: 'string',
1110
+ label: 'Title',
1111
+ required: true,
1112
+ },
1113
+ date: { type: 'date', label: 'Release Date', required: true },
1114
+ status: {
1115
+ type: 'string',
1116
+ label: 'Status',
1117
+ options: [
1118
+ { label: 'Planned', value: 'planned' },
1119
+ { label: 'In Progress', value: 'in-progress' },
1120
+ { label: 'Shipped', value: 'shipped' },
1121
+ ],
1122
+ },
1123
+ progress: {
1124
+ type: 'number',
1125
+ label: 'Progress',
1126
+ min: 0,
1127
+ max: 100,
1128
+ widget: { type: 'slider', step: 10, unit: '%' },
1129
+ },
1130
+ color: { type: 'color', label: 'Accent Color' },
1131
+ highlight: { type: 'boolean', label: 'Highlight' },
1132
+ // An object-valued key: its own render map types the keys
1133
+ // inside it, one level further down.
1134
+ link: {
1135
+ type: 'object',
1136
+ label: 'Link',
1137
+ render: {
1138
+ text: { type: 'string', label: 'Link Text' },
1139
+ href: {
1140
+ type: 'url',
1141
+ label: 'Link URL',
1142
+ pattern: '^https://',
1143
+ // Not a library field, so it arrives as meta.hint.
1144
+ hint: 'Must use https',
1145
+ },
1146
+ },
1147
+ },
1148
+ },
1149
+ },
1150
+ ]}
1151
+ data={[
1152
+ {
1153
+ title: 'Visual editing',
1154
+ date: '2026-03-02',
1155
+ status: 'shipped',
1156
+ progress: 100,
1157
+ color: '#22c55e',
1158
+ highlight: false,
1159
+ link: { text: 'Release notes', href: 'https://github.com' },
1160
+ },
1161
+ {
1162
+ title: 'Custom panels',
1163
+ date: '2026-09-26',
1164
+ status: 'in-progress',
1165
+ progress: 60,
1166
+ color: '#6366f1',
1167
+ highlight: true,
1168
+ link: { text: 'Guide', href: 'https://github.com' },
1169
+ },
1170
+ {
1171
+ title: 'Collaboration',
1172
+ date: '2027-01-15',
1173
+ status: 'planned',
1174
+ progress: 0,
1175
+ color: '#f59e0b',
1176
+ highlight: false,
1177
+ link: { text: 'Discussion', href: 'https://github.com' },
1178
+ },
1179
+ ]}
1180
+ itemKey={item => item.title}
1181
+ renderItem={item => (
1182
+ <div
1183
+ className={cn(
1184
+ 'flex items-center gap-4 border-b border-gray-100 py-4',
1185
+ item.highlight && 'rounded-lg bg-indigo-50 px-4',
1186
+ )}
1187
+ >
1188
+ <span
1189
+ className="size-3 shrink-0 rounded-full"
1190
+ style={{ backgroundColor: item.color }}
1191
+ />
1192
+ <div className="min-w-0 flex-1">
1193
+ <p className="font-semibold text-gray-800">{item.title}</p>
1194
+ <p className="text-sm text-gray-500">
1195
+ {item.date} · {item.status}
1196
+ </p>
1197
+ <ui.Progress value={item.progress} className="mt-2" />
1198
+ </div>
1199
+ <a
1200
+ href={item.link.href}
1201
+ className="text-sm text-indigo-500 hover:underline"
1202
+ >
1203
+ {item.link.text}
1204
+ </a>
1205
+ </div>
1206
+ )}
1207
+ />
1208
+ <p
1209
+ className={cn(
1210
+ 'mt-6 text-center text-sm text-gray-500',
1211
+ //
1212
+ )}
1213
+ >
1214
+ Last updated{' '}
1215
+ <time
1216
+ data-id=""
1217
+ data-binding={[
1218
+ {
1219
+ label: 'Updated On',
1220
+ property: 'dateTime',
1221
+ type: 'date',
1222
+ required: true,
1223
+ },
1224
+ { label: 'Updated Text', property: 'innerText' },
1225
+ ]}
1226
+ dateTime="2026-09-26"
1227
+ >
1228
+ September 26, 2026
1229
+ </time>
1230
+ {' · '}
1231
+ <a
1232
+ data-id=""
1233
+ data-binding={[
1234
+ { label: 'Link Text', property: 'innerText' },
1235
+ {
1236
+ label: 'Link URL',
1237
+ property: 'href',
1238
+ type: 'url',
1239
+ required: true,
1240
+ pattern: '^https://',
1241
+ },
1242
+ ]}
1243
+ href="https://github.com/pjb0811/live-editor/releases"
1244
+ className="text-indigo-500 hover:underline"
1245
+ >
1246
+ All releases
1247
+ </a>
1248
+ </p>
1249
+ </div>
1250
+ </section>
1251
+ `
1252
+ },
1253
+ {
1254
+ id: "faq",
1255
+ name: "FAQ",
1256
+ code: `
1257
+ <section
1258
+ data-name="FAQ"
1259
+ className={cn(
1260
+ 'px-5 py-16',
1261
+ //
1262
+ )}
1263
+ >
1264
+ <div
1265
+ className={cn(
1266
+ 'mx-auto max-w-3xl',
1267
+ //
1268
+ )}
1269
+ >
1270
+ <ui.Typography.Title
1271
+ data-id=""
1272
+ data-binding={[{ label: 'Title', property: 'innerText' }]}
1273
+ level={2}
1274
+ className={cn(
1275
+ 'mb-12 text-center text-4xl font-bold text-gray-800',
1276
+ //
1277
+ )}
1278
+ >
1279
+ Frequently Asked Questions
1280
+ </ui.Typography.Title>
1281
+ <ui.Collapse
1282
+ data-id=""
1283
+ data-binding={[{ label: 'FAQ Items', property: 'items' }]}
1284
+ items={[
1285
+ {
1286
+ key: '1',
1287
+ label: (
1288
+ <ui.Typography.Text
1289
+ data-id=""
1290
+ data-binding={[
1291
+ {
1292
+ label: 'Question 1',
1293
+ property: 'innerText',
1294
+ },
1295
+ ]}
1296
+ className={cn('text-lg font-semibold text-gray-800')}
1297
+ >
1298
+ What is Live Editor?
1299
+ </ui.Typography.Text>
1300
+ ),
1301
+ children: (
1302
+ <ui.Typography.Paragraph
1303
+ data-id=""
1304
+ data-binding={[
1305
+ {
1306
+ label: 'Answer 1',
1307
+ type: 'richtext',
1308
+ },
1309
+ ]}
1310
+ className={cn('text-gray-600')}
1311
+ >
1312
+ Live Editor is an open-source tool for building web
1313
+ interfaces visually. It helps you learn web development by
1314
+ providing instant feedback as you build components.
1315
+ </ui.Typography.Paragraph>
1316
+ ),
1317
+ },
1318
+ {
1319
+ key: '2',
1320
+ label: (
1321
+ <ui.Typography.Text
1322
+ data-id=""
1323
+ data-binding={[
1324
+ {
1325
+ label: 'Question 2',
1326
+ property: 'innerText',
1327
+ },
1328
+ ]}
1329
+ className={cn('text-lg font-semibold text-gray-800')}
1330
+ >
1331
+ Do I need coding experience?
1332
+ </ui.Typography.Text>
1333
+ ),
1334
+ children: (
1335
+ <ui.Typography.Paragraph
1336
+ data-id=""
1337
+ data-binding={[
1338
+ {
1339
+ label: 'Answer 2',
1340
+ type: 'richtext',
1341
+ },
1342
+ ]}
1343
+ className={cn('text-gray-600')}
1344
+ >
1345
+ No! Live Editor is designed for all skill levels. Beginners
1346
+ can learn through visual editing, while experienced
1347
+ developers can work directly with code.
1348
+ </ui.Typography.Paragraph>
1349
+ ),
1350
+ },
1351
+ {
1352
+ key: '3',
1353
+ label: (
1354
+ <ui.Typography.Text
1355
+ data-id=""
1356
+ data-binding={[
1357
+ {
1358
+ label: 'Question 3',
1359
+ property: 'innerText',
1360
+ },
1361
+ ]}
1362
+ className={cn('text-lg font-semibold text-gray-800')}
1363
+ >
1364
+ Is it really free?
1365
+ </ui.Typography.Text>
1366
+ ),
1367
+ children: (
1368
+ <ui.Typography.Paragraph
1369
+ data-id=""
1370
+ data-binding={[
1371
+ {
1372
+ label: 'Answer 3',
1373
+ type: 'richtext',
1374
+ },
1375
+ ]}
1376
+ className={cn('text-gray-600')}
1377
+ >
1378
+ Yes, completely free! Live Editor is an open-source project
1379
+ with no hidden costs or premium tiers. All features are
1380
+ available to everyone.
1381
+ </ui.Typography.Paragraph>
1382
+ ),
1383
+ },
1384
+ {
1385
+ key: '4',
1386
+ label: (
1387
+ <ui.Typography.Text
1388
+ data-id=""
1389
+ data-binding={[
1390
+ {
1391
+ label: 'Question 4',
1392
+ property: 'innerText',
1393
+ },
1394
+ ]}
1395
+ className={cn('text-lg font-semibold text-gray-800')}
1396
+ >
1397
+ How can I contribute?
1398
+ </ui.Typography.Text>
1399
+ ),
1400
+ children: (
1401
+ <ui.Typography.Paragraph
1402
+ data-id=""
1403
+ data-binding={[
1404
+ {
1405
+ label: 'Answer 4',
1406
+ type: 'richtext',
1407
+ },
1408
+ ]}
1409
+ className={cn('text-gray-600')}
1410
+ >
1411
+ You can contribute by reporting bugs, suggesting features,
1412
+ sharing your projects, or contributing code. Check our
1413
+ GitHub repository for more details.
1414
+ </ui.Typography.Paragraph>
1415
+ ),
1416
+ },
1417
+ ]}
1418
+ />
1419
+ </div>
1420
+ </section>
1421
+ `
1422
+ }
1423
+ ];
1424
+ //#endregion
1425
+ //#region src/components/ui-kit/color-picker-field.tsx
1426
+ const COLOR_COMMIT_DELAY = 75;
1427
+ const normalizeToHex = (value) => {
1428
+ const trimmed = value.trim();
1429
+ if (/^#([0-9A-Fa-f]{3}){1,2}$/.test(trimmed)) return trimmed;
1430
+ return "#000000";
1431
+ };
1432
+ const ColorPickerField = ({ value: source, onChange, label }) => {
1433
+ const value = normalizeToHex(source);
1434
+ const [liveValue, setLiveValue] = useState(value);
1435
+ const [prevValue, setPrevValue] = useState(value);
1436
+ const lastCommittedRef = useRef(value);
1437
+ if (value !== prevValue) {
1438
+ setPrevValue(value);
1439
+ setLiveValue(value);
1440
+ }
1441
+ useEffect(() => {
1442
+ lastCommittedRef.current = value;
1443
+ }, [value]);
1444
+ const commit = (next) => {
1445
+ if (next === lastCommittedRef.current) return;
1446
+ lastCommittedRef.current = next;
1447
+ onChange(next);
1448
+ };
1449
+ const debouncedCommit = useDebounce(() => commit(liveValue), {
1450
+ delay: COLOR_COMMIT_DELAY,
1451
+ autoInvoke: false
1452
+ });
1453
+ return /* @__PURE__ */ jsx(ColorPicker, {
1454
+ "aria-label": label,
1455
+ showText: true,
1456
+ value: liveValue,
1457
+ onChange: (next) => {
1458
+ setLiveValue(next);
1459
+ debouncedCommit();
1460
+ },
1461
+ onOpenChange: (open) => {
1462
+ if (!open) commit(liveValue);
1463
+ }
1464
+ });
1465
+ };
1466
+ //#endregion
1467
+ //#region src/components/ui-kit/date-value.ts
1468
+ const parseDateValue = (value) => {
1469
+ const match = /^(\d{4})-(\d{2})-(\d{2})(?:T(\d{2}):(\d{2}))?$/.exec(value.trim());
1470
+ if (!match) return;
1471
+ const [, year, month, day, hours = "0", minutes = "0"] = match;
1472
+ const date = new Date(Number(year), Number(month) - 1, Number(day), Number(hours), Number(minutes));
1473
+ return Number.isNaN(date.getTime()) ? void 0 : date;
1474
+ };
1475
+ const pad = (value) => String(value).padStart(2, "0");
1476
+ const formatDateValue = (date, withTime = false) => {
1477
+ const day = `${date.getFullYear()}-${pad(date.getMonth() + 1)}-${pad(date.getDate())}`;
1478
+ return withTime ? `${day}T${pad(date.getHours())}:${pad(date.getMinutes())}` : day;
1479
+ };
1480
+ //#endregion
1481
+ //#region src/components/ui-kit/ui-kit-field.tsx
1482
+ const RICHTEXT_TOOLBAR = [
1483
+ "bold",
1484
+ "italic",
1485
+ "underline",
1486
+ "bulletList",
1487
+ "orderedList",
1488
+ "link"
1489
+ ];
1490
+ const UiKitField = ({ binding }) => {
1491
+ const { value, rawValue, onChange } = binding;
1492
+ const { validationError, errorId, controlProps, labelledByProps, commitIfChanged, validateAndCommit } = useFieldState(binding);
1493
+ const kind = getFieldKind(binding);
1494
+ if (kind === "richtext") return /* @__PURE__ */ jsx(RichTextEditor, {
1495
+ ...labelledByProps,
1496
+ value: rawValue,
1497
+ toolbar: RICHTEXT_TOOLBAR,
1498
+ onChange: commitIfChanged
1499
+ });
1500
+ if (kind === "boolean") return /* @__PURE__ */ jsx(Checkbox, {
1501
+ ...controlProps,
1502
+ checked: value === true || value === "true",
1503
+ onChange: (checked) => {
1504
+ onChange(checked);
1505
+ }
1506
+ });
1507
+ if (kind === "select") return /* @__PURE__ */ jsx(Select, {
1508
+ ...labelledByProps,
1509
+ value: rawValue,
1510
+ options: binding.options ?? [],
1511
+ onChange: commitIfChanged
1512
+ });
1513
+ if (kind === "color") return /* @__PURE__ */ jsx(ColorPickerField, {
1514
+ value: rawValue,
1515
+ label: binding.label,
1516
+ onChange: commitIfChanged
1517
+ });
1518
+ if (kind === "time") return /* @__PURE__ */ jsxs("div", { children: [/* @__PURE__ */ jsx(TimePicker, {
1519
+ ...controlProps,
1520
+ value: rawValue || null,
1521
+ onChange: (time) => validateAndCommit(time ?? "")
1522
+ }), /* @__PURE__ */ jsx(FieldError, {
1523
+ id: errorId,
1524
+ message: validationError
1525
+ })] });
1526
+ const withTime = kind === "datetime";
1527
+ return /* @__PURE__ */ jsxs("div", { children: [/* @__PURE__ */ jsx(DatePicker, {
1528
+ ...controlProps,
1529
+ value: parseDateValue(rawValue),
1530
+ showTime: withTime,
1531
+ onChange: (date) => validateAndCommit(date ? formatDateValue(date, withTime) : "")
1532
+ }), /* @__PURE__ */ jsx(FieldError, {
1533
+ id: errorId,
1534
+ message: validationError
1535
+ })] });
1536
+ };
1537
+ //#endregion
1538
+ //#region src/components/ui-kit/ui-kit-fields.tsx
1539
+ const UI_KIT_KINDS = /* @__PURE__ */ new Set([
1540
+ "richtext",
1541
+ "boolean",
1542
+ "select",
1543
+ "color",
1544
+ "date",
1545
+ "datetime",
1546
+ "time"
1547
+ ]);
1548
+ const uiKitFields = (props) => UI_KIT_KINDS.has(getFieldKind(props.binding)) ? /* @__PURE__ */ jsx(UiKitField, { ...props }) : void 0;
1549
+ //#endregion
1550
+ export { createUiKitDocument, uiKitFields, uiKitModules, uiKitPaletteSections };
1551
+
1552
+ //# sourceMappingURL=index.js.map