foldkit 0.90.0 → 0.90.1
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/README.md +19 -10
- package/dist/devTools/overlay.d.ts.map +1 -1
- package/dist/devTools/overlay.js +150 -150
- package/dist/runtime/crashUI.js +30 -30
- package/dist/test/apps/bubbling.js +4 -4
- package/dist/test/apps/disabledButton.js +10 -10
- package/dist/test/apps/fileUpload.d.ts.map +1 -1
- package/dist/test/apps/fileUpload.js +13 -13
- package/dist/test/apps/interactions.d.ts.map +1 -1
- package/dist/test/apps/interactions.js +15 -15
- package/dist/test/apps/keypress.js +8 -8
- package/dist/test/apps/login.d.ts.map +1 -1
- package/dist/test/apps/login.js +32 -24
- package/dist/test/apps/logoutButton.d.ts.map +1 -1
- package/dist/test/apps/logoutButton.js +2 -2
- package/dist/test/apps/mountPanel.js +10 -10
- package/dist/test/apps/multiRole.js +3 -3
- package/dist/test/apps/pointer.d.ts.map +1 -1
- package/dist/test/apps/pointer.js +11 -11
- package/dist/test/apps/resumeUpload.d.ts.map +1 -1
- package/dist/test/apps/resumeUpload.js +8 -8
- package/dist/ui/animation/index.js +24 -24
- package/dist/ui/button/index.d.ts.map +1 -1
- package/dist/ui/button/index.js +6 -6
- package/dist/ui/calendar/index.d.ts.map +1 -1
- package/dist/ui/calendar/index.js +101 -99
- package/dist/ui/checkbox/index.d.ts.map +1 -1
- package/dist/ui/checkbox/index.js +15 -15
- package/dist/ui/combobox/shared.d.ts.map +1 -1
- package/dist/ui/combobox/shared.js +102 -90
- package/dist/ui/datePicker/index.js +4 -4
- package/dist/ui/dialog/index.d.ts.map +1 -1
- package/dist/ui/dialog/index.js +27 -27
- package/dist/ui/disclosure/index.d.ts.map +1 -1
- package/dist/ui/disclosure/index.js +24 -22
- package/dist/ui/dragAndDrop/index.d.ts.map +1 -1
- package/dist/ui/dragAndDrop/index.js +15 -15
- package/dist/ui/fieldset/index.js +6 -6
- package/dist/ui/fileDrop/index.d.ts +2 -2
- package/dist/ui/fileDrop/index.d.ts.map +1 -1
- package/dist/ui/fileDrop/index.js +16 -16
- package/dist/ui/input/index.d.ts.map +1 -1
- package/dist/ui/input/index.js +15 -13
- package/dist/ui/listbox/shared.d.ts.map +1 -1
- package/dist/ui/listbox/shared.js +85 -79
- package/dist/ui/menu/index.d.ts.map +1 -1
- package/dist/ui/menu/index.js +69 -67
- package/dist/ui/popover/index.d.ts.map +1 -1
- package/dist/ui/popover/index.js +41 -39
- package/dist/ui/radioGroup/index.d.ts.map +1 -1
- package/dist/ui/radioGroup/index.js +20 -20
- package/dist/ui/select/index.d.ts.map +1 -1
- package/dist/ui/select/index.js +13 -11
- package/dist/ui/slider/index.d.ts.map +1 -1
- package/dist/ui/slider/index.js +26 -26
- package/dist/ui/switch/index.d.ts.map +1 -1
- package/dist/ui/switch/index.js +14 -14
- package/dist/ui/tabs/index.d.ts.map +1 -1
- package/dist/ui/tabs/index.js +40 -36
- package/dist/ui/textarea/index.d.ts.map +1 -1
- package/dist/ui/textarea/index.js +15 -13
- package/dist/ui/toast/index.d.ts.map +1 -1
- package/dist/ui/toast/index.js +27 -27
- package/dist/ui/tooltip/index.d.ts.map +1 -1
- package/dist/ui/tooltip/index.js +23 -23
- package/dist/ui/virtualList/index.d.ts.map +1 -1
- package/dist/ui/virtualList/index.js +18 -15
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -92,26 +92,35 @@ const init: Runtime.ProgramInit<Model, Message> = () => [{ count: 0 }, []]
|
|
|
92
92
|
|
|
93
93
|
// VIEW
|
|
94
94
|
|
|
95
|
-
const
|
|
95
|
+
const h = html<Message>()
|
|
96
96
|
|
|
97
97
|
const view = (model: Model): Html =>
|
|
98
|
-
div(
|
|
98
|
+
h.div(
|
|
99
99
|
[
|
|
100
|
-
Class(
|
|
100
|
+
h.Class(
|
|
101
101
|
'min-h-screen bg-white flex flex-col items-center justify-center gap-6 p-6',
|
|
102
102
|
),
|
|
103
103
|
],
|
|
104
104
|
[
|
|
105
|
-
div(
|
|
106
|
-
[Class('text-6xl font-bold text-gray-800')],
|
|
105
|
+
h.div(
|
|
106
|
+
[h.Class('text-6xl font-bold text-gray-800')],
|
|
107
107
|
[model.count.toString()],
|
|
108
108
|
),
|
|
109
|
-
div(
|
|
110
|
-
[Class('flex flex-wrap justify-center gap-4')],
|
|
109
|
+
h.div(
|
|
110
|
+
[h.Class('flex flex-wrap justify-center gap-4')],
|
|
111
111
|
[
|
|
112
|
-
button(
|
|
113
|
-
|
|
114
|
-
|
|
112
|
+
h.button(
|
|
113
|
+
[h.OnClick(ClickedDecrement()), h.Class(buttonStyle)],
|
|
114
|
+
['-'],
|
|
115
|
+
),
|
|
116
|
+
h.button(
|
|
117
|
+
[h.OnClick(ClickedReset()), h.Class(buttonStyle)],
|
|
118
|
+
['Reset'],
|
|
119
|
+
),
|
|
120
|
+
h.button(
|
|
121
|
+
[h.OnClick(ClickedIncrement()), h.Class(buttonStyle)],
|
|
122
|
+
['+'],
|
|
123
|
+
),
|
|
115
124
|
],
|
|
116
125
|
),
|
|
117
126
|
],
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"overlay.d.ts","sourceRoot":"","sources":["../../src/devTools/overlay.ts"],"names":[],"mappings":"AACA,OAAO,EAEL,OAAO,EACP,MAAM,EAGN,OAAO,EAGP,MAAM,EAKN,MAAM,IAAI,CAAC,EAGX,eAAe,EAEhB,MAAM,QAAQ,CAAA;AAEf,OAAO,KAAK,OAAO,MAAM,qBAAqB,CAAA;AAa9C,OAAO,KAAK,EAAE,YAAY,EAAE,gBAAgB,EAAE,MAAM,uBAAuB,CAAA;AAO3E,OAAO,EACL,KAAK,aAAa,EAClB,KAAK,aAAa,EAElB,KAAK,WAAW,EAChB,KAAK,UAAU,EAChB,MAAM,YAAY,CAAA;;oFAiYJ,CAAC;;;;;;;;;;;;;AAtIhB,cAAM,YAAa,SAAQ,iBAE1B;CAAG;;AAEJ,cAAM,iBAAkB,SAAQ,sBAGC;CAAG;AAEpC,eAAO,MAAM,UAAU;;iBAGsB,CAAA;AAE7C,eAAO,MAAM,YAAY;;iBAGwB,CAAA;AAWjD,eAAO,MAAM,MAAM;;;;wBAUlB,CAAA;AAED,eAAO,MAAM,YAAY;;;;;;;;wBAIqB,CAAA;AAE9C,eAAO,MAAM,aAAa;;;;;;wBAYzB,CAAA;AAED,eAAO,MAAM,MAAM;;wBASlB,CAAA;AAED,eAAO,MAAM,KAAK;;wBASjB,CAAA;AAED,eAAO,MAAM,WAAW;;6BAYvB,CAAA;
|
|
1
|
+
{"version":3,"file":"overlay.d.ts","sourceRoot":"","sources":["../../src/devTools/overlay.ts"],"names":[],"mappings":"AACA,OAAO,EAEL,OAAO,EACP,MAAM,EAGN,OAAO,EAGP,MAAM,EAKN,MAAM,IAAI,CAAC,EAGX,eAAe,EAEhB,MAAM,QAAQ,CAAA;AAEf,OAAO,KAAK,OAAO,MAAM,qBAAqB,CAAA;AAa9C,OAAO,KAAK,EAAE,YAAY,EAAE,gBAAgB,EAAE,MAAM,uBAAuB,CAAA;AAO3E,OAAO,EACL,KAAK,aAAa,EAClB,KAAK,aAAa,EAElB,KAAK,WAAW,EAChB,KAAK,UAAU,EAChB,MAAM,YAAY,CAAA;;oFAiYJ,CAAC;;;;;;;;;;;;;AAtIhB,cAAM,YAAa,SAAQ,iBAE1B;CAAG;;AAEJ,cAAM,iBAAkB,SAAQ,sBAGC;CAAG;AAEpC,eAAO,MAAM,UAAU;;iBAGsB,CAAA;AAE7C,eAAO,MAAM,YAAY;;iBAGwB,CAAA;AAWjD,eAAO,MAAM,MAAM;;;;wBAUlB,CAAA;AAED,eAAO,MAAM,YAAY;;;;;;;;wBAIqB,CAAA;AAE9C,eAAO,MAAM,aAAa;;;;;;wBAYzB,CAAA;AAED,eAAO,MAAM,MAAM;;wBASlB,CAAA;AAED,eAAO,MAAM,KAAK;;wBASjB,CAAA;AAED,eAAO,MAAM,WAAW;;6BAYvB,CAAA;AA2/CD,eAAO,MAAM,aAAa,GACxB,OAAO,aAAa,EACpB,UAAU,gBAAgB,EAC1B,MAAM,YAAY,EAClB,aAAa,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,sCAoDhC,CAAA"}
|
package/dist/devTools/overlay.js
CHANGED
|
@@ -422,34 +422,34 @@ const PANEL_POSITION_CLASS = {
|
|
|
422
422
|
TopLeft: 'dt-panel-tl',
|
|
423
423
|
};
|
|
424
424
|
const makeView = (position, mode, maybeBanner) => {
|
|
425
|
-
const
|
|
425
|
+
const h = html();
|
|
426
426
|
const lazyTreeNode = createKeyedLazy();
|
|
427
427
|
const lazyMessageRow = createKeyedLazy();
|
|
428
428
|
const lazyTabContent = createKeyedLazy();
|
|
429
429
|
const lazyMessageList = createLazy();
|
|
430
430
|
// JSON TREE
|
|
431
|
-
const leafValueView = (value) => M.value(value).pipe(M.when(Predicate.isNull, () => span([Class('json-null italic')], ['null'])), M.when(Predicate.isUndefined, () => span([Class('json-null italic')], ['undefined'])), M.when(Predicate.isString, stringValue => span([Class('json-string')], [`"${stringValue}"`])), M.when(Predicate.isNumber, numberValue => span([Class('json-number')], [String(numberValue)])), M.when(Predicate.isBoolean, booleanValue => span([Class('json-boolean')], [String(booleanValue)])), M.orElse(unknownValue => span([Class('json-null')], [String(unknownValue)])));
|
|
432
|
-
const keyView = (key) => span([Class('json-key')], [`${key}:\u00a0`]);
|
|
431
|
+
const leafValueView = (value) => M.value(value).pipe(M.when(Predicate.isNull, () => h.span([h.Class('json-null italic')], ['null'])), M.when(Predicate.isUndefined, () => h.span([h.Class('json-null italic')], ['undefined'])), M.when(Predicate.isString, stringValue => h.span([h.Class('json-string')], [`"${stringValue}"`])), M.when(Predicate.isNumber, numberValue => h.span([h.Class('json-number')], [String(numberValue)])), M.when(Predicate.isBoolean, booleanValue => h.span([h.Class('json-boolean')], [String(booleanValue)])), M.orElse(unknownValue => h.span([h.Class('json-null')], [String(unknownValue)])));
|
|
432
|
+
const keyView = (key) => h.span([h.Class('json-key')], [`${key}:\u00a0`]);
|
|
433
433
|
const CHEVRON_RIGHT = 'M8.25 4.5l7.5 7.5-7.5 7.5';
|
|
434
434
|
const CHEVRON_DOWN = 'M19.5 8.25l-7.5 7.5-7.5-7.5';
|
|
435
|
-
const arrowView = (isExpanded) => svg([
|
|
436
|
-
AriaHidden(true),
|
|
437
|
-
Class('json-arrow shrink-0'),
|
|
438
|
-
Xmlns('http://www.w3.org/2000/svg'),
|
|
439
|
-
Fill('none'),
|
|
440
|
-
ViewBox('0 0 24 24'),
|
|
441
|
-
StrokeWidth('2'),
|
|
442
|
-
Stroke('currentColor'),
|
|
435
|
+
const arrowView = (isExpanded) => h.svg([
|
|
436
|
+
h.AriaHidden(true),
|
|
437
|
+
h.Class('json-arrow shrink-0'),
|
|
438
|
+
h.Xmlns('http://www.w3.org/2000/h.svg'),
|
|
439
|
+
h.Fill('none'),
|
|
440
|
+
h.ViewBox('0 0 24 24'),
|
|
441
|
+
h.StrokeWidth('2'),
|
|
442
|
+
h.Stroke('currentColor'),
|
|
443
443
|
], [
|
|
444
|
-
path([
|
|
445
|
-
StrokeLinecap('round'),
|
|
446
|
-
StrokeLinejoin('round'),
|
|
447
|
-
D(isExpanded ? CHEVRON_DOWN : CHEVRON_RIGHT),
|
|
444
|
+
h.path([
|
|
445
|
+
h.StrokeLinecap('round'),
|
|
446
|
+
h.StrokeLinejoin('round'),
|
|
447
|
+
h.D(isExpanded ? CHEVRON_DOWN : CHEVRON_RIGHT),
|
|
448
448
|
], []),
|
|
449
449
|
]);
|
|
450
|
-
const tagLabelView = (tag) => span([Class('json-tag')], [tag]);
|
|
451
|
-
const diffDotView = span([Class('diff-dot')], []);
|
|
452
|
-
const inlineDiffDotView = span([Class('diff-dot-inline')], []);
|
|
450
|
+
const tagLabelView = (tag) => h.span([h.Class('json-tag')], [tag]);
|
|
451
|
+
const diffDotView = h.span([h.Class('diff-dot')], []);
|
|
452
|
+
const inlineDiffDotView = h.span([h.Class('diff-dot-inline')], []);
|
|
453
453
|
const flattenTree = ({ value, treePath, depth, key, ...shared }) => {
|
|
454
454
|
const { rootPath, expandedPaths, changedPaths, affectedPaths, accumulator, indentRootChildren, } = shared;
|
|
455
455
|
const isRoot = treePath === rootPath;
|
|
@@ -492,12 +492,12 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
492
492
|
}
|
|
493
493
|
};
|
|
494
494
|
const flatNodeView = (value, treePath, depth, key, nodeIsExpandable, isExpanded, isChanged, isAffected, isRoot, tag) => {
|
|
495
|
-
const indent = Style({ paddingLeft: `${depth * TREE_INDENT_PX}px` });
|
|
495
|
+
const indent = h.Style({ paddingLeft: `${depth * TREE_INDENT_PX}px` });
|
|
496
496
|
const hasDiffDot = isChanged || isAffected;
|
|
497
497
|
if (!nodeIsExpandable) {
|
|
498
|
-
return div([
|
|
499
|
-
Key(treePath),
|
|
500
|
-
Class(clsx('tree-row flex items-center gap-px font-mono text-2xs', {
|
|
498
|
+
return h.div([
|
|
499
|
+
h.Key(treePath),
|
|
500
|
+
h.Class(clsx('tree-row flex items-center gap-px font-mono text-2xs', {
|
|
501
501
|
'diff-changed': isChanged,
|
|
502
502
|
})),
|
|
503
503
|
indent,
|
|
@@ -512,20 +512,20 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
512
512
|
? `(${value.length})`
|
|
513
513
|
: ''
|
|
514
514
|
: collapsedPreview(value);
|
|
515
|
-
return div([
|
|
516
|
-
Key(treePath),
|
|
517
|
-
Class(clsx('tree-row flex items-center gap-px font-mono text-2xs', {
|
|
515
|
+
return h.div([
|
|
516
|
+
h.Key(treePath),
|
|
517
|
+
h.Class(clsx('tree-row flex items-center gap-px font-mono text-2xs', {
|
|
518
518
|
'tree-row-expandable cursor-pointer': !isRoot,
|
|
519
519
|
'diff-changed': isChanged,
|
|
520
520
|
})),
|
|
521
521
|
indent,
|
|
522
|
-
...(isRoot ? [] : [OnClick(ToggledTreeNode({ path: treePath }))]),
|
|
522
|
+
...(isRoot ? [] : [h.OnClick(ToggledTreeNode({ path: treePath }))]),
|
|
523
523
|
], [
|
|
524
524
|
...(isRoot ? [] : [arrowView(isExpanded)]),
|
|
525
525
|
...(!isRoot && hasDiffDot ? [diffDotView] : []),
|
|
526
526
|
...(String_.isNonEmpty(key) ? [keyView(key)] : []),
|
|
527
527
|
...(String_.isNonEmpty(tag) ? [tagLabelView(tag)] : []),
|
|
528
|
-
span([Class('json-preview')], [preview]),
|
|
528
|
+
h.span([h.Class('json-preview')], [preview]),
|
|
529
529
|
]);
|
|
530
530
|
};
|
|
531
531
|
const renderFlatNode = (node) => lazyTreeNode(node.treePath, flatNodeView, [
|
|
@@ -554,8 +554,8 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
554
554
|
accumulator: nodes,
|
|
555
555
|
indentRootChildren,
|
|
556
556
|
});
|
|
557
|
-
return div([
|
|
558
|
-
Class('inspector-tree flex-1 overflow-auto min-h-0 min-w-0 overscroll-none'),
|
|
557
|
+
return h.div([
|
|
558
|
+
h.Class('inspector-tree flex-1 overflow-auto min-h-0 min-w-0 overscroll-none'),
|
|
559
559
|
], nodes.map(renderFlatNode));
|
|
560
560
|
};
|
|
561
561
|
const inspectedTimestamp = (model) => {
|
|
@@ -579,8 +579,8 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
579
579
|
: `+${remainingMs.toFixed(1)}ms`;
|
|
580
580
|
}), Option.getOrElse(() => ''));
|
|
581
581
|
};
|
|
582
|
-
const emptyInspectorView = div([
|
|
583
|
-
Class('flex-1 flex items-center justify-center text-dt-muted text-2xs font-mono min-w-0'),
|
|
582
|
+
const emptyInspectorView = h.div([
|
|
583
|
+
h.Class('flex-1 flex items-center justify-center text-dt-muted text-2xs font-mono min-w-0'),
|
|
584
584
|
], ['Click a message to inspect']);
|
|
585
585
|
const INSPECTOR_TABS = [
|
|
586
586
|
'Model',
|
|
@@ -588,8 +588,8 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
588
588
|
'Commands',
|
|
589
589
|
'Mounts',
|
|
590
590
|
];
|
|
591
|
-
const noMessageView = div([
|
|
592
|
-
Class('flex-1 flex items-center justify-center text-dt-muted text-2xs font-mono min-w-0'),
|
|
591
|
+
const noMessageView = h.div([
|
|
592
|
+
h.Class('flex-1 flex items-center justify-center text-dt-muted text-2xs font-mono min-w-0'),
|
|
593
593
|
], ['init — no Message']);
|
|
594
594
|
const modelTabContent = (inspectedModel, expandedPaths, changedPaths, affectedPaths) => treeView(inspectedModel, 'root', expandedPaths, changedPaths, affectedPaths, Option.none(), true);
|
|
595
595
|
const unwrapIfFiltered = (message, maybeSubmodelFilter) => {
|
|
@@ -619,11 +619,11 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
619
619
|
onNone: () => noMessageView,
|
|
620
620
|
onSome: rawMessage => {
|
|
621
621
|
const message = unwrapIfFiltered(rawMessage, maybeSubmodelFilter);
|
|
622
|
-
return div([Class('flex flex-col flex-1 min-h-0 min-w-0')], [
|
|
623
|
-
div([
|
|
624
|
-
Class('px-2 py-1 border-b text-2xs text-dt-muted font-mono shrink-0'),
|
|
622
|
+
return h.div([h.Class('flex flex-col flex-1 min-h-0 min-w-0')], [
|
|
623
|
+
h.div([
|
|
624
|
+
h.Class('px-2 py-1 border-b text-2xs text-dt-muted font-mono shrink-0'),
|
|
625
625
|
], [timestamp]),
|
|
626
|
-
div([Class('flex flex-col flex-1 min-h-0 min-w-0 pt-1 pl-1')], [
|
|
626
|
+
h.div([h.Class('flex flex-col flex-1 min-h-0 min-w-0 pt-1 pl-1')], [
|
|
627
627
|
treeView(message, 'root', expandedPaths, HashSet.empty(), HashSet.empty(), Option.none(), false),
|
|
628
628
|
]),
|
|
629
629
|
]);
|
|
@@ -661,14 +661,14 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
661
661
|
return nodes;
|
|
662
662
|
};
|
|
663
663
|
const commandsTabContent = (commands, expandedPaths) => Array_.match(commands, {
|
|
664
|
-
onEmpty: () => div([
|
|
665
|
-
Class('flex-1 flex items-center justify-center text-dt-muted text-2xs font-mono min-w-0'),
|
|
664
|
+
onEmpty: () => h.div([
|
|
665
|
+
h.Class('flex-1 flex items-center justify-center text-dt-muted text-2xs font-mono min-w-0'),
|
|
666
666
|
], ['No Commands returned']),
|
|
667
|
-
onNonEmpty: commandList => div([
|
|
668
|
-
Class('flex flex-col flex-1 min-h-0 min-w-0 overflow-auto overscroll-none'),
|
|
669
|
-
], Array_.map(commandList, (command, index) => div([Class('flex items-start px-2 py-1 border-b gap-1.5')], [
|
|
670
|
-
span([Class(indexClass)], [String(index + 1)]),
|
|
671
|
-
div([Class('flex flex-col flex-1 min-w-0')], Array_.map(flattenCommand(command, index, expandedPaths), renderFlatNode)),
|
|
667
|
+
onNonEmpty: commandList => h.div([
|
|
668
|
+
h.Class('flex flex-col flex-1 min-h-0 min-w-0 overflow-auto overscroll-none'),
|
|
669
|
+
], Array_.map(commandList, (command, index) => h.div([h.Class('flex items-start px-2 py-1 border-b gap-1.5')], [
|
|
670
|
+
h.span([h.Class(indexClass)], [String(index + 1)]),
|
|
671
|
+
h.div([h.Class('flex flex-col flex-1 min-w-0')], Array_.map(flattenCommand(command, index, expandedPaths), renderFlatNode)),
|
|
672
672
|
]))),
|
|
673
673
|
});
|
|
674
674
|
const selectedMountActivity = (model) => {
|
|
@@ -707,25 +707,25 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
707
707
|
});
|
|
708
708
|
return nodes;
|
|
709
709
|
};
|
|
710
|
-
const mountListSection = (label, mounts, expandedPaths) => div([Class('flex flex-col shrink-0')], [
|
|
711
|
-
div([
|
|
712
|
-
Class('px-2 py-1 border-b text-2xs text-dt-muted font-mono shrink-0'),
|
|
710
|
+
const mountListSection = (label, mounts, expandedPaths) => h.div([h.Class('flex flex-col shrink-0')], [
|
|
711
|
+
h.div([
|
|
712
|
+
h.Class('px-2 py-1 border-b text-2xs text-dt-muted font-mono shrink-0'),
|
|
713
713
|
], [label]),
|
|
714
|
-
...Array_.map(mounts, (mount, index) => div([Class('flex items-start px-2 py-1 border-b gap-1.5')], [
|
|
715
|
-
span([Class(indexClass)], [String(index + 1)]),
|
|
716
|
-
div([Class('flex flex-col flex-1 min-w-0')], Array_.map(flattenMount(mount, label, index, expandedPaths), renderFlatNode)),
|
|
714
|
+
...Array_.map(mounts, (mount, index) => h.div([h.Class('flex items-start px-2 py-1 border-b gap-1.5')], [
|
|
715
|
+
h.span([h.Class(indexClass)], [String(index + 1)]),
|
|
716
|
+
h.div([h.Class('flex flex-col flex-1 min-w-0')], Array_.map(flattenMount(mount, label, index, expandedPaths), renderFlatNode)),
|
|
717
717
|
])),
|
|
718
718
|
]);
|
|
719
719
|
const mountsTabContent = (starts, ends, expandedPaths) => {
|
|
720
720
|
const hasAny = Array_.isReadonlyArrayNonEmpty(starts) ||
|
|
721
721
|
Array_.isReadonlyArrayNonEmpty(ends);
|
|
722
722
|
if (!hasAny) {
|
|
723
|
-
return div([
|
|
724
|
-
Class('flex-1 flex items-center justify-center text-dt-muted text-2xs font-mono min-w-0'),
|
|
723
|
+
return h.div([
|
|
724
|
+
h.Class('flex-1 flex items-center justify-center text-dt-muted text-2xs font-mono min-w-0'),
|
|
725
725
|
], ['No Mounts during this render']);
|
|
726
726
|
}
|
|
727
|
-
return div([
|
|
728
|
-
Class('flex flex-col flex-1 min-h-0 min-w-0 overflow-auto overscroll-none'),
|
|
727
|
+
return h.div([
|
|
728
|
+
h.Class('flex flex-col flex-1 min-h-0 min-w-0 overflow-auto overscroll-none'),
|
|
729
729
|
], [
|
|
730
730
|
...(Array_.isReadonlyArrayNonEmpty(starts)
|
|
731
731
|
? [mountListSection('Started', starts, expandedPaths)]
|
|
@@ -756,8 +756,8 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
756
756
|
model.expandedPaths,
|
|
757
757
|
]);
|
|
758
758
|
}), M.exhaustive);
|
|
759
|
-
const inspectorPaneView = (model) => div([
|
|
760
|
-
Class('flex flex-col border-l min-w-0 min-h-0 flex-1 dt-inspector-pane'),
|
|
759
|
+
const inspectorPaneView = (model) => h.div([
|
|
760
|
+
h.Class('flex flex-col border-l min-w-0 min-h-0 flex-1 dt-inspector-pane'),
|
|
761
761
|
], [
|
|
762
762
|
Tabs.view({
|
|
763
763
|
model: model.inspectorTabs,
|
|
@@ -765,14 +765,14 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
765
765
|
tabs: INSPECTOR_TABS,
|
|
766
766
|
tabListAriaLabel: 'Inspector tabs',
|
|
767
767
|
persistPanels: true,
|
|
768
|
-
attributes: [Class('flex flex-col flex-1 min-h-0')],
|
|
769
|
-
tabListAttributes: [Class('flex border-b shrink-0')],
|
|
768
|
+
attributes: [h.Class('flex flex-col flex-1 min-h-0')],
|
|
769
|
+
tabListAttributes: [h.Class('flex border-b shrink-0')],
|
|
770
770
|
tabToConfig: (tab, { isActive }) => ({
|
|
771
771
|
buttonAttributes: [
|
|
772
|
-
Class(clsx('dt-tab-button cursor-pointer text-base font-mono px-3 py-1', isActive ? 'text-dt dt-tab-active' : 'text-dt-muted')),
|
|
772
|
+
h.Class(clsx('dt-tab-h.button cursor-pointer text-base font-mono px-3 py-1', isActive ? 'text-dt dt-tab-active' : 'text-dt-muted')),
|
|
773
773
|
],
|
|
774
|
-
buttonContent: span([], [tab]),
|
|
775
|
-
panelAttributes: [Class('flex flex-col flex-1 min-h-0 min-w-0')],
|
|
774
|
+
buttonContent: h.span([], [tab]),
|
|
775
|
+
panelAttributes: [h.Class('flex flex-col flex-1 min-h-0 min-w-0')],
|
|
776
776
|
panelContent: Option.match(model.maybeInspectedModel, {
|
|
777
777
|
onNone: () => emptyInspectorView,
|
|
778
778
|
onSome: inspectedModel => inspectorTabContent(model, tab, inspectedModel),
|
|
@@ -781,47 +781,47 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
781
781
|
}),
|
|
782
782
|
]);
|
|
783
783
|
// MESSAGE LIST
|
|
784
|
-
const badgeView = (model) => button([
|
|
785
|
-
Class(clsx('fixed bg-dt-bg text-dt cursor-pointer flex flex-col items-center justify-center font-mono outline-none dt-badge', BADGE_POSITION_CLASS[position], model.isPaused ? 'dt-badge-paused' : 'dt-badge-accent')),
|
|
786
|
-
Style({ width: '22px', height: '56px', fontSize: '10px' }),
|
|
787
|
-
OnClick(ClickedToggle()),
|
|
784
|
+
const badgeView = (model) => h.button([
|
|
785
|
+
h.Class(clsx('fixed bg-dt-bg text-dt cursor-pointer flex flex-col items-center justify-center font-mono outline-none dt-badge', BADGE_POSITION_CLASS[position], model.isPaused ? 'dt-badge-paused' : 'dt-badge-accent')),
|
|
786
|
+
h.Style({ width: '22px', height: '56px', fontSize: '10px' }),
|
|
787
|
+
h.OnClick(ClickedToggle()),
|
|
788
788
|
], [
|
|
789
789
|
model.isOpen
|
|
790
|
-
? svg([
|
|
791
|
-
AriaHidden(true),
|
|
792
|
-
Xmlns('http://www.w3.org/2000/svg'),
|
|
793
|
-
Fill('none'),
|
|
794
|
-
ViewBox('0 0 24 24'),
|
|
795
|
-
StrokeWidth('1.5'),
|
|
796
|
-
Stroke('currentColor'),
|
|
797
|
-
Style({ width: '12px', height: '12px' }),
|
|
790
|
+
? h.svg([
|
|
791
|
+
h.AriaHidden(true),
|
|
792
|
+
h.Xmlns('http://www.w3.org/2000/h.svg'),
|
|
793
|
+
h.Fill('none'),
|
|
794
|
+
h.ViewBox('0 0 24 24'),
|
|
795
|
+
h.StrokeWidth('1.5'),
|
|
796
|
+
h.Stroke('currentColor'),
|
|
797
|
+
h.Style({ width: '12px', height: '12px' }),
|
|
798
798
|
], [
|
|
799
|
-
path([
|
|
800
|
-
StrokeLinecap('round'),
|
|
801
|
-
StrokeLinejoin('round'),
|
|
802
|
-
D('M6 18L18 6M6 6l12 12'),
|
|
799
|
+
h.path([
|
|
800
|
+
h.StrokeLinecap('round'),
|
|
801
|
+
h.StrokeLinejoin('round'),
|
|
802
|
+
h.D('M6 18L18 6M6 6l12 12'),
|
|
803
803
|
], []),
|
|
804
804
|
])
|
|
805
|
-
: div([
|
|
806
|
-
Class(clsx('flex flex-col items-center gap-0.5 font-semibold tracking-wider leading-none', model.isPaused ? 'text-dt-bg' : 'text-dt-muted')),
|
|
807
|
-
], [span([], ['D']), span([], ['E']), span([], ['V'])]),
|
|
805
|
+
: h.div([
|
|
806
|
+
h.Class(clsx('flex flex-col items-center gap-0.5 font-semibold tracking-wider leading-none', model.isPaused ? 'text-dt-bg' : 'text-dt-muted')),
|
|
807
|
+
], [h.span([], ['D']), h.span([], ['E']), h.span([], ['V'])]),
|
|
808
808
|
]);
|
|
809
809
|
const headerClass = 'flex items-center justify-between px-3 py-1.5 border-b shrink-0';
|
|
810
|
-
const actionButtonClass = 'dt-resume-button bg-transparent border-none text-dt-live cursor-pointer text-base font-mono font-medium';
|
|
810
|
+
const actionButtonClass = 'dt-resume-h.button bg-transparent border-none text-dt-live cursor-pointer text-base font-mono font-medium';
|
|
811
811
|
const statusClass = 'text-base font-mono';
|
|
812
|
-
const clearHistoryButton = button([Class(headerButtonClass), OnClick(ClickedClear())], ['Clear history']);
|
|
812
|
+
const clearHistoryButton = h.button([h.Class(headerButtonClass), h.OnClick(ClickedClear())], ['Clear history']);
|
|
813
813
|
const submodelLabel = (tag) => pipe(tag, String_.replace(/^Got/, ''), String_.replace(/Message$/, ''));
|
|
814
814
|
const CHECK_ICON = 'M4.5 12.75l6 6 9-13.5';
|
|
815
|
-
const checkIconView = svg([
|
|
816
|
-
AriaHidden(true),
|
|
817
|
-
Class('dt-filter-check shrink-0'),
|
|
818
|
-
Xmlns('http://www.w3.org/2000/svg'),
|
|
819
|
-
Fill('none'),
|
|
820
|
-
ViewBox('0 0 24 24'),
|
|
821
|
-
StrokeWidth('2'),
|
|
822
|
-
Stroke('currentColor'),
|
|
815
|
+
const checkIconView = h.svg([
|
|
816
|
+
h.AriaHidden(true),
|
|
817
|
+
h.Class('dt-filter-check shrink-0'),
|
|
818
|
+
h.Xmlns('http://www.w3.org/2000/h.svg'),
|
|
819
|
+
h.Fill('none'),
|
|
820
|
+
h.ViewBox('0 0 24 24'),
|
|
821
|
+
h.StrokeWidth('2'),
|
|
822
|
+
h.Stroke('currentColor'),
|
|
823
823
|
], [
|
|
824
|
-
path([D(CHECK_ICON), StrokeLinecap('round'), StrokeLinejoin('round')], []),
|
|
824
|
+
h.path([h.D(CHECK_ICON), h.StrokeLinecap('round'), h.StrokeLinejoin('round')], []),
|
|
825
825
|
]);
|
|
826
826
|
const filterItemLabel = (item) => String_.isNonEmpty(item) ? submodelLabel(item) : 'All Messages';
|
|
827
827
|
const submodelFilterView = (model) => {
|
|
@@ -836,27 +836,27 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
836
836
|
items: [ALL_MESSAGES_VALUE, ...model.submodelTags],
|
|
837
837
|
itemToConfig: item => ({
|
|
838
838
|
className: 'dt-filter-item',
|
|
839
|
-
content: div([Class('flex items-center gap-2')], [checkIconView, span([], [filterItemLabel(item)])]),
|
|
839
|
+
content: h.div([h.Class('flex items-center gap-2')], [checkIconView, h.span([], [filterItemLabel(item)])]),
|
|
840
840
|
}),
|
|
841
|
-
buttonContent: span([Class('flex flex-1 items-center justify-between')], [
|
|
842
|
-
span([], [buttonLabel]),
|
|
843
|
-
svg([
|
|
844
|
-
AriaHidden(true),
|
|
845
|
-
Class('json-arrow shrink-0'),
|
|
846
|
-
Xmlns('http://www.w3.org/2000/svg'),
|
|
847
|
-
Fill('none'),
|
|
848
|
-
ViewBox('0 0 24 24'),
|
|
849
|
-
StrokeWidth('2'),
|
|
850
|
-
Stroke('currentColor'),
|
|
841
|
+
buttonContent: h.span([h.Class('flex flex-1 items-center justify-between')], [
|
|
842
|
+
h.span([], [buttonLabel]),
|
|
843
|
+
h.svg([
|
|
844
|
+
h.AriaHidden(true),
|
|
845
|
+
h.Class('json-arrow shrink-0'),
|
|
846
|
+
h.Xmlns('http://www.w3.org/2000/h.svg'),
|
|
847
|
+
h.Fill('none'),
|
|
848
|
+
h.ViewBox('0 0 24 24'),
|
|
849
|
+
h.StrokeWidth('2'),
|
|
850
|
+
h.Stroke('currentColor'),
|
|
851
851
|
], [
|
|
852
|
-
path([
|
|
853
|
-
D(CHEVRON_DOWN),
|
|
854
|
-
StrokeLinecap('round'),
|
|
855
|
-
StrokeLinejoin('round'),
|
|
852
|
+
h.path([
|
|
853
|
+
h.D(CHEVRON_DOWN),
|
|
854
|
+
h.StrokeLinecap('round'),
|
|
855
|
+
h.StrokeLinejoin('round'),
|
|
856
856
|
], []),
|
|
857
857
|
]),
|
|
858
858
|
]),
|
|
859
|
-
buttonClassName: 'dt-filter-button',
|
|
859
|
+
buttonClassName: 'dt-filter-h.button',
|
|
860
860
|
itemsClassName: 'dt-filter-items',
|
|
861
861
|
className: 'dt-filter-wrapper',
|
|
862
862
|
backdropClassName: 'dt-filter-backdrop',
|
|
@@ -865,60 +865,60 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
865
865
|
const headerView = (model) => {
|
|
866
866
|
const { status, maybeAction } = M.value(mode).pipe(M.withReturnType(), M.when('TimeTravel', () => model.isPaused
|
|
867
867
|
? {
|
|
868
|
-
status: span([Class(`${statusClass} text-dt-paused`)], [
|
|
868
|
+
status: h.span([h.Class(`${statusClass} text-dt-paused`)], [
|
|
869
869
|
model.pausedAtIndex === INIT_INDEX
|
|
870
870
|
? 'Paused (init)'
|
|
871
871
|
: `Paused (${model.pausedAtIndex + 1})`,
|
|
872
872
|
]),
|
|
873
|
-
maybeAction: Option.some(button([Class(actionButtonClass), OnClick(ClickedResume())], ['Resume →'])),
|
|
873
|
+
maybeAction: Option.some(h.button([h.Class(actionButtonClass), h.OnClick(ClickedResume())], ['Resume →'])),
|
|
874
874
|
}
|
|
875
875
|
: {
|
|
876
|
-
status: span([Class(`${statusClass} text-dt-live font-medium`)], ['Live']),
|
|
876
|
+
status: h.span([h.Class(`${statusClass} text-dt-live font-medium`)], ['Live']),
|
|
877
877
|
maybeAction: Option.none(),
|
|
878
878
|
}), M.when('Inspect', () => ({
|
|
879
|
-
status: span([Class(`${statusClass} text-dt-accent`)], [
|
|
879
|
+
status: h.span([h.Class(`${statusClass} text-dt-accent`)], [
|
|
880
880
|
model.selectedIndex === INIT_INDEX
|
|
881
881
|
? 'Inspecting (init)'
|
|
882
882
|
: `Inspecting (${model.selectedIndex + 1})`,
|
|
883
883
|
]),
|
|
884
|
-
maybeAction: OptionExt.when(!model.isFollowingLatest, button([Class(actionButtonClass), OnClick(ClickedFollowLatest())], ['Follow Latest →'])),
|
|
884
|
+
maybeAction: OptionExt.when(!model.isFollowingLatest, h.button([h.Class(actionButtonClass), h.OnClick(ClickedFollowLatest())], ['Follow Latest →'])),
|
|
885
885
|
})), M.exhaustive);
|
|
886
|
-
return header([Class(headerClass)], [status, ...Option.toArray(maybeAction), clearHistoryButton]);
|
|
886
|
+
return h.header([h.Class(headerClass)], [status, ...Option.toArray(maybeAction), clearHistoryButton]);
|
|
887
887
|
};
|
|
888
|
-
const initRowView = (isSelected, isPausedHere) => keyed('li')('init', [
|
|
889
|
-
Class(clsx(ROW_BASE, { selected: isSelected })),
|
|
890
|
-
OnClick(ClickedRow({ index: INIT_INDEX })),
|
|
888
|
+
const initRowView = (isSelected, isPausedHere) => h.keyed('li')('init', [
|
|
889
|
+
h.Class(clsx(ROW_BASE, { selected: isSelected })),
|
|
890
|
+
h.OnClick(ClickedRow({ index: INIT_INDEX })),
|
|
891
891
|
], [
|
|
892
|
-
...OptionExt.when(mode === 'TimeTravel', span([Class('pause-column')], isPausedHere ? [pauseIconView] : [])).pipe(Option.toArray),
|
|
893
|
-
span([Class('dot-column')], []),
|
|
894
|
-
span([Class(indexClass)], []),
|
|
895
|
-
span([Class('text-base text-dt-muted font-mono')], ['init']),
|
|
892
|
+
...OptionExt.when(mode === 'TimeTravel', h.span([h.Class('pause-column')], isPausedHere ? [pauseIconView] : [])).pipe(Option.toArray),
|
|
893
|
+
h.span([h.Class('dot-column')], []),
|
|
894
|
+
h.span([h.Class(indexClass)], []),
|
|
895
|
+
h.span([h.Class('text-base text-dt-muted font-mono')], ['init']),
|
|
896
896
|
]);
|
|
897
|
-
const pauseIconView = svg([
|
|
898
|
-
AriaHidden(true),
|
|
899
|
-
Class('dt-pause-icon'),
|
|
900
|
-
Xmlns('http://www.w3.org/2000/svg'),
|
|
901
|
-
Fill('none'),
|
|
902
|
-
ViewBox('0 0 24 24'),
|
|
903
|
-
StrokeWidth('2.5'),
|
|
904
|
-
Stroke('currentColor'),
|
|
897
|
+
const pauseIconView = h.svg([
|
|
898
|
+
h.AriaHidden(true),
|
|
899
|
+
h.Class('dt-pause-icon'),
|
|
900
|
+
h.Xmlns('http://www.w3.org/2000/h.svg'),
|
|
901
|
+
h.Fill('none'),
|
|
902
|
+
h.ViewBox('0 0 24 24'),
|
|
903
|
+
h.StrokeWidth('2.5'),
|
|
904
|
+
h.Stroke('currentColor'),
|
|
905
905
|
], [
|
|
906
|
-
path([
|
|
907
|
-
StrokeLinecap('round'),
|
|
908
|
-
StrokeLinejoin('round'),
|
|
909
|
-
D('M5.75 3v18M18.25 3v18'),
|
|
906
|
+
h.path([
|
|
907
|
+
h.StrokeLinecap('round'),
|
|
908
|
+
h.StrokeLinejoin('round'),
|
|
909
|
+
h.D('M5.75 3v18M18.25 3v18'),
|
|
910
910
|
], []),
|
|
911
911
|
]);
|
|
912
|
-
const messageRowView = (tag, absoluteIndex, isSelected, isPausedHere, timeDelta, isModelChanged) => keyed('li')(String(absoluteIndex), [
|
|
913
|
-
Class(clsx(ROW_BASE, { selected: isSelected })),
|
|
914
|
-
OnClick(ClickedRow({ index: absoluteIndex })),
|
|
912
|
+
const messageRowView = (tag, absoluteIndex, isSelected, isPausedHere, timeDelta, isModelChanged) => h.keyed('li')(String(absoluteIndex), [
|
|
913
|
+
h.Class(clsx(ROW_BASE, { selected: isSelected })),
|
|
914
|
+
h.OnClick(ClickedRow({ index: absoluteIndex })),
|
|
915
915
|
], [
|
|
916
|
-
...OptionExt.when(mode === 'TimeTravel', span([Class('pause-column')], isPausedHere ? [pauseIconView] : [])).pipe(Option.toArray),
|
|
917
|
-
span([Class('dot-column')], isModelChanged ? [inlineDiffDotView] : []),
|
|
918
|
-
span([Class(indexClass)], [String(absoluteIndex + 1)]),
|
|
919
|
-
span([Class('text-base text-dt font-mono flex-1 truncate')], [tag]),
|
|
920
|
-
span([
|
|
921
|
-
Class('text-2xs text-dt-muted font-mono shrink-0 text-right min-w-5'),
|
|
916
|
+
...OptionExt.when(mode === 'TimeTravel', h.span([h.Class('pause-column')], isPausedHere ? [pauseIconView] : [])).pipe(Option.toArray),
|
|
917
|
+
h.span([h.Class('dot-column')], isModelChanged ? [inlineDiffDotView] : []),
|
|
918
|
+
h.span([h.Class(indexClass)], [String(absoluteIndex + 1)]),
|
|
919
|
+
h.span([h.Class('text-base text-dt font-mono flex-1 truncate')], [tag]),
|
|
920
|
+
h.span([
|
|
921
|
+
h.Class('text-2xs text-dt-muted font-mono shrink-0 text-right min-w-5'),
|
|
922
922
|
], [formatTimeDelta(timeDelta)]),
|
|
923
923
|
]);
|
|
924
924
|
const messageListBody = (entries, startIndex, selectedIndex, isPaused, pausedAtIndex, maybeFilterTag) => {
|
|
@@ -949,7 +949,7 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
949
949
|
entry.isModelChanged,
|
|
950
950
|
]);
|
|
951
951
|
}), Array_.reverse);
|
|
952
|
-
return ul([Class('message-list flex-1 overflow-y-auto min-h-0 overscroll-none')], isFiltered
|
|
952
|
+
return h.ul([h.Class('message-list flex-1 overflow-y-auto min-h-0 overscroll-none')], isFiltered
|
|
953
953
|
? messageRows
|
|
954
954
|
: [
|
|
955
955
|
...messageRows,
|
|
@@ -972,15 +972,15 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
972
972
|
]);
|
|
973
973
|
};
|
|
974
974
|
// PANEL
|
|
975
|
-
const panelView = (model) => keyed('div')('dt-panel', [
|
|
976
|
-
Class(clsx('fixed dt-panel dt-panel-wide bg-dt-bg border rounded-lg flex flex-col overflow-hidden font-mono text-dt', PANEL_POSITION_CLASS[position])),
|
|
975
|
+
const panelView = (model) => h.keyed('div')('dt-panel', [
|
|
976
|
+
h.Class(clsx('fixed dt-panel dt-panel-wide bg-dt-bg border rounded-lg flex flex-col overflow-hidden font-mono text-dt', PANEL_POSITION_CLASS[position])),
|
|
977
977
|
], [
|
|
978
|
-
...Option.map(maybeBanner, banner => div([
|
|
979
|
-
Class('px-3 py-2 border-b text-sm text-dt-muted font-mono shrink-0 leading-snug'),
|
|
978
|
+
...Option.map(maybeBanner, banner => h.div([
|
|
979
|
+
h.Class('px-3 py-2 border-b text-sm text-dt-muted font-mono shrink-0 leading-snug'),
|
|
980
980
|
], [banner])).pipe(Option.toArray),
|
|
981
981
|
headerView(model),
|
|
982
|
-
div([Class('flex flex-1 min-h-0 dt-content')], [
|
|
983
|
-
div([Class('flex flex-col min-h-0 dt-message-pane')], [
|
|
982
|
+
h.div([h.Class('flex flex-1 min-h-0 dt-content')], [
|
|
983
|
+
h.div([h.Class('flex flex-col min-h-0 dt-message-pane')], [
|
|
984
984
|
...Array_.match(model.submodelTags, {
|
|
985
985
|
onEmpty: () => [],
|
|
986
986
|
onNonEmpty: () => [submodelFilterView(model)],
|
|
@@ -990,10 +990,10 @@ const makeView = (position, mode, maybeBanner) => {
|
|
|
990
990
|
inspectorPaneView(model),
|
|
991
991
|
]),
|
|
992
992
|
]);
|
|
993
|
-
const interactionBlocker = div([Class('dt-interaction-blocker')], []);
|
|
993
|
+
const interactionBlocker = h.div([h.Class('dt-interaction-blocker')], []);
|
|
994
994
|
return (model) => ({
|
|
995
995
|
title: 'Foldkit DevTools',
|
|
996
|
-
body: div([], [
|
|
996
|
+
body: h.div([], [
|
|
997
997
|
...OptionExt.when(model.isPaused && mode === 'TimeTravel', interactionBlocker).pipe(Option.toArray),
|
|
998
998
|
...OptionExt.when(model.isOpen, panelView(model)).pipe(Option.toArray),
|
|
999
999
|
badgeView(model),
|