uidex 0.5.2 → 0.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +3 -3
- package/dist/cli/cli.cjs +1542 -1227
- package/dist/cli/cli.cjs.map +1 -1
- package/dist/cloud/index.cjs +385 -175
- package/dist/cloud/index.cjs.map +1 -1
- package/dist/cloud/index.d.cts +192 -4
- package/dist/cloud/index.d.ts +192 -4
- package/dist/cloud/index.js +377 -177
- package/dist/cloud/index.js.map +1 -1
- package/dist/headless/index.cjs +116 -251
- package/dist/headless/index.cjs.map +1 -1
- package/dist/headless/index.d.cts +6 -11
- package/dist/headless/index.d.ts +6 -11
- package/dist/headless/index.js +116 -253
- package/dist/headless/index.js.map +1 -1
- package/dist/index.cjs +776 -1055
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +152 -160
- package/dist/index.d.ts +152 -160
- package/dist/index.js +792 -1066
- package/dist/index.js.map +1 -1
- package/dist/react/index.cjs +801 -1019
- package/dist/react/index.cjs.map +1 -1
- package/dist/react/index.d.cts +102 -86
- package/dist/react/index.d.ts +102 -86
- package/dist/react/index.js +821 -1038
- package/dist/react/index.js.map +1 -1
- package/dist/scan/index.cjs +1550 -1220
- package/dist/scan/index.cjs.map +1 -1
- package/dist/scan/index.d.cts +210 -12
- package/dist/scan/index.d.ts +210 -12
- package/dist/scan/index.js +1547 -1219
- package/dist/scan/index.js.map +1 -1
- package/package.json +22 -21
- package/templates/claude/SKILL.md +71 -0
- package/templates/claude/references/audit.md +43 -0
- package/templates/claude/{rules.md → references/conventions.md} +25 -28
- package/templates/claude/audit.md +0 -43
- /package/templates/claude/{api.md → references/api.md} +0 -0
package/dist/react/index.js
CHANGED
|
@@ -74,6 +74,7 @@ function freezeEntity(entity, flows) {
|
|
|
74
74
|
function createRegistry() {
|
|
75
75
|
const store = emptyStore();
|
|
76
76
|
let flowsCache = null;
|
|
77
|
+
const patternCache = /* @__PURE__ */ new Map();
|
|
77
78
|
const getFlows = () => {
|
|
78
79
|
if (flowsCache === null) flowsCache = Array.from(store.flow.values());
|
|
79
80
|
return flowsCache;
|
|
@@ -83,6 +84,7 @@ function createRegistry() {
|
|
|
83
84
|
const key = entityKey(entity);
|
|
84
85
|
store[entity.kind].set(key, entity);
|
|
85
86
|
flowsCache = null;
|
|
87
|
+
patternCache.delete(entity.kind);
|
|
86
88
|
};
|
|
87
89
|
const get = (kind, id) => {
|
|
88
90
|
assertEntityKind(kind);
|
|
@@ -90,6 +92,51 @@ function createRegistry() {
|
|
|
90
92
|
if (raw === void 0) return void 0;
|
|
91
93
|
return freezeEntity(raw, getFlows());
|
|
92
94
|
};
|
|
95
|
+
const getPatternsForKind = (kind) => {
|
|
96
|
+
const cached = patternCache.get(kind);
|
|
97
|
+
if (cached !== void 0) return cached;
|
|
98
|
+
const patterns = [];
|
|
99
|
+
for (const [key, entity] of store[kind]) {
|
|
100
|
+
if (key.includes("*")) {
|
|
101
|
+
const segments = key.split("*");
|
|
102
|
+
patterns.push({
|
|
103
|
+
segments,
|
|
104
|
+
staticLength: segments.reduce((n, s) => n + s.length, 0),
|
|
105
|
+
entity
|
|
106
|
+
});
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
patternCache.set(
|
|
110
|
+
kind,
|
|
111
|
+
patterns
|
|
112
|
+
);
|
|
113
|
+
return patterns;
|
|
114
|
+
};
|
|
115
|
+
const matchesSegments = (segments, id) => {
|
|
116
|
+
const first = segments[0];
|
|
117
|
+
const last = segments[segments.length - 1];
|
|
118
|
+
if (!id.startsWith(first)) return false;
|
|
119
|
+
let pos = first.length;
|
|
120
|
+
for (let i = 1; i < segments.length - 1; i++) {
|
|
121
|
+
const idx = id.indexOf(segments[i], pos);
|
|
122
|
+
if (idx === -1) return false;
|
|
123
|
+
pos = idx + segments[i].length;
|
|
124
|
+
}
|
|
125
|
+
return id.endsWith(last) && id.length - last.length >= pos;
|
|
126
|
+
};
|
|
127
|
+
const matchPattern = (kind, id) => {
|
|
128
|
+
assertEntityKind(kind);
|
|
129
|
+
const patterns = getPatternsForKind(kind);
|
|
130
|
+
if (patterns.length === 0) return void 0;
|
|
131
|
+
let best;
|
|
132
|
+
for (const entry of patterns) {
|
|
133
|
+
if (matchesSegments(entry.segments, id) && (best === void 0 || entry.staticLength > best.staticLength)) {
|
|
134
|
+
best = entry;
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
if (best === void 0) return void 0;
|
|
138
|
+
return freezeEntity(best.entity, getFlows());
|
|
139
|
+
};
|
|
93
140
|
const list = (kind) => {
|
|
94
141
|
assertEntityKind(kind);
|
|
95
142
|
const flows = getFlows();
|
|
@@ -140,6 +187,7 @@ function createRegistry() {
|
|
|
140
187
|
return {
|
|
141
188
|
add,
|
|
142
189
|
get,
|
|
190
|
+
matchPattern,
|
|
143
191
|
list,
|
|
144
192
|
query,
|
|
145
193
|
byScope,
|
|
@@ -393,7 +441,7 @@ function createNetworkCapture(options = {}) {
|
|
|
393
441
|
|
|
394
442
|
// src/browser/ingest/index.ts
|
|
395
443
|
function createIngest(options = {}) {
|
|
396
|
-
const
|
|
444
|
+
const opts = options;
|
|
397
445
|
const wantConsole = opts.captureConsole !== false;
|
|
398
446
|
const wantNetwork = opts.captureNetwork !== false;
|
|
399
447
|
const consoleCapture = wantConsole ? createConsoleCapture({
|
|
@@ -412,14 +460,12 @@ function createIngest(options = {}) {
|
|
|
412
460
|
consoleCapture?.start();
|
|
413
461
|
networkCapture?.start();
|
|
414
462
|
active = Boolean(consoleCapture?.isActive || networkCapture?.isActive);
|
|
415
|
-
if (active) session?.setIngest(true);
|
|
416
463
|
}
|
|
417
464
|
function stop() {
|
|
418
465
|
if (!active) return;
|
|
419
466
|
consoleCapture?.stop();
|
|
420
467
|
networkCapture?.stop();
|
|
421
468
|
active = false;
|
|
422
|
-
session?.setIngest(false);
|
|
423
469
|
}
|
|
424
470
|
return {
|
|
425
471
|
start,
|
|
@@ -541,8 +587,7 @@ var COMMAND_PALETTE_ENTRY = {
|
|
|
541
587
|
function createModeStore(options) {
|
|
542
588
|
const { nav, bindings } = options;
|
|
543
589
|
const store = createStore(() => ({
|
|
544
|
-
mode: "idle"
|
|
545
|
-
inspectorActive: false
|
|
590
|
+
mode: "idle"
|
|
546
591
|
}));
|
|
547
592
|
const transition = {
|
|
548
593
|
openPalette() {
|
|
@@ -551,17 +596,17 @@ function createModeStore(options) {
|
|
|
551
596
|
bindings?.destroyInspector?.();
|
|
552
597
|
}
|
|
553
598
|
nav.nav.reset([COMMAND_PALETTE_ENTRY]);
|
|
554
|
-
store.setState({ mode: "palette"
|
|
599
|
+
store.setState({ mode: "palette" });
|
|
555
600
|
},
|
|
556
601
|
openInspector() {
|
|
557
602
|
bindings?.mountInspector?.();
|
|
558
603
|
nav.nav.clear();
|
|
559
|
-
store.setState({ mode: "inspecting"
|
|
604
|
+
store.setState({ mode: "inspecting" });
|
|
560
605
|
},
|
|
561
606
|
closeInspector() {
|
|
562
607
|
bindings?.destroyInspector?.();
|
|
563
608
|
nav.nav.clear();
|
|
564
|
-
store.setState({ mode: "idle"
|
|
609
|
+
store.setState({ mode: "idle" });
|
|
565
610
|
},
|
|
566
611
|
toggleInspector() {
|
|
567
612
|
if (store.getState().mode === "inspecting") {
|
|
@@ -576,7 +621,7 @@ function createModeStore(options) {
|
|
|
576
621
|
bindings?.destroyInspector?.();
|
|
577
622
|
}
|
|
578
623
|
nav.nav.reset(initialStack);
|
|
579
|
-
store.setState({ mode: "viewing"
|
|
624
|
+
store.setState({ mode: "viewing" });
|
|
580
625
|
},
|
|
581
626
|
dismiss() {
|
|
582
627
|
const prev = store.getState();
|
|
@@ -584,7 +629,7 @@ function createModeStore(options) {
|
|
|
584
629
|
bindings?.destroyInspector?.();
|
|
585
630
|
}
|
|
586
631
|
nav.nav.clear();
|
|
587
|
-
store.setState({ mode: "idle"
|
|
632
|
+
store.setState({ mode: "idle" });
|
|
588
633
|
},
|
|
589
634
|
popOrTransition() {
|
|
590
635
|
const { stack } = nav.getState();
|
|
@@ -592,12 +637,12 @@ function createModeStore(options) {
|
|
|
592
637
|
nav.nav.pop();
|
|
593
638
|
} else if (stack.length === 2 && stack[0]?.id === "command-palette") {
|
|
594
639
|
nav.nav.reset([COMMAND_PALETTE_ENTRY]);
|
|
595
|
-
store.setState({ mode: "palette"
|
|
640
|
+
store.setState({ mode: "palette" });
|
|
596
641
|
} else if (stack.length === 2) {
|
|
597
642
|
nav.nav.pop();
|
|
598
643
|
} else {
|
|
599
644
|
nav.nav.clear();
|
|
600
|
-
store.setState({ mode: "idle"
|
|
645
|
+
store.setState({ mode: "idle" });
|
|
601
646
|
}
|
|
602
647
|
},
|
|
603
648
|
pushView(entry) {
|
|
@@ -614,7 +659,7 @@ function createModeStore(options) {
|
|
|
614
659
|
case "inspecting":
|
|
615
660
|
bindings?.destroyInspector?.();
|
|
616
661
|
nav.nav.reset([entry]);
|
|
617
|
-
store.setState({ mode: "viewing"
|
|
662
|
+
store.setState({ mode: "viewing" });
|
|
618
663
|
break;
|
|
619
664
|
case "palette":
|
|
620
665
|
case "viewing":
|
|
@@ -649,14 +694,6 @@ function createNavigationStore() {
|
|
|
649
694
|
store.setState({ stack: s.slice(0, -1) });
|
|
650
695
|
}
|
|
651
696
|
},
|
|
652
|
-
replace(entry) {
|
|
653
|
-
const s = store.getState().stack;
|
|
654
|
-
if (s.length === 0) {
|
|
655
|
-
store.setState({ stack: [entry] });
|
|
656
|
-
} else {
|
|
657
|
-
store.setState({ stack: [...s.slice(0, -1), entry] });
|
|
658
|
-
}
|
|
659
|
-
},
|
|
660
697
|
clear() {
|
|
661
698
|
store.setState({ stack: [] });
|
|
662
699
|
},
|
|
@@ -671,14 +708,11 @@ function createNavigationStore() {
|
|
|
671
708
|
|
|
672
709
|
// src/browser/session/store.ts
|
|
673
710
|
var defaultSnapshot = {
|
|
674
|
-
hover: null,
|
|
675
|
-
selection: null,
|
|
676
711
|
stack: [],
|
|
677
712
|
pinnedHighlight: null,
|
|
678
|
-
|
|
713
|
+
mode: "idle",
|
|
679
714
|
theme: "auto",
|
|
680
715
|
resolvedTheme: "light",
|
|
681
|
-
ingestActive: false,
|
|
682
716
|
user: null
|
|
683
717
|
};
|
|
684
718
|
function resolveTheme(preference, detect) {
|
|
@@ -729,7 +763,6 @@ function createSession(options = {}) {
|
|
|
729
763
|
} else if (highlightMode === "transient") {
|
|
730
764
|
onUpdateOverlay?.(hlCtx);
|
|
731
765
|
}
|
|
732
|
-
store.setState({ hover: ref2 });
|
|
733
766
|
},
|
|
734
767
|
unhover() {
|
|
735
768
|
if (highlightMode === "transient") {
|
|
@@ -739,7 +772,6 @@ function createSession(options = {}) {
|
|
|
739
772
|
hlCtx.color = null;
|
|
740
773
|
onHideOverlay?.();
|
|
741
774
|
}
|
|
742
|
-
store.setState({ hover: null });
|
|
743
775
|
},
|
|
744
776
|
pin(ref2) {
|
|
745
777
|
const pinRef = ref2 ?? hlCtx.ref;
|
|
@@ -767,14 +799,11 @@ function createSession(options = {}) {
|
|
|
767
799
|
};
|
|
768
800
|
const store = createStore3(() => ({
|
|
769
801
|
...defaultSnapshot,
|
|
770
|
-
hover: overrides.hover ?? null,
|
|
771
|
-
selection: overrides.selection ?? null,
|
|
772
802
|
stack: [],
|
|
773
803
|
pinnedHighlight: null,
|
|
774
|
-
|
|
804
|
+
mode: "idle",
|
|
775
805
|
theme: initialPref,
|
|
776
806
|
resolvedTheme: initialResolved,
|
|
777
|
-
ingestActive: overrides.ingestActive ?? false,
|
|
778
807
|
user: overrides.user ?? null
|
|
779
808
|
}));
|
|
780
809
|
nav.subscribe(() => {
|
|
@@ -784,29 +813,21 @@ function createSession(options = {}) {
|
|
|
784
813
|
}
|
|
785
814
|
});
|
|
786
815
|
modeStore.subscribe(() => {
|
|
787
|
-
const {
|
|
788
|
-
if (store.getState().
|
|
789
|
-
store.setState({
|
|
816
|
+
const { mode } = modeStore.getState();
|
|
817
|
+
if (store.getState().mode !== mode) {
|
|
818
|
+
store.setState({ mode });
|
|
790
819
|
}
|
|
791
820
|
});
|
|
792
821
|
const session = store;
|
|
793
822
|
session.nav = nav;
|
|
794
823
|
session.mode = modeStore;
|
|
795
824
|
session.highlight = highlightActions;
|
|
796
|
-
session.select = (ref2) => {
|
|
797
|
-
if (sameRef(store.getState().selection, ref2)) return;
|
|
798
|
-
store.setState({ selection: ref2 });
|
|
799
|
-
};
|
|
800
825
|
session.setTheme = (theme, resolved) => {
|
|
801
826
|
const state = store.getState();
|
|
802
827
|
const nextResolved = resolved ?? resolveTheme(theme, detectTheme);
|
|
803
828
|
if (state.theme === theme && state.resolvedTheme === nextResolved) return;
|
|
804
829
|
store.setState({ theme, resolvedTheme: nextResolved });
|
|
805
830
|
};
|
|
806
|
-
session.setIngest = (active) => {
|
|
807
|
-
if (store.getState().ingestActive === active) return;
|
|
808
|
-
store.setState({ ingestActive: active });
|
|
809
|
-
};
|
|
810
831
|
if (initialStack.length > 0) {
|
|
811
832
|
modeStore.transition.openPalette();
|
|
812
833
|
for (let i = 1; i < initialStack.length; i++) {
|
|
@@ -1098,6 +1119,9 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1098
1119
|
.relative {
|
|
1099
1120
|
position: relative;
|
|
1100
1121
|
}
|
|
1122
|
+
.static {
|
|
1123
|
+
position: static;
|
|
1124
|
+
}
|
|
1101
1125
|
.inset-0 {
|
|
1102
1126
|
inset: calc(var(--spacing) * 0);
|
|
1103
1127
|
}
|
|
@@ -1116,9 +1140,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1116
1140
|
.right-0 {
|
|
1117
1141
|
right: calc(var(--spacing) * 0);
|
|
1118
1142
|
}
|
|
1119
|
-
.right-2 {
|
|
1120
|
-
right: calc(var(--spacing) * 2);
|
|
1121
|
-
}
|
|
1122
1143
|
.bottom-full {
|
|
1123
1144
|
bottom: 100%;
|
|
1124
1145
|
}
|
|
@@ -1161,9 +1182,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1161
1182
|
.mx-2 {
|
|
1162
1183
|
margin-inline: calc(var(--spacing) * 2);
|
|
1163
1184
|
}
|
|
1164
|
-
.my-1 {
|
|
1165
|
-
margin-block: calc(var(--spacing) * 1);
|
|
1166
|
-
}
|
|
1167
1185
|
.ms-auto {
|
|
1168
1186
|
margin-inline-start: auto;
|
|
1169
1187
|
}
|
|
@@ -1200,9 +1218,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1200
1218
|
.inline-flex {
|
|
1201
1219
|
display: inline-flex;
|
|
1202
1220
|
}
|
|
1203
|
-
.list-item {
|
|
1204
|
-
display: list-item;
|
|
1205
|
-
}
|
|
1206
1221
|
.table {
|
|
1207
1222
|
display: table;
|
|
1208
1223
|
}
|
|
@@ -1210,10 +1225,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1210
1225
|
width: calc(var(--spacing) * 2);
|
|
1211
1226
|
height: calc(var(--spacing) * 2);
|
|
1212
1227
|
}
|
|
1213
|
-
.size-3 {
|
|
1214
|
-
width: calc(var(--spacing) * 3);
|
|
1215
|
-
height: calc(var(--spacing) * 3);
|
|
1216
|
-
}
|
|
1217
1228
|
.size-3\\.5 {
|
|
1218
1229
|
width: calc(var(--spacing) * 3.5);
|
|
1219
1230
|
height: calc(var(--spacing) * 3.5);
|
|
@@ -1271,15 +1282,9 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1271
1282
|
.h-\\[26rem\\] {
|
|
1272
1283
|
height: 26rem;
|
|
1273
1284
|
}
|
|
1274
|
-
.h-auto {
|
|
1275
|
-
height: auto;
|
|
1276
|
-
}
|
|
1277
1285
|
.h-full {
|
|
1278
1286
|
height: 100%;
|
|
1279
1287
|
}
|
|
1280
|
-
.h-px {
|
|
1281
|
-
height: 1px;
|
|
1282
|
-
}
|
|
1283
1288
|
.max-h-32 {
|
|
1284
1289
|
max-height: calc(var(--spacing) * 32);
|
|
1285
1290
|
}
|
|
@@ -1289,9 +1294,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1289
1294
|
.min-h-0 {
|
|
1290
1295
|
min-height: calc(var(--spacing) * 0);
|
|
1291
1296
|
}
|
|
1292
|
-
.min-h-7 {
|
|
1293
|
-
min-height: calc(var(--spacing) * 7);
|
|
1294
|
-
}
|
|
1295
1297
|
.min-h-8 {
|
|
1296
1298
|
min-height: calc(var(--spacing) * 8);
|
|
1297
1299
|
}
|
|
@@ -1316,9 +1318,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1316
1318
|
.w-56 {
|
|
1317
1319
|
width: calc(var(--spacing) * 56);
|
|
1318
1320
|
}
|
|
1319
|
-
.w-auto {
|
|
1320
|
-
width: auto;
|
|
1321
|
-
}
|
|
1322
1321
|
.w-full {
|
|
1323
1322
|
width: 100%;
|
|
1324
1323
|
}
|
|
@@ -1393,9 +1392,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1393
1392
|
.animate-spin {
|
|
1394
1393
|
animation: var(--animate-spin);
|
|
1395
1394
|
}
|
|
1396
|
-
.cursor-default {
|
|
1397
|
-
cursor: default;
|
|
1398
|
-
}
|
|
1399
1395
|
.cursor-pointer {
|
|
1400
1396
|
cursor: pointer;
|
|
1401
1397
|
}
|
|
@@ -1405,9 +1401,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1405
1401
|
.scroll-py-2 {
|
|
1406
1402
|
scroll-padding-block: calc(var(--spacing) * 2);
|
|
1407
1403
|
}
|
|
1408
|
-
.list-none {
|
|
1409
|
-
list-style-type: none;
|
|
1410
|
-
}
|
|
1411
1404
|
.appearance-none {
|
|
1412
1405
|
appearance: none;
|
|
1413
1406
|
}
|
|
@@ -1429,9 +1422,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1429
1422
|
.justify-center {
|
|
1430
1423
|
justify-content: center;
|
|
1431
1424
|
}
|
|
1432
|
-
.justify-start {
|
|
1433
|
-
justify-content: flex-start;
|
|
1434
|
-
}
|
|
1435
1425
|
.gap-0 {
|
|
1436
1426
|
gap: calc(var(--spacing) * 0);
|
|
1437
1427
|
}
|
|
@@ -1456,9 +1446,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1456
1446
|
.gap-6 {
|
|
1457
1447
|
gap: calc(var(--spacing) * 6);
|
|
1458
1448
|
}
|
|
1459
|
-
.self-start {
|
|
1460
|
-
align-self: flex-start;
|
|
1461
|
-
}
|
|
1462
1449
|
.truncate {
|
|
1463
1450
|
overflow: hidden;
|
|
1464
1451
|
text-overflow: ellipsis;
|
|
@@ -1673,9 +1660,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1673
1660
|
.p-6 {
|
|
1674
1661
|
padding: calc(var(--spacing) * 6);
|
|
1675
1662
|
}
|
|
1676
|
-
.px-0 {
|
|
1677
|
-
padding-inline: calc(var(--spacing) * 0);
|
|
1678
|
-
}
|
|
1679
1663
|
.px-1 {
|
|
1680
1664
|
padding-inline: calc(var(--spacing) * 1);
|
|
1681
1665
|
}
|
|
@@ -1700,9 +1684,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1700
1684
|
.px-6 {
|
|
1701
1685
|
padding-inline: calc(var(--spacing) * 6);
|
|
1702
1686
|
}
|
|
1703
|
-
.py-0 {
|
|
1704
|
-
padding-block: calc(var(--spacing) * 0);
|
|
1705
|
-
}
|
|
1706
1687
|
.py-1 {
|
|
1707
1688
|
padding-block: calc(var(--spacing) * 1);
|
|
1708
1689
|
}
|
|
@@ -1775,9 +1756,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
1775
1756
|
.text-\\[9px\\] {
|
|
1776
1757
|
font-size: 9px;
|
|
1777
1758
|
}
|
|
1778
|
-
.text-\\[10px\\] {
|
|
1779
|
-
font-size: 10px;
|
|
1780
|
-
}
|
|
1781
1759
|
.text-\\[11px\\] {
|
|
1782
1760
|
font-size: 11px;
|
|
1783
1761
|
}
|
|
@@ -2017,10 +1995,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
2017
1995
|
outline-style: var(--tw-outline-style);
|
|
2018
1996
|
outline-width: 1px;
|
|
2019
1997
|
}
|
|
2020
|
-
.blur {
|
|
2021
|
-
--tw-blur: blur(8px);
|
|
2022
|
-
filter: var(--tw-blur,) var(--tw-brightness,) var(--tw-contrast,) var(--tw-grayscale,) var(--tw-hue-rotate,) var(--tw-invert,) var(--tw-saturate,) var(--tw-sepia,) var(--tw-drop-shadow,);
|
|
2023
|
-
}
|
|
2024
1998
|
.filter {
|
|
2025
1999
|
filter: var(--tw-blur,) var(--tw-brightness,) var(--tw-contrast,) var(--tw-grayscale,) var(--tw-hue-rotate,) var(--tw-invert,) var(--tw-saturate,) var(--tw-sepia,) var(--tw-drop-shadow,);
|
|
2026
2000
|
}
|
|
@@ -2186,25 +2160,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
2186
2160
|
box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);
|
|
2187
2161
|
}
|
|
2188
2162
|
}
|
|
2189
|
-
.focus-within\\:border-ring {
|
|
2190
|
-
&:focus-within {
|
|
2191
|
-
border-color: var(--ring);
|
|
2192
|
-
}
|
|
2193
|
-
}
|
|
2194
|
-
.focus-within\\:ring-\\[3px\\] {
|
|
2195
|
-
&:focus-within {
|
|
2196
|
-
--tw-ring-shadow: var(--tw-ring-inset,) 0 0 0 calc(3px + var(--tw-ring-offset-width)) var(--tw-ring-color, currentcolor);
|
|
2197
|
-
box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);
|
|
2198
|
-
}
|
|
2199
|
-
}
|
|
2200
|
-
.focus-within\\:ring-ring\\/30 {
|
|
2201
|
-
&:focus-within {
|
|
2202
|
-
--tw-ring-color: var(--ring);
|
|
2203
|
-
@supports (color: color-mix(in lab, red, red)) {
|
|
2204
|
-
--tw-ring-color: color-mix(in oklab, var(--ring) 30%, transparent);
|
|
2205
|
-
}
|
|
2206
|
-
}
|
|
2207
|
-
}
|
|
2208
2163
|
.hover\\:border-destructive\\/30 {
|
|
2209
2164
|
&:hover {
|
|
2210
2165
|
@media (hover: hover) {
|
|
@@ -2348,11 +2303,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
2348
2303
|
pointer-events: none;
|
|
2349
2304
|
}
|
|
2350
2305
|
}
|
|
2351
|
-
.disabled\\:cursor-not-allowed {
|
|
2352
|
-
&:disabled {
|
|
2353
|
-
cursor: not-allowed;
|
|
2354
|
-
}
|
|
2355
|
-
}
|
|
2356
2306
|
.disabled\\:opacity-50 {
|
|
2357
2307
|
&:disabled {
|
|
2358
2308
|
opacity: 50%;
|
|
@@ -2363,11 +2313,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
2363
2313
|
opacity: 60%;
|
|
2364
2314
|
}
|
|
2365
2315
|
}
|
|
2366
|
-
.has-disabled\\:opacity-60 {
|
|
2367
|
-
&:has(*:disabled) {
|
|
2368
|
-
opacity: 60%;
|
|
2369
|
-
}
|
|
2370
|
-
}
|
|
2371
2316
|
.aria-invalid\\:border-destructive\\/40 {
|
|
2372
2317
|
&[aria-invalid="true"] {
|
|
2373
2318
|
border-color: var(--destructive);
|
|
@@ -2774,32 +2719,6 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
2774
2719
|
height: calc(var(--spacing) * 4.5);
|
|
2775
2720
|
}
|
|
2776
2721
|
}
|
|
2777
|
-
.\\[\\&\\>svg\\]\\:pointer-events-none {
|
|
2778
|
-
&>svg {
|
|
2779
|
-
pointer-events: none;
|
|
2780
|
-
}
|
|
2781
|
-
}
|
|
2782
|
-
.\\[\\&\\>svg\\]\\:-mx-0\\.5 {
|
|
2783
|
-
&>svg {
|
|
2784
|
-
margin-inline: calc(var(--spacing) * -0.5);
|
|
2785
|
-
}
|
|
2786
|
-
}
|
|
2787
|
-
.\\[\\&\\>svg\\]\\:shrink-0 {
|
|
2788
|
-
&>svg {
|
|
2789
|
-
flex-shrink: 0;
|
|
2790
|
-
}
|
|
2791
|
-
}
|
|
2792
|
-
.\\[\\&\\>svg\\:not\\(\\[class\\*\\=\\'opacity-\\'\\]\\)\\]\\:opacity-80 {
|
|
2793
|
-
&>svg:not([class*='opacity-']) {
|
|
2794
|
-
opacity: 80%;
|
|
2795
|
-
}
|
|
2796
|
-
}
|
|
2797
|
-
.\\[\\&\\>svg\\:not\\(\\[class\\*\\=\\'size-\\'\\]\\)\\]\\:size-4 {
|
|
2798
|
-
&>svg:not([class*='size-']) {
|
|
2799
|
-
width: calc(var(--spacing) * 4);
|
|
2800
|
-
height: calc(var(--spacing) * 4);
|
|
2801
|
-
}
|
|
2802
|
-
}
|
|
2803
2722
|
.\\[\\[data-kbd-nav\\]_\\&\\]\\:focus-within\\:bg-accent {
|
|
2804
2723
|
[data-kbd-nav] & {
|
|
2805
2724
|
&:focus-within {
|
|
@@ -3361,18 +3280,23 @@ var tailwind_built_default = `/*! tailwindcss v4.2.2 | MIT License | https://tai
|
|
|
3361
3280
|
|
|
3362
3281
|
// src/browser/surface/constants.ts
|
|
3363
3282
|
var SURFACE_HOST_CLASS = "uidex-surface-host";
|
|
3364
|
-
var SURFACE_CONTAINER_CLASS = "uidex-container";
|
|
3365
3283
|
var Z_BASE = 2147483630;
|
|
3366
3284
|
var Z_OVERLAY = 2147483635;
|
|
3367
3285
|
var Z_PIN_LAYER = 2147483640;
|
|
3368
3286
|
var Z_CHROME = 2147483645;
|
|
3369
|
-
var SURFACE_IGNORE_SELECTOR = `.${SURFACE_HOST_CLASS}
|
|
3287
|
+
var SURFACE_IGNORE_SELECTOR = `.${SURFACE_HOST_CLASS}`;
|
|
3370
3288
|
var UIDEX_ATTR_TO_KIND = [
|
|
3371
3289
|
["data-uidex", "element"],
|
|
3372
3290
|
["data-uidex-region", "region"],
|
|
3373
3291
|
["data-uidex-widget", "widget"],
|
|
3374
3292
|
["data-uidex-primitive", "primitive"]
|
|
3375
3293
|
];
|
|
3294
|
+
var DOM_BACKED_KINDS = /* @__PURE__ */ new Set([
|
|
3295
|
+
"element",
|
|
3296
|
+
"region",
|
|
3297
|
+
"widget",
|
|
3298
|
+
"primitive"
|
|
3299
|
+
]);
|
|
3376
3300
|
|
|
3377
3301
|
// src/browser/surface/host.ts
|
|
3378
3302
|
function createSurfaceHost(options) {
|
|
@@ -3550,7 +3474,7 @@ function createCursorTooltip(deps) {
|
|
|
3550
3474
|
// src/browser/surface/inspector.ts
|
|
3551
3475
|
function entityForRef(ref2, registry) {
|
|
3552
3476
|
if (registry) {
|
|
3553
|
-
const found = registry.get(ref2.kind, ref2.id);
|
|
3477
|
+
const found = registry.get(ref2.kind, ref2.id) ?? registry.matchPattern?.(ref2.kind, ref2.id);
|
|
3554
3478
|
if (found) return found;
|
|
3555
3479
|
}
|
|
3556
3480
|
if (ref2.kind === "route") return { kind: "route", path: ref2.id, page: ref2.id };
|
|
@@ -3662,7 +3586,6 @@ function createInspector(options) {
|
|
|
3662
3586
|
e.preventDefault();
|
|
3663
3587
|
e.stopPropagation();
|
|
3664
3588
|
const match = stack[layerIndex];
|
|
3665
|
-
session.select(match.ref);
|
|
3666
3589
|
onSelect?.(match, { x: e.clientX, y: e.clientY });
|
|
3667
3590
|
};
|
|
3668
3591
|
const onContextMenu = (e) => {
|
|
@@ -3711,8 +3634,6 @@ function createInspector(options) {
|
|
|
3711
3634
|
|
|
3712
3635
|
// src/browser/surface/menu-bar.ts
|
|
3713
3636
|
import {
|
|
3714
|
-
ChevronLeft,
|
|
3715
|
-
ChevronRight,
|
|
3716
3637
|
Command,
|
|
3717
3638
|
Highlighter,
|
|
3718
3639
|
MapPin,
|
|
@@ -3990,49 +3911,12 @@ function createMenuBar(options) {
|
|
|
3990
3911
|
},
|
|
3991
3912
|
pinIcon
|
|
3992
3913
|
);
|
|
3993
|
-
const commitCycler = el("div", {
|
|
3994
|
-
class: "relative z-1 inline-flex items-center gap-0.5",
|
|
3995
|
-
attrs: { "data-uidex-menubar-commit-cycler": "" }
|
|
3996
|
-
});
|
|
3997
|
-
commitCycler.hidden = true;
|
|
3998
|
-
const prevIcon = createLucideElement2(ChevronLeft);
|
|
3999
|
-
prevIcon.setAttribute("class", "size-3");
|
|
4000
|
-
prevIcon.setAttribute("aria-hidden", "true");
|
|
4001
|
-
const prevBtn = el(
|
|
4002
|
-
"button",
|
|
4003
|
-
{
|
|
4004
|
-
class: BUTTON_CLASS,
|
|
4005
|
-
attrs: { type: "button", "aria-label": "Previous commit" },
|
|
4006
|
-
style: { width: "18px", height: "18px" }
|
|
4007
|
-
},
|
|
4008
|
-
prevIcon
|
|
4009
|
-
);
|
|
4010
|
-
const commitLabel = el("span", {
|
|
4011
|
-
class: "relative z-1 whitespace-nowrap px-1 text-[10px] font-mono text-muted-foreground",
|
|
4012
|
-
attrs: { "data-uidex-menubar-commit-label": "" }
|
|
4013
|
-
});
|
|
4014
|
-
const nextIcon = createLucideElement2(ChevronRight);
|
|
4015
|
-
nextIcon.setAttribute("class", "size-3");
|
|
4016
|
-
nextIcon.setAttribute("aria-hidden", "true");
|
|
4017
|
-
const nextBtn = el(
|
|
4018
|
-
"button",
|
|
4019
|
-
{
|
|
4020
|
-
class: BUTTON_CLASS,
|
|
4021
|
-
attrs: { type: "button", "aria-label": "Next commit" },
|
|
4022
|
-
style: { width: "18px", height: "18px" }
|
|
4023
|
-
},
|
|
4024
|
-
nextIcon
|
|
4025
|
-
);
|
|
4026
|
-
commitCycler.appendChild(prevBtn);
|
|
4027
|
-
commitCycler.appendChild(commitLabel);
|
|
4028
|
-
commitCycler.appendChild(nextBtn);
|
|
4029
3914
|
const pinWrapper = el("div", {
|
|
4030
3915
|
class: "relative z-1 inline-flex items-center gap-0.5",
|
|
4031
3916
|
attrs: { "data-uidex-menubar-pin-wrapper": "" }
|
|
4032
3917
|
});
|
|
4033
3918
|
pinWrapper.hidden = true;
|
|
4034
3919
|
pinWrapper.appendChild(pinBtn);
|
|
4035
|
-
pinWrapper.appendChild(commitCycler);
|
|
4036
3920
|
root.appendChild(pinWrapper);
|
|
4037
3921
|
const updatePinUI = () => {
|
|
4038
3922
|
if (!activePinLayer) {
|
|
@@ -4040,16 +3924,7 @@ function createMenuBar(options) {
|
|
|
4040
3924
|
return;
|
|
4041
3925
|
}
|
|
4042
3926
|
const pinsVisible = activePinLayer.visible;
|
|
4043
|
-
const state = activePinLayer.filterState;
|
|
4044
|
-
const hasCommits = state.commits.length > 0;
|
|
4045
3927
|
pinWrapper.hidden = false;
|
|
4046
|
-
commitCycler.hidden = !pinsVisible || !hasCommits;
|
|
4047
|
-
if (state.commitIndex === -1 || !state.commits[state.commitIndex]) {
|
|
4048
|
-
commitLabel.textContent = `all (${state.commits.length})`;
|
|
4049
|
-
} else {
|
|
4050
|
-
const sha = state.commits[state.commitIndex] ?? "";
|
|
4051
|
-
commitLabel.textContent = sha.slice(0, 7);
|
|
4052
|
-
}
|
|
4053
3928
|
pinBtn.className = cn(BUTTON_CLASS, pinsVisible && BUTTON_ACTIVE_CLASS);
|
|
4054
3929
|
};
|
|
4055
3930
|
pinBtn.addEventListener("click", (e) => {
|
|
@@ -4058,14 +3933,6 @@ function createMenuBar(options) {
|
|
|
4058
3933
|
activePinLayer.setVisible(!activePinLayer.visible);
|
|
4059
3934
|
}
|
|
4060
3935
|
});
|
|
4061
|
-
prevBtn.addEventListener("click", (e) => {
|
|
4062
|
-
e.stopPropagation();
|
|
4063
|
-
activePinLayer?.prevCommit();
|
|
4064
|
-
});
|
|
4065
|
-
nextBtn.addEventListener("click", (e) => {
|
|
4066
|
-
e.stopPropagation();
|
|
4067
|
-
activePinLayer?.nextCommit();
|
|
4068
|
-
});
|
|
4069
3936
|
let unsubscribePinFilter = activePinLayer?.onFilterChange(() => updatePinUI());
|
|
4070
3937
|
const presenceIcon = createLucideElement2(Users);
|
|
4071
3938
|
presenceIcon.setAttribute("class", "size-3.5");
|
|
@@ -4159,7 +4026,7 @@ function createMenuBar(options) {
|
|
|
4159
4026
|
container.appendChild(root);
|
|
4160
4027
|
const syncButtonStates = () => {
|
|
4161
4028
|
const state = session.getState();
|
|
4162
|
-
const inspectActive = state.
|
|
4029
|
+
const inspectActive = state.mode === "inspecting";
|
|
4163
4030
|
inspectBtn.setAttribute(
|
|
4164
4031
|
"data-uidex-menubar-inspect-active",
|
|
4165
4032
|
inspectActive ? "true" : "false"
|
|
@@ -4278,6 +4145,49 @@ function createMenuBar(options) {
|
|
|
4278
4145
|
};
|
|
4279
4146
|
}
|
|
4280
4147
|
|
|
4148
|
+
// src/browser/internal/repositioner.ts
|
|
4149
|
+
function createRepositioner(onReflow) {
|
|
4150
|
+
let rafId = null;
|
|
4151
|
+
let attached = false;
|
|
4152
|
+
const schedule = () => {
|
|
4153
|
+
if (rafId !== null) return;
|
|
4154
|
+
rafId = typeof requestAnimationFrame === "function" ? requestAnimationFrame(() => {
|
|
4155
|
+
rafId = null;
|
|
4156
|
+
onReflow();
|
|
4157
|
+
}) : setTimeout(() => {
|
|
4158
|
+
rafId = null;
|
|
4159
|
+
onReflow();
|
|
4160
|
+
}, 0);
|
|
4161
|
+
};
|
|
4162
|
+
const cancel = () => {
|
|
4163
|
+
if (rafId === null) return;
|
|
4164
|
+
if (typeof cancelAnimationFrame === "function") cancelAnimationFrame(rafId);
|
|
4165
|
+
else clearTimeout(rafId);
|
|
4166
|
+
rafId = null;
|
|
4167
|
+
};
|
|
4168
|
+
const onScroll = () => schedule();
|
|
4169
|
+
const onResize = () => schedule();
|
|
4170
|
+
const attach = () => {
|
|
4171
|
+
if (attached) return;
|
|
4172
|
+
attached = true;
|
|
4173
|
+
window.addEventListener("resize", onResize);
|
|
4174
|
+
window.addEventListener("scroll", onScroll, {
|
|
4175
|
+
capture: true,
|
|
4176
|
+
passive: true
|
|
4177
|
+
});
|
|
4178
|
+
};
|
|
4179
|
+
const detach = () => {
|
|
4180
|
+
if (!attached) return;
|
|
4181
|
+
attached = false;
|
|
4182
|
+
window.removeEventListener("resize", onResize);
|
|
4183
|
+
window.removeEventListener("scroll", onScroll, {
|
|
4184
|
+
capture: true
|
|
4185
|
+
});
|
|
4186
|
+
cancel();
|
|
4187
|
+
};
|
|
4188
|
+
return { schedule, cancel, attach, detach };
|
|
4189
|
+
}
|
|
4190
|
+
|
|
4281
4191
|
// src/browser/surface/overlay.ts
|
|
4282
4192
|
var DEFAULT_COLOR = "#34d399";
|
|
4283
4193
|
var DEFAULT_BORDER_WIDTH = 2;
|
|
@@ -4345,44 +4255,7 @@ function createOverlay(deps) {
|
|
|
4345
4255
|
fillOpacity: DEFAULT_FILL_OPACITY,
|
|
4346
4256
|
backdrop: false
|
|
4347
4257
|
};
|
|
4348
|
-
|
|
4349
|
-
let attached = false;
|
|
4350
|
-
const schedule = () => {
|
|
4351
|
-
if (rafId !== null) return;
|
|
4352
|
-
rafId = typeof requestAnimationFrame === "function" ? requestAnimationFrame(() => {
|
|
4353
|
-
rafId = null;
|
|
4354
|
-
updatePosition();
|
|
4355
|
-
}) : setTimeout(() => {
|
|
4356
|
-
rafId = null;
|
|
4357
|
-
updatePosition();
|
|
4358
|
-
}, 0);
|
|
4359
|
-
};
|
|
4360
|
-
const cancelSchedule = () => {
|
|
4361
|
-
if (rafId === null) return;
|
|
4362
|
-
if (typeof cancelAnimationFrame === "function") cancelAnimationFrame(rafId);
|
|
4363
|
-
else clearTimeout(rafId);
|
|
4364
|
-
rafId = null;
|
|
4365
|
-
};
|
|
4366
|
-
const onScroll = () => schedule();
|
|
4367
|
-
const onResize = () => schedule();
|
|
4368
|
-
const attach = () => {
|
|
4369
|
-
if (attached) return;
|
|
4370
|
-
attached = true;
|
|
4371
|
-
window.addEventListener("resize", onResize);
|
|
4372
|
-
window.addEventListener("scroll", onScroll, {
|
|
4373
|
-
capture: true,
|
|
4374
|
-
passive: true
|
|
4375
|
-
});
|
|
4376
|
-
};
|
|
4377
|
-
const detach = () => {
|
|
4378
|
-
if (!attached) return;
|
|
4379
|
-
attached = false;
|
|
4380
|
-
window.removeEventListener("resize", onResize);
|
|
4381
|
-
window.removeEventListener("scroll", onScroll, {
|
|
4382
|
-
capture: true
|
|
4383
|
-
});
|
|
4384
|
-
cancelSchedule();
|
|
4385
|
-
};
|
|
4258
|
+
const repositioner = createRepositioner(() => updatePosition());
|
|
4386
4259
|
function updatePosition() {
|
|
4387
4260
|
if (!target) return;
|
|
4388
4261
|
const rect = target.getBoundingClientRect();
|
|
@@ -4446,16 +4319,16 @@ function createOverlay(deps) {
|
|
|
4446
4319
|
box.offsetHeight;
|
|
4447
4320
|
}
|
|
4448
4321
|
box.style.opacity = "1";
|
|
4449
|
-
attach();
|
|
4322
|
+
repositioner.attach();
|
|
4450
4323
|
},
|
|
4451
4324
|
hide() {
|
|
4452
4325
|
target = null;
|
|
4453
4326
|
box.style.opacity = "0";
|
|
4454
4327
|
backdrop.style.opacity = "0";
|
|
4455
|
-
detach();
|
|
4328
|
+
repositioner.detach();
|
|
4456
4329
|
},
|
|
4457
4330
|
destroy() {
|
|
4458
|
-
detach();
|
|
4331
|
+
repositioner.detach();
|
|
4459
4332
|
box.remove();
|
|
4460
4333
|
backdrop.remove();
|
|
4461
4334
|
target = null;
|
|
@@ -4572,8 +4445,7 @@ function createSurfaceShell(options) {
|
|
|
4572
4445
|
const overlay = createOverlay({ container: host.shadowRoot });
|
|
4573
4446
|
cleanup.add(overlay);
|
|
4574
4447
|
const tooltip = createCursorTooltip({
|
|
4575
|
-
container: host.chromeEl
|
|
4576
|
-
session: options.session
|
|
4448
|
+
container: host.chromeEl
|
|
4577
4449
|
});
|
|
4578
4450
|
cleanup.add(tooltip);
|
|
4579
4451
|
const afterHover = options.inspector?.onAfterHover;
|
|
@@ -4765,9 +4637,6 @@ function createPinLayer(options) {
|
|
|
4765
4637
|
const seenIds = /* @__PURE__ */ new Set();
|
|
4766
4638
|
const byComp = /* @__PURE__ */ new Map();
|
|
4767
4639
|
const indicators = /* @__PURE__ */ new Map();
|
|
4768
|
-
let filter = { branch: null, commit: null };
|
|
4769
|
-
let commits = [];
|
|
4770
|
-
let commitIndex = -1;
|
|
4771
4640
|
const filterCbs = /* @__PURE__ */ new Set();
|
|
4772
4641
|
const notifyFilter = () => {
|
|
4773
4642
|
for (const cb of filterCbs) cb();
|
|
@@ -4782,8 +4651,6 @@ function createPinLayer(options) {
|
|
|
4782
4651
|
}
|
|
4783
4652
|
};
|
|
4784
4653
|
const rerender = () => {
|
|
4785
|
-
commits = [];
|
|
4786
|
-
commitIndex = -1;
|
|
4787
4654
|
rebuildFiltered();
|
|
4788
4655
|
for (const id of Array.from(indicators.keys())) {
|
|
4789
4656
|
if (!byComp.has(id)) removeIndicator(id);
|
|
@@ -4792,45 +4659,8 @@ function createPinLayer(options) {
|
|
|
4792
4659
|
notifyFilter();
|
|
4793
4660
|
onPinsChanged?.();
|
|
4794
4661
|
};
|
|
4795
|
-
let rafId = null;
|
|
4796
|
-
let winAttached = false;
|
|
4797
4662
|
let obs = null;
|
|
4798
|
-
const
|
|
4799
|
-
if (rafId !== null) return;
|
|
4800
|
-
rafId = typeof requestAnimationFrame === "function" ? requestAnimationFrame(() => {
|
|
4801
|
-
rafId = null;
|
|
4802
|
-
posAll();
|
|
4803
|
-
}) : setTimeout(() => {
|
|
4804
|
-
rafId = null;
|
|
4805
|
-
posAll();
|
|
4806
|
-
}, 0);
|
|
4807
|
-
};
|
|
4808
|
-
const cancelPos = () => {
|
|
4809
|
-
if (rafId === null) return;
|
|
4810
|
-
if (typeof cancelAnimationFrame === "function") cancelAnimationFrame(rafId);
|
|
4811
|
-
else clearTimeout(rafId);
|
|
4812
|
-
rafId = null;
|
|
4813
|
-
};
|
|
4814
|
-
const onScroll = () => schedulePos();
|
|
4815
|
-
const onResize = () => schedulePos();
|
|
4816
|
-
const attachWin = () => {
|
|
4817
|
-
if (winAttached) return;
|
|
4818
|
-
winAttached = true;
|
|
4819
|
-
window.addEventListener("scroll", onScroll, {
|
|
4820
|
-
capture: true,
|
|
4821
|
-
passive: true
|
|
4822
|
-
});
|
|
4823
|
-
window.addEventListener("resize", onResize);
|
|
4824
|
-
};
|
|
4825
|
-
const detachWin = () => {
|
|
4826
|
-
if (!winAttached) return;
|
|
4827
|
-
winAttached = false;
|
|
4828
|
-
window.removeEventListener("scroll", onScroll, {
|
|
4829
|
-
capture: true
|
|
4830
|
-
});
|
|
4831
|
-
window.removeEventListener("resize", onResize);
|
|
4832
|
-
cancelPos();
|
|
4833
|
-
};
|
|
4663
|
+
const repositioner = createRepositioner(() => posAll());
|
|
4834
4664
|
const attachObs = () => {
|
|
4835
4665
|
if (obs || typeof MutationObserver === "undefined") return;
|
|
4836
4666
|
obs = new MutationObserver((recs) => {
|
|
@@ -4854,7 +4684,7 @@ function createPinLayer(options) {
|
|
|
4854
4684
|
s.anchor = resolveEntityElement(parseComponentRef(s.componentId));
|
|
4855
4685
|
changed = true;
|
|
4856
4686
|
}
|
|
4857
|
-
if (changed)
|
|
4687
|
+
if (changed) repositioner.schedule();
|
|
4858
4688
|
};
|
|
4859
4689
|
const expand = (st) => {
|
|
4860
4690
|
if (st.expanded) return;
|
|
@@ -5096,7 +4926,7 @@ function createPinLayer(options) {
|
|
|
5096
4926
|
if (!st) {
|
|
5097
4927
|
st = buildIndicator(componentId);
|
|
5098
4928
|
indicators.set(componentId, st);
|
|
5099
|
-
|
|
4929
|
+
repositioner.attach();
|
|
5100
4930
|
attachObs();
|
|
5101
4931
|
}
|
|
5102
4932
|
if (st.pinIndex >= pins.length) st.pinIndex = 0;
|
|
@@ -5110,7 +4940,7 @@ function createPinLayer(options) {
|
|
|
5110
4940
|
st.wrap.remove();
|
|
5111
4941
|
indicators.delete(componentId);
|
|
5112
4942
|
if (indicators.size === 0) {
|
|
5113
|
-
|
|
4943
|
+
repositioner.detach();
|
|
5114
4944
|
detachObs();
|
|
5115
4945
|
}
|
|
5116
4946
|
};
|
|
@@ -5145,17 +4975,22 @@ function createPinLayer(options) {
|
|
|
5145
4975
|
seenIds.clear();
|
|
5146
4976
|
byComp.clear();
|
|
5147
4977
|
for (const id of Array.from(indicators.keys())) removeIndicator(id);
|
|
5148
|
-
commits = [];
|
|
5149
|
-
commitIndex = -1;
|
|
5150
4978
|
notifyFilter();
|
|
5151
4979
|
},
|
|
5152
4980
|
getPinsForElement: (id) => byComp.get(id) ?? [],
|
|
5153
|
-
getAllPinsForElement: (id) => allPins.filter((p) => (p.entity ?? "") === id),
|
|
5154
4981
|
getAllPins: () => allPins.slice(),
|
|
5155
4982
|
attachChannel(channel) {
|
|
5156
|
-
|
|
4983
|
+
const offPin = channel.onPin((pin) => {
|
|
5157
4984
|
layer.addPin(pin);
|
|
5158
4985
|
});
|
|
4986
|
+
const offArchived = channel.onPinArchived?.((reportId) => {
|
|
4987
|
+
layer.removePin(reportId);
|
|
4988
|
+
}) ?? (() => {
|
|
4989
|
+
});
|
|
4990
|
+
return () => {
|
|
4991
|
+
offPin();
|
|
4992
|
+
offArchived();
|
|
4993
|
+
};
|
|
5159
4994
|
},
|
|
5160
4995
|
attachCloud(opts) {
|
|
5161
4996
|
const offCh = opts.channel ? layer.attachChannel(opts.channel) : () => {
|
|
@@ -5186,39 +5021,6 @@ function createPinLayer(options) {
|
|
|
5186
5021
|
async refresh() {
|
|
5187
5022
|
if (activeRefresh) await activeRefresh();
|
|
5188
5023
|
},
|
|
5189
|
-
get filterState() {
|
|
5190
|
-
return {
|
|
5191
|
-
branch: filter.branch,
|
|
5192
|
-
commit: filter.commit,
|
|
5193
|
-
commits,
|
|
5194
|
-
commitIndex
|
|
5195
|
-
};
|
|
5196
|
-
},
|
|
5197
|
-
setFilter(next) {
|
|
5198
|
-
filter = {
|
|
5199
|
-
branch: next.branch !== void 0 ? next.branch : filter.branch,
|
|
5200
|
-
commit: next.commit !== void 0 ? next.commit : filter.commit
|
|
5201
|
-
};
|
|
5202
|
-
rerender();
|
|
5203
|
-
},
|
|
5204
|
-
nextCommit() {
|
|
5205
|
-
if (!commits.length) return;
|
|
5206
|
-
commitIndex = commitIndex >= commits.length - 1 ? -1 : commitIndex + 1;
|
|
5207
|
-
filter = {
|
|
5208
|
-
...filter,
|
|
5209
|
-
commit: commitIndex === -1 ? null : commits[commitIndex]
|
|
5210
|
-
};
|
|
5211
|
-
rerender();
|
|
5212
|
-
},
|
|
5213
|
-
prevCommit() {
|
|
5214
|
-
if (!commits.length) return;
|
|
5215
|
-
commitIndex = commitIndex <= -1 ? commits.length - 1 : commitIndex - 1;
|
|
5216
|
-
filter = {
|
|
5217
|
-
...filter,
|
|
5218
|
-
commit: commitIndex === -1 ? null : commits[commitIndex]
|
|
5219
|
-
};
|
|
5220
|
-
rerender();
|
|
5221
|
-
},
|
|
5222
5024
|
onFilterChange(cb) {
|
|
5223
5025
|
filterCbs.add(cb);
|
|
5224
5026
|
return () => {
|
|
@@ -5237,7 +5039,7 @@ function createPinLayer(options) {
|
|
|
5237
5039
|
},
|
|
5238
5040
|
destroy() {
|
|
5239
5041
|
layer.clear();
|
|
5240
|
-
|
|
5042
|
+
repositioner.detach();
|
|
5241
5043
|
detachObs();
|
|
5242
5044
|
layerEl.remove();
|
|
5243
5045
|
activeRefresh = null;
|
|
@@ -5280,9 +5082,11 @@ function createRouter(options) {
|
|
|
5280
5082
|
if (view === null || typeof view !== "object" || typeof view.id !== "string" || view.id.length === 0) {
|
|
5281
5083
|
throw new ViewValidationError("View must have a non-empty string id");
|
|
5282
5084
|
}
|
|
5283
|
-
|
|
5085
|
+
const hasSurface = typeof view.surface === "function";
|
|
5086
|
+
const hasRender = typeof view.render === "function";
|
|
5087
|
+
if (!hasSurface && !hasRender) {
|
|
5284
5088
|
throw new ViewValidationError(
|
|
5285
|
-
`View ${view.id}: 'surface'
|
|
5089
|
+
`View ${view.id}: a 'surface' function (or a 'render' override) is required`
|
|
5286
5090
|
);
|
|
5287
5091
|
}
|
|
5288
5092
|
if (!view.matches && !view.palette) {
|
|
@@ -5340,7 +5144,6 @@ function createRouter(options) {
|
|
|
5340
5144
|
if (idx >= 0) recentRefs.splice(idx, 1);
|
|
5341
5145
|
recentRefs.unshift(ref2);
|
|
5342
5146
|
if (recentRefs.length > MAX_RECENTS) recentRefs.length = MAX_RECENTS;
|
|
5343
|
-
options.session.select(ref2);
|
|
5344
5147
|
const entry = { id: match.view.id, ref: ref2 };
|
|
5345
5148
|
const { mode } = options.session.mode.getState();
|
|
5346
5149
|
if (mode === "idle" || mode === "inspecting") {
|
|
@@ -5395,74 +5198,24 @@ function detectDev() {
|
|
|
5395
5198
|
|
|
5396
5199
|
// src/browser/internal/lit.ts
|
|
5397
5200
|
import { html, svg, render, nothing } from "lit-html";
|
|
5398
|
-
import { repeat } from "lit-html/directives/repeat.js";
|
|
5399
5201
|
import { ref, createRef } from "lit-html/directives/ref.js";
|
|
5400
|
-
import { classMap } from "lit-html/directives/class-map.js";
|
|
5401
5202
|
|
|
5402
|
-
// src/browser/internal/
|
|
5403
|
-
|
|
5404
|
-
|
|
5405
|
-
|
|
5406
|
-
|
|
5407
|
-
|
|
5408
|
-
|
|
5409
|
-
|
|
5410
|
-
|
|
5411
|
-
|
|
5412
|
-
|
|
5413
|
-
|
|
5414
|
-
|
|
5415
|
-
|
|
5416
|
-
if (
|
|
5417
|
-
|
|
5418
|
-
continue;
|
|
5419
|
-
}
|
|
5420
|
-
if (typeof rawValue === "boolean") {
|
|
5421
|
-
if (rawValue) node.setAttribute(key, "");
|
|
5422
|
-
else node.removeAttribute(key);
|
|
5423
|
-
continue;
|
|
5424
|
-
}
|
|
5425
|
-
if (key === "style" && typeof rawValue === "object") {
|
|
5426
|
-
Object.assign(
|
|
5427
|
-
node.style,
|
|
5428
|
-
rawValue
|
|
5429
|
-
);
|
|
5430
|
-
continue;
|
|
5431
|
-
}
|
|
5432
|
-
if (key === "className" || key === "class") {
|
|
5433
|
-
node.setAttribute("class", String(rawValue));
|
|
5434
|
-
continue;
|
|
5435
|
-
}
|
|
5436
|
-
if (key === "htmlFor") {
|
|
5437
|
-
node.setAttribute("for", String(rawValue));
|
|
5438
|
-
continue;
|
|
5439
|
-
}
|
|
5440
|
-
if (key === "tabIndex") {
|
|
5441
|
-
;
|
|
5442
|
-
node.tabIndex = Number(rawValue);
|
|
5443
|
-
continue;
|
|
5444
|
-
}
|
|
5445
|
-
node.setAttribute(key, String(rawValue));
|
|
5446
|
-
}
|
|
5447
|
-
return () => removers.forEach((fn) => fn());
|
|
5448
|
-
}
|
|
5449
|
-
|
|
5450
|
-
// src/browser/internal/lit-icon.ts
|
|
5451
|
-
import { noChange } from "lit-html";
|
|
5452
|
-
import {
|
|
5453
|
-
Directive,
|
|
5454
|
-
directive,
|
|
5455
|
-
PartType
|
|
5456
|
-
} from "lit-html/directive.js";
|
|
5457
|
-
import { createElement } from "lucide";
|
|
5458
|
-
var LucideIconDirective = class extends Directive {
|
|
5459
|
-
_icon;
|
|
5460
|
-
_class;
|
|
5461
|
-
_el;
|
|
5462
|
-
constructor(partInfo) {
|
|
5463
|
-
super(partInfo);
|
|
5464
|
-
if (partInfo.type !== PartType.CHILD) {
|
|
5465
|
-
throw new Error("icon() can only be used in a child position");
|
|
5203
|
+
// src/browser/internal/lit-icon.ts
|
|
5204
|
+
import { noChange } from "lit-html";
|
|
5205
|
+
import {
|
|
5206
|
+
Directive,
|
|
5207
|
+
directive,
|
|
5208
|
+
PartType
|
|
5209
|
+
} from "lit-html/directive.js";
|
|
5210
|
+
import { createElement } from "lucide";
|
|
5211
|
+
var LucideIconDirective = class extends Directive {
|
|
5212
|
+
_icon;
|
|
5213
|
+
_class;
|
|
5214
|
+
_el;
|
|
5215
|
+
constructor(partInfo) {
|
|
5216
|
+
super(partInfo);
|
|
5217
|
+
if (partInfo.type !== PartType.CHILD) {
|
|
5218
|
+
throw new Error("icon() can only be used in a child position");
|
|
5466
5219
|
}
|
|
5467
5220
|
}
|
|
5468
5221
|
update(_part, [iconNode, className]) {
|
|
@@ -5483,6 +5236,16 @@ var LucideIconDirective = class extends Directive {
|
|
|
5483
5236
|
};
|
|
5484
5237
|
var icon = directive(LucideIconDirective);
|
|
5485
5238
|
|
|
5239
|
+
// src/browser/views/primitives/chip.ts
|
|
5240
|
+
var CHIP_CLASS = "inline-flex items-center gap-1.5 text-xs font-medium text-muted-foreground";
|
|
5241
|
+
function createChip(options = {}, children = []) {
|
|
5242
|
+
const { class: extra, ...rest } = options;
|
|
5243
|
+
return el("span", { ...rest, class: cn(CHIP_CLASS, extra) }, children);
|
|
5244
|
+
}
|
|
5245
|
+
|
|
5246
|
+
// src/browser/views/primitives/kind-icon.ts
|
|
5247
|
+
import { createElement as createLucideElement4 } from "lucide";
|
|
5248
|
+
|
|
5486
5249
|
// src/browser/ui/cva.ts
|
|
5487
5250
|
function cva(base, config = {}) {
|
|
5488
5251
|
return (props = {}) => {
|
|
@@ -5521,17 +5284,15 @@ var badgeVariants = cva(badgeBase, {
|
|
|
5521
5284
|
}
|
|
5522
5285
|
}
|
|
5523
5286
|
});
|
|
5524
|
-
|
|
5525
|
-
|
|
5526
|
-
|
|
5527
|
-
|
|
5528
|
-
|
|
5529
|
-
|
|
5287
|
+
function badgeTpl(content, options = {}) {
|
|
5288
|
+
const { variant, size, class: extra } = options;
|
|
5289
|
+
return html`
|
|
5290
|
+
<span class=${cn(badgeVariants({ variant, size }), extra)} data-slot="badge"
|
|
5291
|
+
>${content}</span
|
|
5292
|
+
>
|
|
5293
|
+
`;
|
|
5530
5294
|
}
|
|
5531
5295
|
|
|
5532
|
-
// src/browser/views/primitives/kind-icon.ts
|
|
5533
|
-
import { createElement as createLucideElement4 } from "lucide";
|
|
5534
|
-
|
|
5535
5296
|
// src/browser/views/primitives/icon-tile.ts
|
|
5536
5297
|
var TILE_CLASS = "inline-flex size-6 shrink-0 items-center justify-center rounded-md bg-muted text-muted-foreground";
|
|
5537
5298
|
var ICON_SIZE_CLASS_RE = /\b(h-\d+|w-\d+|size-\d+)\b/g;
|
|
@@ -6039,6 +5800,54 @@ function createScrollArea(props = {}) {
|
|
|
6039
5800
|
);
|
|
6040
5801
|
}
|
|
6041
5802
|
|
|
5803
|
+
// src/browser/internal/apply-props.ts
|
|
5804
|
+
function applyProps(node, props) {
|
|
5805
|
+
const removers = [];
|
|
5806
|
+
for (const [key, rawValue] of Object.entries(props)) {
|
|
5807
|
+
if (key === "children" || key === "dangerouslySetInnerHTML") continue;
|
|
5808
|
+
if (key.startsWith("on") && typeof rawValue === "function") {
|
|
5809
|
+
const eventName = key.slice(2).toLowerCase();
|
|
5810
|
+
const isTextControl = node instanceof HTMLInputElement && node.type !== "checkbox" && node.type !== "radio" || node instanceof HTMLTextAreaElement;
|
|
5811
|
+
const effectiveEvent = eventName === "change" && isTextControl ? "input" : eventName;
|
|
5812
|
+
const listener = rawValue;
|
|
5813
|
+
node.addEventListener(effectiveEvent, listener);
|
|
5814
|
+
removers.push(() => node.removeEventListener(effectiveEvent, listener));
|
|
5815
|
+
continue;
|
|
5816
|
+
}
|
|
5817
|
+
if (rawValue === void 0 || rawValue === null) {
|
|
5818
|
+
node.removeAttribute(key);
|
|
5819
|
+
continue;
|
|
5820
|
+
}
|
|
5821
|
+
if (typeof rawValue === "boolean") {
|
|
5822
|
+
if (rawValue) node.setAttribute(key, "");
|
|
5823
|
+
else node.removeAttribute(key);
|
|
5824
|
+
continue;
|
|
5825
|
+
}
|
|
5826
|
+
if (key === "style" && typeof rawValue === "object") {
|
|
5827
|
+
Object.assign(
|
|
5828
|
+
node.style,
|
|
5829
|
+
rawValue
|
|
5830
|
+
);
|
|
5831
|
+
continue;
|
|
5832
|
+
}
|
|
5833
|
+
if (key === "className" || key === "class") {
|
|
5834
|
+
node.setAttribute("class", String(rawValue));
|
|
5835
|
+
continue;
|
|
5836
|
+
}
|
|
5837
|
+
if (key === "htmlFor") {
|
|
5838
|
+
node.setAttribute("for", String(rawValue));
|
|
5839
|
+
continue;
|
|
5840
|
+
}
|
|
5841
|
+
if (key === "tabIndex") {
|
|
5842
|
+
;
|
|
5843
|
+
node.tabIndex = Number(rawValue);
|
|
5844
|
+
continue;
|
|
5845
|
+
}
|
|
5846
|
+
node.setAttribute(key, String(rawValue));
|
|
5847
|
+
}
|
|
5848
|
+
return () => removers.forEach((fn) => fn());
|
|
5849
|
+
}
|
|
5850
|
+
|
|
6042
5851
|
// src/browser/views/builder/spread-props.ts
|
|
6043
5852
|
function spreadProps(node, props) {
|
|
6044
5853
|
return applyProps(node, props);
|
|
@@ -6058,21 +5867,6 @@ function createPersistentSpreads() {
|
|
|
6058
5867
|
};
|
|
6059
5868
|
}
|
|
6060
5869
|
|
|
6061
|
-
// src/browser/views/render/detail.ts
|
|
6062
|
-
import {
|
|
6063
|
-
ArchiveX,
|
|
6064
|
-
Camera,
|
|
6065
|
-
ChevronDown,
|
|
6066
|
-
Copy,
|
|
6067
|
-
Highlighter as Highlighter2,
|
|
6068
|
-
Inbox,
|
|
6069
|
-
MessageCircleWarning,
|
|
6070
|
-
StickyNote as StickyNote2,
|
|
6071
|
-
TicketPlus,
|
|
6072
|
-
View,
|
|
6073
|
-
createElement as createLucideElement5
|
|
6074
|
-
} from "lucide";
|
|
6075
|
-
|
|
6076
5870
|
// src/browser/internal/arrow-nav.ts
|
|
6077
5871
|
var NAV_KEYS = /* @__PURE__ */ new Set(["ArrowDown", "ArrowUp", "Home", "End"]);
|
|
6078
5872
|
function bindArrowNav(options) {
|
|
@@ -6144,30 +5938,6 @@ function focusItem(items, idx) {
|
|
|
6144
5938
|
items[idx].focus();
|
|
6145
5939
|
}
|
|
6146
5940
|
|
|
6147
|
-
// src/browser/views/builder/filter.ts
|
|
6148
|
-
function normalizeQuery(query) {
|
|
6149
|
-
return query.trim().toLowerCase();
|
|
6150
|
-
}
|
|
6151
|
-
function matchesQuery(haystack, query) {
|
|
6152
|
-
const q = normalizeQuery(query);
|
|
6153
|
-
if (!q) return true;
|
|
6154
|
-
return haystack.toLowerCase().includes(q);
|
|
6155
|
-
}
|
|
6156
|
-
function filterEntities(entities, query) {
|
|
6157
|
-
const q = normalizeQuery(query);
|
|
6158
|
-
if (!q) return entities;
|
|
6159
|
-
return entities.filter((e) => {
|
|
6160
|
-
const name = displayName(e).toLowerCase();
|
|
6161
|
-
const id = entityKey(e).toLowerCase();
|
|
6162
|
-
return name.includes(q) || id.includes(q) || e.kind.toLowerCase().includes(q);
|
|
6163
|
-
});
|
|
6164
|
-
}
|
|
6165
|
-
function filterIds(ids, query) {
|
|
6166
|
-
const q = normalizeQuery(query);
|
|
6167
|
-
if (!q) return ids;
|
|
6168
|
-
return ids.filter((id) => id.toLowerCase().includes(q));
|
|
6169
|
-
}
|
|
6170
|
-
|
|
6171
5941
|
// src/browser/views/labels.ts
|
|
6172
5942
|
var SECTION_LABELS = {
|
|
6173
5943
|
acceptance: "Acceptance criteria",
|
|
@@ -6192,171 +5962,6 @@ var LIST_ITEM_STATE_CLASS = "data-[disabled]:pointer-events-none data-[disabled]
|
|
|
6192
5962
|
var LIST_ITEM_INTERACTIVE_CLASS = "uidex-item-interactive [[data-kbd-nav]_&]:focus:bg-accent [[data-kbd-nav]_&]:focus:text-accent-foreground [[data-kbd-nav]_&]:focus-within:bg-accent [[data-kbd-nav]_&]:focus-within:text-accent-foreground";
|
|
6193
5963
|
var LIST_GROUP_LABEL_CLASS = "text-muted-foreground px-2 py-1.5 text-xs font-medium";
|
|
6194
5964
|
|
|
6195
|
-
// src/browser/ui/button.ts
|
|
6196
|
-
var buttonBase = "focus-visible:ring-ring focus-visible:ring-offset-background disabled:opacity-60 relative inline-flex shrink-0 cursor-pointer items-center justify-center gap-2 whitespace-nowrap rounded-lg border text-sm font-medium outline-none transition-shadow focus-visible:ring-2 focus-visible:ring-offset-1 disabled:pointer-events-none [&_svg:not([class*='size-'])]:size-4 [&_svg:not([class*='opacity-'])]:opacity-80 [&_svg]:pointer-events-none [&_svg]:shrink-0";
|
|
6197
|
-
var buttonVariants = cva(buttonBase, {
|
|
6198
|
-
defaultVariants: { size: "default", variant: "default" },
|
|
6199
|
-
variants: {
|
|
6200
|
-
size: {
|
|
6201
|
-
default: "h-8 px-3",
|
|
6202
|
-
sm: "h-7 gap-1.5 px-2.5",
|
|
6203
|
-
xs: "h-6 gap-1 rounded-md px-2 text-xs",
|
|
6204
|
-
lg: "h-9 px-3.5",
|
|
6205
|
-
xl: "h-10 px-4 text-base",
|
|
6206
|
-
icon: "size-8",
|
|
6207
|
-
"icon-sm": "size-7",
|
|
6208
|
-
"icon-lg": "size-9",
|
|
6209
|
-
"icon-xs": "size-6 rounded-md"
|
|
6210
|
-
},
|
|
6211
|
-
variant: {
|
|
6212
|
-
default: "border-primary bg-primary text-primary-foreground shadow-xs hover:bg-primary/90",
|
|
6213
|
-
destructive: "border-destructive bg-destructive shadow-xs hover:bg-destructive/90 text-white",
|
|
6214
|
-
"destructive-outline": "border-input bg-popover text-destructive-foreground shadow-xs/5 hover:border-destructive/30 hover:bg-destructive/5 dark:bg-input/30",
|
|
6215
|
-
ghost: "text-foreground hover:bg-accent hover:text-accent-foreground border-transparent",
|
|
6216
|
-
link: "text-foreground border-transparent underline-offset-4 hover:underline",
|
|
6217
|
-
outline: "border-input bg-popover text-foreground shadow-xs/5 hover:bg-accent hover:text-accent-foreground dark:bg-input/30",
|
|
6218
|
-
secondary: "bg-secondary text-secondary-foreground hover:bg-secondary/90 border-transparent"
|
|
6219
|
-
}
|
|
6220
|
-
}
|
|
6221
|
-
});
|
|
6222
|
-
|
|
6223
|
-
// src/browser/views/primitives/entity-presence.ts
|
|
6224
|
-
var DOM_BACKED_KINDS = /* @__PURE__ */ new Set([
|
|
6225
|
-
"element",
|
|
6226
|
-
"region",
|
|
6227
|
-
"widget",
|
|
6228
|
-
"primitive"
|
|
6229
|
-
]);
|
|
6230
|
-
var TOUCH_RESOLVE_KINDS = [
|
|
6231
|
-
"element",
|
|
6232
|
-
"widget",
|
|
6233
|
-
"region",
|
|
6234
|
-
"primitive"
|
|
6235
|
-
];
|
|
6236
|
-
function isAbsentFromPage(ref2, registry) {
|
|
6237
|
-
if (DOM_BACKED_KINDS.has(ref2.kind)) {
|
|
6238
|
-
return !resolveEntityElement(ref2);
|
|
6239
|
-
}
|
|
6240
|
-
if (ref2.kind === "flow" && registry) {
|
|
6241
|
-
const flow = registry.get("flow", ref2.id);
|
|
6242
|
-
if (!flow) return true;
|
|
6243
|
-
for (const touchId of flow.touches) {
|
|
6244
|
-
for (const kind of TOUCH_RESOLVE_KINDS) {
|
|
6245
|
-
const entity = registry.get(kind, touchId);
|
|
6246
|
-
if (entity && resolveEntityElement({ kind, id: touchId })) return false;
|
|
6247
|
-
}
|
|
6248
|
-
}
|
|
6249
|
-
return true;
|
|
6250
|
-
}
|
|
6251
|
-
return false;
|
|
6252
|
-
}
|
|
6253
|
-
|
|
6254
|
-
// src/browser/ui/kbd.ts
|
|
6255
|
-
var KBD_CLASS = "bg-muted text-muted-foreground pointer-events-none inline-flex h-5 min-w-5 select-none items-center justify-center gap-1 rounded px-1 font-sans text-xs font-medium [&_svg:not([class*='size-'])]:size-3";
|
|
6256
|
-
var COMMAND_SHORTCUT_CLASS = "text-muted-foreground/70 ms-auto font-sans text-xs font-medium tracking-widest";
|
|
6257
|
-
function createCommandShortcut(options = {}, children = []) {
|
|
6258
|
-
const { class: extra, attrs, ...rest } = options;
|
|
6259
|
-
return el(
|
|
6260
|
-
"kbd",
|
|
6261
|
-
{
|
|
6262
|
-
...rest,
|
|
6263
|
-
class: cn(COMMAND_SHORTCUT_CLASS, extra),
|
|
6264
|
-
attrs: { "data-slot": "command-shortcut", ...attrs }
|
|
6265
|
-
},
|
|
6266
|
-
children
|
|
6267
|
-
);
|
|
6268
|
-
}
|
|
6269
|
-
function kbdTpl(text, className) {
|
|
6270
|
-
return html`<kbd class=${cn(KBD_CLASS, className)} data-slot="kbd"
|
|
6271
|
-
>${text}</kbd
|
|
6272
|
-
>`;
|
|
6273
|
-
}
|
|
6274
|
-
function commandShortcutTpl(text, className) {
|
|
6275
|
-
return html`<kbd
|
|
6276
|
-
class=${cn(COMMAND_SHORTCUT_CLASS, className)}
|
|
6277
|
-
data-slot="command-shortcut"
|
|
6278
|
-
>${text}</kbd
|
|
6279
|
-
>`;
|
|
6280
|
-
}
|
|
6281
|
-
|
|
6282
|
-
// src/browser/views/primitives/row.ts
|
|
6283
|
-
var LABEL_CLASS = "min-w-0 flex-1 truncate";
|
|
6284
|
-
var SUBTITLE_CLASS = "truncate text-xs text-muted-foreground";
|
|
6285
|
-
function fillRowWithHandle(host, content) {
|
|
6286
|
-
if (content.leading) host.append(content.leading);
|
|
6287
|
-
const label = el("span", { class: LABEL_CLASS, text: content.label });
|
|
6288
|
-
host.append(label);
|
|
6289
|
-
if (content.subtitle) {
|
|
6290
|
-
host.append(
|
|
6291
|
-
el("span", {
|
|
6292
|
-
class: SUBTITLE_CLASS,
|
|
6293
|
-
attrs: { "data-uidex-row-subtitle": "" },
|
|
6294
|
-
text: content.subtitle
|
|
6295
|
-
})
|
|
6296
|
-
);
|
|
6297
|
-
}
|
|
6298
|
-
if (content.trailing != null) {
|
|
6299
|
-
host.append(
|
|
6300
|
-
typeof content.trailing === "string" ? createCommandShortcut({ text: content.trailing }) : content.trailing
|
|
6301
|
-
);
|
|
6302
|
-
}
|
|
6303
|
-
return { label };
|
|
6304
|
-
}
|
|
6305
|
-
function rowTpl(content) {
|
|
6306
|
-
return html`
|
|
6307
|
-
${content.leading ?? nothing}
|
|
6308
|
-
<span class=${LABEL_CLASS}>${content.label}</span>
|
|
6309
|
-
${content.subtitle ? html`<span class=${SUBTITLE_CLASS} data-uidex-row-subtitle
|
|
6310
|
-
>${content.subtitle}</span
|
|
6311
|
-
>` : nothing}
|
|
6312
|
-
${content.trailing != null ? typeof content.trailing === "string" ? commandShortcutTpl(content.trailing) : content.trailing : nothing}
|
|
6313
|
-
`;
|
|
6314
|
-
}
|
|
6315
|
-
|
|
6316
|
-
// src/browser/views/primitives/entity-link.ts
|
|
6317
|
-
var ACTION_CLASS = cn(
|
|
6318
|
-
LIST_ITEM_CLASS,
|
|
6319
|
-
LIST_ITEM_INTERACTIVE_CLASS,
|
|
6320
|
-
"w-full cursor-pointer text-left font-normal"
|
|
6321
|
-
);
|
|
6322
|
-
function entityLinkTpl(options) {
|
|
6323
|
-
const { ctx, target, label, leading, class: extraClass } = options;
|
|
6324
|
-
const absent = isAbsentFromPage(target);
|
|
6325
|
-
const resolvedLabel = label ?? `${target.kind}: ${target.id}`;
|
|
6326
|
-
const onClick = () => ctx.views.navigate(target);
|
|
6327
|
-
const preview = () => {
|
|
6328
|
-
ctx.highlight.show(target, { color: KIND_STYLE[target.kind].color });
|
|
6329
|
-
};
|
|
6330
|
-
const restoreParent = () => {
|
|
6331
|
-
if (ctx.ref) {
|
|
6332
|
-
ctx.highlight.show(ctx.ref, { color: KIND_STYLE[ctx.ref.kind].color });
|
|
6333
|
-
} else {
|
|
6334
|
-
ctx.highlight.hide();
|
|
6335
|
-
}
|
|
6336
|
-
};
|
|
6337
|
-
return html`
|
|
6338
|
-
<button
|
|
6339
|
-
type="button"
|
|
6340
|
-
class=${cn(ACTION_CLASS, "w-full", absent && "opacity-50", extraClass)}
|
|
6341
|
-
data-slot="list-item-button"
|
|
6342
|
-
data-uidex-entity-link
|
|
6343
|
-
data-uidex-ref-kind=${target.kind}
|
|
6344
|
-
data-uidex-ref-id=${target.id}
|
|
6345
|
-
title=${absent ? "Not on this page" : ""}
|
|
6346
|
-
@click=${onClick}
|
|
6347
|
-
@mouseenter=${preview}
|
|
6348
|
-
@mouseleave=${restoreParent}
|
|
6349
|
-
@focus=${preview}
|
|
6350
|
-
@blur=${restoreParent}
|
|
6351
|
-
>
|
|
6352
|
-
${rowTpl({
|
|
6353
|
-
leading,
|
|
6354
|
-
label: resolvedLabel
|
|
6355
|
-
})}
|
|
6356
|
-
</button>
|
|
6357
|
-
`;
|
|
6358
|
-
}
|
|
6359
|
-
|
|
6360
5965
|
// src/browser/views/primitives/text.ts
|
|
6361
5966
|
var MUTED_CLASS = "text-sm text-muted-foreground";
|
|
6362
5967
|
var HEADING_CLASS = LIST_GROUP_LABEL_CLASS;
|
|
@@ -6368,7 +5973,20 @@ function headingTpl(text, className) {
|
|
|
6368
5973
|
return html`<h3 class=${cn(HEADING_CLASS, className)}>${text}</h3>`;
|
|
6369
5974
|
}
|
|
6370
5975
|
|
|
6371
|
-
// src/browser/views/render/detail.ts
|
|
5976
|
+
// src/browser/views/render/detail-actions.ts
|
|
5977
|
+
import {
|
|
5978
|
+
ArchiveX,
|
|
5979
|
+
Camera,
|
|
5980
|
+
ChevronDown,
|
|
5981
|
+
Copy,
|
|
5982
|
+
Highlighter as Highlighter2,
|
|
5983
|
+
Inbox,
|
|
5984
|
+
MessageCircleWarning,
|
|
5985
|
+
StickyNote as StickyNote2,
|
|
5986
|
+
TicketPlus,
|
|
5987
|
+
View,
|
|
5988
|
+
createElement as createLucideElement5
|
|
5989
|
+
} from "lucide";
|
|
6372
5990
|
var ICON_MAP = {
|
|
6373
5991
|
"archive-x": ArchiveX,
|
|
6374
5992
|
copy: Copy,
|
|
@@ -6384,23 +6002,6 @@ var ICON_MAP = {
|
|
|
6384
6002
|
function iconFor(icon2) {
|
|
6385
6003
|
return icon2 ? ICON_MAP[icon2] : null;
|
|
6386
6004
|
}
|
|
6387
|
-
function subtitleTpl(subtitle) {
|
|
6388
|
-
const text = subtitle.extra ? `${subtitle.rawId} \xB7 ${subtitle.extra}` : subtitle.rawId;
|
|
6389
|
-
return html`<p
|
|
6390
|
-
class=${cn("text-muted-foreground font-mono text-xs", "px-2")}
|
|
6391
|
-
data-uidex-detail-subtitle
|
|
6392
|
-
>
|
|
6393
|
-
${text}
|
|
6394
|
-
</p>`;
|
|
6395
|
-
}
|
|
6396
|
-
function notFoundTpl(ref2) {
|
|
6397
|
-
return html`<p
|
|
6398
|
-
class=${cn("text-muted-foreground text-sm", "p-4")}
|
|
6399
|
-
data-uidex-detail-missing
|
|
6400
|
-
>
|
|
6401
|
-
${ref2.kind}: ${ref2.id} not found in registry
|
|
6402
|
-
</p>`;
|
|
6403
|
-
}
|
|
6404
6005
|
function renderActions(actions, ctx, root, heading) {
|
|
6405
6006
|
const cleanups = [];
|
|
6406
6007
|
const buttons = [];
|
|
@@ -6511,6 +6112,169 @@ function renderActions(actions, ctx, root, heading) {
|
|
|
6511
6112
|
}
|
|
6512
6113
|
return { node: section, buttons, cleanup: composeCleanups(cleanups) };
|
|
6513
6114
|
}
|
|
6115
|
+
|
|
6116
|
+
// src/browser/views/render/detail-sections.ts
|
|
6117
|
+
import {
|
|
6118
|
+
html as staticHtml,
|
|
6119
|
+
literal
|
|
6120
|
+
} from "lit-html/static.js";
|
|
6121
|
+
|
|
6122
|
+
// src/browser/views/builder/filter.ts
|
|
6123
|
+
function normalizeQuery(query) {
|
|
6124
|
+
return query.trim().toLowerCase();
|
|
6125
|
+
}
|
|
6126
|
+
function matchesQuery(haystack, query) {
|
|
6127
|
+
const q = normalizeQuery(query);
|
|
6128
|
+
if (!q) return true;
|
|
6129
|
+
return haystack.toLowerCase().includes(q);
|
|
6130
|
+
}
|
|
6131
|
+
function filterEntities(entities, query) {
|
|
6132
|
+
const q = normalizeQuery(query);
|
|
6133
|
+
if (!q) return entities;
|
|
6134
|
+
return entities.filter((e) => {
|
|
6135
|
+
const name = displayName(e).toLowerCase();
|
|
6136
|
+
const id = entityKey(e).toLowerCase();
|
|
6137
|
+
return name.includes(q) || id.includes(q) || e.kind.toLowerCase().includes(q);
|
|
6138
|
+
});
|
|
6139
|
+
}
|
|
6140
|
+
function filterIds(ids, query) {
|
|
6141
|
+
const q = normalizeQuery(query);
|
|
6142
|
+
if (!q) return ids;
|
|
6143
|
+
return ids.filter((id) => id.toLowerCase().includes(q));
|
|
6144
|
+
}
|
|
6145
|
+
|
|
6146
|
+
// src/browser/views/primitives/entity-presence.ts
|
|
6147
|
+
var TOUCH_RESOLVE_KINDS = [
|
|
6148
|
+
"element",
|
|
6149
|
+
"widget",
|
|
6150
|
+
"region",
|
|
6151
|
+
"primitive"
|
|
6152
|
+
];
|
|
6153
|
+
function isAbsentFromPage(ref2, registry) {
|
|
6154
|
+
if (DOM_BACKED_KINDS.has(ref2.kind)) {
|
|
6155
|
+
return !resolveEntityElement(ref2);
|
|
6156
|
+
}
|
|
6157
|
+
if (ref2.kind === "flow" && registry) {
|
|
6158
|
+
const flow = registry.get("flow", ref2.id);
|
|
6159
|
+
if (!flow) return true;
|
|
6160
|
+
for (const touchId of flow.touches) {
|
|
6161
|
+
for (const kind of TOUCH_RESOLVE_KINDS) {
|
|
6162
|
+
const entity = registry.get(kind, touchId);
|
|
6163
|
+
if (entity && resolveEntityElement({ kind, id: touchId })) return false;
|
|
6164
|
+
}
|
|
6165
|
+
}
|
|
6166
|
+
return true;
|
|
6167
|
+
}
|
|
6168
|
+
return false;
|
|
6169
|
+
}
|
|
6170
|
+
|
|
6171
|
+
// src/browser/ui/kbd.ts
|
|
6172
|
+
var KBD_CLASS = "bg-muted text-muted-foreground pointer-events-none inline-flex h-5 min-w-5 select-none items-center justify-center gap-1 rounded px-1 font-sans text-xs font-medium [&_svg:not([class*='size-'])]:size-3";
|
|
6173
|
+
var COMMAND_SHORTCUT_CLASS = "text-muted-foreground/70 ms-auto font-sans text-xs font-medium tracking-widest";
|
|
6174
|
+
function createCommandShortcut(options = {}, children = []) {
|
|
6175
|
+
const { class: extra, attrs, ...rest } = options;
|
|
6176
|
+
return el(
|
|
6177
|
+
"kbd",
|
|
6178
|
+
{
|
|
6179
|
+
...rest,
|
|
6180
|
+
class: cn(COMMAND_SHORTCUT_CLASS, extra),
|
|
6181
|
+
attrs: { "data-slot": "command-shortcut", ...attrs }
|
|
6182
|
+
},
|
|
6183
|
+
children
|
|
6184
|
+
);
|
|
6185
|
+
}
|
|
6186
|
+
function kbdTpl(text, className) {
|
|
6187
|
+
return html`<kbd class=${cn(KBD_CLASS, className)} data-slot="kbd"
|
|
6188
|
+
>${text}</kbd
|
|
6189
|
+
>`;
|
|
6190
|
+
}
|
|
6191
|
+
function commandShortcutTpl(text, className) {
|
|
6192
|
+
return html`<kbd
|
|
6193
|
+
class=${cn(COMMAND_SHORTCUT_CLASS, className)}
|
|
6194
|
+
data-slot="command-shortcut"
|
|
6195
|
+
>${text}</kbd
|
|
6196
|
+
>`;
|
|
6197
|
+
}
|
|
6198
|
+
|
|
6199
|
+
// src/browser/views/primitives/row.ts
|
|
6200
|
+
var LABEL_CLASS = "min-w-0 flex-1 truncate";
|
|
6201
|
+
var SUBTITLE_CLASS = "truncate text-xs text-muted-foreground";
|
|
6202
|
+
function fillRowWithHandle(host, content) {
|
|
6203
|
+
if (content.leading) host.append(content.leading);
|
|
6204
|
+
const label = el("span", { class: LABEL_CLASS, text: content.label });
|
|
6205
|
+
host.append(label);
|
|
6206
|
+
if (content.subtitle) {
|
|
6207
|
+
host.append(
|
|
6208
|
+
el("span", {
|
|
6209
|
+
class: SUBTITLE_CLASS,
|
|
6210
|
+
attrs: { "data-uidex-row-subtitle": "" },
|
|
6211
|
+
text: content.subtitle
|
|
6212
|
+
})
|
|
6213
|
+
);
|
|
6214
|
+
}
|
|
6215
|
+
if (content.trailing != null) {
|
|
6216
|
+
host.append(
|
|
6217
|
+
typeof content.trailing === "string" ? createCommandShortcut({ text: content.trailing }) : content.trailing
|
|
6218
|
+
);
|
|
6219
|
+
}
|
|
6220
|
+
return { label };
|
|
6221
|
+
}
|
|
6222
|
+
function rowTpl(content) {
|
|
6223
|
+
return html`
|
|
6224
|
+
${content.leading ?? nothing}
|
|
6225
|
+
<span class=${LABEL_CLASS}>${content.label}</span>
|
|
6226
|
+
${content.subtitle ? html`<span class=${SUBTITLE_CLASS} data-uidex-row-subtitle
|
|
6227
|
+
>${content.subtitle}</span
|
|
6228
|
+
>` : nothing}
|
|
6229
|
+
${content.trailing != null ? typeof content.trailing === "string" ? commandShortcutTpl(content.trailing) : content.trailing : nothing}
|
|
6230
|
+
`;
|
|
6231
|
+
}
|
|
6232
|
+
|
|
6233
|
+
// src/browser/views/primitives/entity-link.ts
|
|
6234
|
+
var ACTION_CLASS = cn(
|
|
6235
|
+
LIST_ITEM_CLASS,
|
|
6236
|
+
LIST_ITEM_INTERACTIVE_CLASS,
|
|
6237
|
+
"w-full cursor-pointer text-left font-normal"
|
|
6238
|
+
);
|
|
6239
|
+
function entityLinkTpl(options) {
|
|
6240
|
+
const { ctx, target, label, leading, class: extraClass } = options;
|
|
6241
|
+
const absent = isAbsentFromPage(target);
|
|
6242
|
+
const resolvedLabel = label ?? `${target.kind}: ${target.id}`;
|
|
6243
|
+
const onClick = () => ctx.views.navigate(target);
|
|
6244
|
+
const preview = () => {
|
|
6245
|
+
ctx.highlight.show(target, { color: KIND_STYLE[target.kind].color });
|
|
6246
|
+
};
|
|
6247
|
+
const restoreParent = () => {
|
|
6248
|
+
if (ctx.ref) {
|
|
6249
|
+
ctx.highlight.show(ctx.ref, { color: KIND_STYLE[ctx.ref.kind].color });
|
|
6250
|
+
} else {
|
|
6251
|
+
ctx.highlight.hide();
|
|
6252
|
+
}
|
|
6253
|
+
};
|
|
6254
|
+
return html`
|
|
6255
|
+
<button
|
|
6256
|
+
type="button"
|
|
6257
|
+
class=${cn(ACTION_CLASS, "w-full", absent && "opacity-50", extraClass)}
|
|
6258
|
+
data-slot="list-item-button"
|
|
6259
|
+
data-uidex-entity-link
|
|
6260
|
+
data-uidex-ref-kind=${target.kind}
|
|
6261
|
+
data-uidex-ref-id=${target.id}
|
|
6262
|
+
title=${absent ? "Not on this page" : ""}
|
|
6263
|
+
@click=${onClick}
|
|
6264
|
+
@mouseenter=${preview}
|
|
6265
|
+
@mouseleave=${restoreParent}
|
|
6266
|
+
@focus=${preview}
|
|
6267
|
+
@blur=${restoreParent}
|
|
6268
|
+
>
|
|
6269
|
+
${rowTpl({
|
|
6270
|
+
leading,
|
|
6271
|
+
label: resolvedLabel
|
|
6272
|
+
})}
|
|
6273
|
+
</button>
|
|
6274
|
+
`;
|
|
6275
|
+
}
|
|
6276
|
+
|
|
6277
|
+
// src/browser/views/render/detail-sections.ts
|
|
6514
6278
|
function entityListItems(ctx, entities) {
|
|
6515
6279
|
return html`${entities.map((entity) => {
|
|
6516
6280
|
const eRef = { kind: entity.kind, id: entityKey(entity) };
|
|
@@ -6524,71 +6288,29 @@ function entityListItems(ctx, entities) {
|
|
|
6524
6288
|
</li>`;
|
|
6525
6289
|
})}`;
|
|
6526
6290
|
}
|
|
6527
|
-
|
|
6528
|
-
|
|
6529
|
-
|
|
6530
|
-
|
|
6531
|
-
|
|
6532
|
-
|
|
6533
|
-
|
|
6534
|
-
|
|
6535
|
-
|
|
6536
|
-
`;
|
|
6537
|
-
}
|
|
6538
|
-
function usedByListTpl(ctx, label, entities) {
|
|
6539
|
-
if (entities.length === 0) return null;
|
|
6540
|
-
return html`
|
|
6541
|
-
<section class="flex flex-col" data-uidex-detail-used-by>
|
|
6542
|
-
${headingTpl(label)}
|
|
6543
|
-
<ul class="flex flex-col">
|
|
6544
|
-
${entityListItems(ctx, entities)}
|
|
6545
|
-
</ul>
|
|
6546
|
-
</section>
|
|
6547
|
-
`;
|
|
6548
|
-
}
|
|
6549
|
-
function flowListTpl(ctx, flows) {
|
|
6550
|
-
if (flows.length === 0) return null;
|
|
6551
|
-
return html`
|
|
6552
|
-
<section class="flex flex-col" data-uidex-detail-flows>
|
|
6553
|
-
${headingTpl(SECTION_LABELS.flows)}
|
|
6554
|
-
<ul class="flex flex-col">
|
|
6555
|
-
${flows.map(
|
|
6556
|
-
(flow) => html`<li>
|
|
6557
|
-
${entityLinkTpl({
|
|
6558
|
-
ctx,
|
|
6559
|
-
target: { kind: "flow", id: flow.id },
|
|
6560
|
-
label: displayName(flow),
|
|
6561
|
-
leading: kindIconTileTpl("flow")
|
|
6562
|
-
})}
|
|
6563
|
-
</li>`
|
|
6564
|
-
)}
|
|
6565
|
-
</ul>
|
|
6566
|
-
</section>
|
|
6567
|
-
`;
|
|
6568
|
-
}
|
|
6569
|
-
function touchesTpl(ctx, entities, query) {
|
|
6291
|
+
var DETAIL_SECTION_ATTRS = {
|
|
6292
|
+
composes: literal`data-uidex-detail-composes`,
|
|
6293
|
+
"used-by": literal`data-uidex-detail-used-by`,
|
|
6294
|
+
flows: literal`data-uidex-detail-flows`,
|
|
6295
|
+
touches: literal`data-uidex-detail-touches`
|
|
6296
|
+
};
|
|
6297
|
+
function entitySectionTpl(ctx, opts) {
|
|
6298
|
+
const { label, entities, dataAttr, emptyText } = opts;
|
|
6299
|
+
const attr = DETAIL_SECTION_ATTRS[dataAttr];
|
|
6570
6300
|
if (entities.length === 0) {
|
|
6571
|
-
return
|
|
6572
|
-
|
|
6573
|
-
|
|
6574
|
-
${
|
|
6301
|
+
if (emptyText === void 0) return null;
|
|
6302
|
+
return staticHtml`
|
|
6303
|
+
<section class="flex flex-col gap-2" ${attr}>
|
|
6304
|
+
${headingTpl(label)}
|
|
6305
|
+
${mutedTextTpl(emptyText)}
|
|
6575
6306
|
</section>
|
|
6576
6307
|
`;
|
|
6577
6308
|
}
|
|
6578
|
-
return
|
|
6579
|
-
<section class="flex flex-col"
|
|
6580
|
-
${headingTpl(
|
|
6309
|
+
return staticHtml`
|
|
6310
|
+
<section class="flex flex-col" ${attr}>
|
|
6311
|
+
${headingTpl(label)}
|
|
6581
6312
|
<ul class="flex flex-col">
|
|
6582
|
-
${entities
|
|
6583
|
-
(entity) => html`<li>
|
|
6584
|
-
${entityLinkTpl({
|
|
6585
|
-
ctx,
|
|
6586
|
-
target: { kind: entity.kind, id: entityKey(entity) },
|
|
6587
|
-
label: displayName(entity),
|
|
6588
|
-
leading: kindIconTileTpl(entity.kind)
|
|
6589
|
-
})}
|
|
6590
|
-
</li>`
|
|
6591
|
-
)}
|
|
6313
|
+
${entityListItems(ctx, entities)}
|
|
6592
6314
|
</ul>
|
|
6593
6315
|
</section>
|
|
6594
6316
|
`;
|
|
@@ -6745,6 +6467,20 @@ function screenshotTpl(url) {
|
|
|
6745
6467
|
</section>
|
|
6746
6468
|
`;
|
|
6747
6469
|
}
|
|
6470
|
+
function lazyScreenshotEl(load) {
|
|
6471
|
+
const holder = document.createElement("div");
|
|
6472
|
+
holder.hidden = true;
|
|
6473
|
+
void load().then(
|
|
6474
|
+
(url) => {
|
|
6475
|
+
if (!url) return;
|
|
6476
|
+
render(screenshotTpl(url), holder);
|
|
6477
|
+
holder.hidden = false;
|
|
6478
|
+
},
|
|
6479
|
+
() => {
|
|
6480
|
+
}
|
|
6481
|
+
);
|
|
6482
|
+
return holder;
|
|
6483
|
+
}
|
|
6748
6484
|
function metadataListTpl(entries) {
|
|
6749
6485
|
return html`
|
|
6750
6486
|
<div
|
|
@@ -6775,28 +6511,30 @@ function sectionTpl(section, ctx, query) {
|
|
|
6775
6511
|
return acceptanceChecklistTpl(section.items);
|
|
6776
6512
|
}
|
|
6777
6513
|
case "composes":
|
|
6778
|
-
return
|
|
6779
|
-
|
|
6780
|
-
section.
|
|
6781
|
-
|
|
6782
|
-
);
|
|
6514
|
+
return entitySectionTpl(ctx, {
|
|
6515
|
+
label: section.label,
|
|
6516
|
+
entities: section.filterable ? filterEntities(section.entities, query) : section.entities,
|
|
6517
|
+
dataAttr: "composes"
|
|
6518
|
+
});
|
|
6783
6519
|
case "used-by":
|
|
6784
|
-
return
|
|
6785
|
-
|
|
6786
|
-
section.
|
|
6787
|
-
|
|
6788
|
-
);
|
|
6520
|
+
return entitySectionTpl(ctx, {
|
|
6521
|
+
label: section.label,
|
|
6522
|
+
entities: section.filterable ? filterEntities(section.entities, query) : section.entities,
|
|
6523
|
+
dataAttr: "used-by"
|
|
6524
|
+
});
|
|
6789
6525
|
case "flows":
|
|
6790
|
-
return
|
|
6791
|
-
|
|
6792
|
-
section.filterable ? filterEntities(section.flows, query) : section.flows
|
|
6793
|
-
|
|
6526
|
+
return entitySectionTpl(ctx, {
|
|
6527
|
+
label: SECTION_LABELS.flows,
|
|
6528
|
+
entities: section.filterable ? filterEntities(section.flows, query) : section.flows,
|
|
6529
|
+
dataAttr: "flows"
|
|
6530
|
+
});
|
|
6794
6531
|
case "touches":
|
|
6795
|
-
return
|
|
6796
|
-
|
|
6797
|
-
section.filterable ? filterEntities(section.entities, query) : section.entities,
|
|
6798
|
-
|
|
6799
|
-
|
|
6532
|
+
return entitySectionTpl(ctx, {
|
|
6533
|
+
label: SECTION_LABELS.touches,
|
|
6534
|
+
entities: section.filterable ? filterEntities(section.entities, query) : section.entities,
|
|
6535
|
+
dataAttr: "touches",
|
|
6536
|
+
emptyText: query ? "No matches" : "No entities touched"
|
|
6537
|
+
});
|
|
6800
6538
|
case "steps":
|
|
6801
6539
|
return stepsTpl(
|
|
6802
6540
|
ctx,
|
|
@@ -6808,11 +6546,32 @@ function sectionTpl(section, ctx, query) {
|
|
|
6808
6546
|
section.filterable ? filterIds(section.paths, query) : section.paths
|
|
6809
6547
|
);
|
|
6810
6548
|
case "screenshot":
|
|
6811
|
-
return screenshotTpl(section.url);
|
|
6549
|
+
if (section.url) return screenshotTpl(section.url);
|
|
6550
|
+
if (section.load) return html`${lazyScreenshotEl(section.load)}`;
|
|
6551
|
+
return null;
|
|
6812
6552
|
case "metadata":
|
|
6813
6553
|
return section.entries.length > 0 ? metadataListTpl(section.entries) : null;
|
|
6814
6554
|
}
|
|
6815
6555
|
}
|
|
6556
|
+
|
|
6557
|
+
// src/browser/views/render/detail.ts
|
|
6558
|
+
function subtitleTpl(subtitle) {
|
|
6559
|
+
const text = subtitle.extra ? `${subtitle.rawId} \xB7 ${subtitle.extra}` : subtitle.rawId;
|
|
6560
|
+
return html`<p
|
|
6561
|
+
class=${cn("text-muted-foreground font-mono text-xs", "px-2")}
|
|
6562
|
+
data-uidex-detail-subtitle
|
|
6563
|
+
>
|
|
6564
|
+
${text}
|
|
6565
|
+
</p>`;
|
|
6566
|
+
}
|
|
6567
|
+
function notFoundTpl(ref2) {
|
|
6568
|
+
return html`<p
|
|
6569
|
+
class=${cn("text-muted-foreground text-sm", "p-4")}
|
|
6570
|
+
data-uidex-detail-missing
|
|
6571
|
+
>
|
|
6572
|
+
${ref2.kind}: ${ref2.id} not found in registry
|
|
6573
|
+
</p>`;
|
|
6574
|
+
}
|
|
6816
6575
|
function hasFilterableSections(sections) {
|
|
6817
6576
|
return sections.some((s) => "filterable" in s && s.filterable === true);
|
|
6818
6577
|
}
|
|
@@ -6877,7 +6636,10 @@ function renderDetailSurface(surface, ctx, root) {
|
|
|
6877
6636
|
>
|
|
6878
6637
|
${surface.title}
|
|
6879
6638
|
</h2>` : nothing}
|
|
6880
|
-
<span class="ml-auto"
|
|
6639
|
+
<span class="ml-auto flex items-center gap-1">
|
|
6640
|
+
${surface.unregistered ? badgeTpl("Unregistered", { variant: "warning", size: "sm" }) : nothing}
|
|
6641
|
+
${kindBadgeTpl(surface.entityKind)}
|
|
6642
|
+
</span>
|
|
6881
6643
|
</div>
|
|
6882
6644
|
${surface.subtitle ? subtitleTpl(surface.subtitle) : nothing}
|
|
6883
6645
|
<div
|
|
@@ -7170,6 +6932,34 @@ function createScreenshotLightbox(trigger, dataUrl, options) {
|
|
|
7170
6932
|
};
|
|
7171
6933
|
}
|
|
7172
6934
|
|
|
6935
|
+
// src/browser/ui/button.ts
|
|
6936
|
+
var buttonBase = "focus-visible:ring-ring focus-visible:ring-offset-background disabled:opacity-60 relative inline-flex shrink-0 cursor-pointer items-center justify-center gap-2 whitespace-nowrap rounded-lg border text-sm font-medium outline-none transition-shadow focus-visible:ring-2 focus-visible:ring-offset-1 disabled:pointer-events-none [&_svg:not([class*='size-'])]:size-4 [&_svg:not([class*='opacity-'])]:opacity-80 [&_svg]:pointer-events-none [&_svg]:shrink-0";
|
|
6937
|
+
var buttonVariants = cva(buttonBase, {
|
|
6938
|
+
defaultVariants: { size: "default", variant: "default" },
|
|
6939
|
+
variants: {
|
|
6940
|
+
size: {
|
|
6941
|
+
default: "h-8 px-3",
|
|
6942
|
+
sm: "h-7 gap-1.5 px-2.5",
|
|
6943
|
+
xs: "h-6 gap-1 rounded-md px-2 text-xs",
|
|
6944
|
+
lg: "h-9 px-3.5",
|
|
6945
|
+
xl: "h-10 px-4 text-base",
|
|
6946
|
+
icon: "size-8",
|
|
6947
|
+
"icon-sm": "size-7",
|
|
6948
|
+
"icon-lg": "size-9",
|
|
6949
|
+
"icon-xs": "size-6 rounded-md"
|
|
6950
|
+
},
|
|
6951
|
+
variant: {
|
|
6952
|
+
default: "border-primary bg-primary text-primary-foreground shadow-xs hover:bg-primary/90",
|
|
6953
|
+
destructive: "border-destructive bg-destructive shadow-xs hover:bg-destructive/90 text-white",
|
|
6954
|
+
"destructive-outline": "border-input bg-popover text-destructive-foreground shadow-xs/5 hover:border-destructive/30 hover:bg-destructive/5 dark:bg-input/30",
|
|
6955
|
+
ghost: "text-foreground hover:bg-accent hover:text-accent-foreground border-transparent",
|
|
6956
|
+
link: "text-foreground border-transparent underline-offset-4 hover:underline",
|
|
6957
|
+
outline: "border-input bg-popover text-foreground shadow-xs/5 hover:bg-accent hover:text-accent-foreground dark:bg-input/30",
|
|
6958
|
+
secondary: "bg-secondary text-secondary-foreground hover:bg-secondary/90 border-transparent"
|
|
6959
|
+
}
|
|
6960
|
+
}
|
|
6961
|
+
});
|
|
6962
|
+
|
|
7173
6963
|
// src/browser/views/render/form.ts
|
|
7174
6964
|
var fieldSeq = 0;
|
|
7175
6965
|
var nextFieldId = () => `uidex-field-${++fieldSeq}`;
|
|
@@ -7366,9 +7156,9 @@ function iconMediaTpl(iconTpl) {
|
|
|
7366
7156
|
</div>
|
|
7367
7157
|
`;
|
|
7368
7158
|
}
|
|
7369
|
-
function loadingViewTpl() {
|
|
7159
|
+
function loadingViewTpl(rootRef) {
|
|
7370
7160
|
return html`
|
|
7371
|
-
<div class=${EMPTY_ROOT} aria-live="polite" hidden>
|
|
7161
|
+
<div class=${EMPTY_ROOT} aria-live="polite" hidden ${ref(rootRef)}>
|
|
7372
7162
|
${iconMediaTpl(icon(Loader2, "animate-spin"))}
|
|
7373
7163
|
<div class="flex max-w-sm flex-col items-center text-center">
|
|
7374
7164
|
<div class=${SKELETON + " h-6 w-36 rounded-md"}></div>
|
|
@@ -7381,42 +7171,47 @@ function loadingViewTpl() {
|
|
|
7381
7171
|
</div>
|
|
7382
7172
|
`;
|
|
7383
7173
|
}
|
|
7384
|
-
function successViewTpl() {
|
|
7174
|
+
function successViewTpl(refs) {
|
|
7385
7175
|
return html`
|
|
7386
|
-
<div class=${EMPTY_ROOT} hidden data-uidex-success-view>
|
|
7176
|
+
<div class=${EMPTY_ROOT} hidden data-uidex-success-view ${ref(refs.root)}>
|
|
7387
7177
|
${iconMediaTpl(icon(CircleCheck))}
|
|
7388
7178
|
<div class="flex max-w-sm flex-col items-center text-center">
|
|
7389
7179
|
<div
|
|
7390
7180
|
class="font-heading text-xl font-semibold"
|
|
7391
7181
|
data-uidex-success-title
|
|
7182
|
+
${ref(refs.title)}
|
|
7392
7183
|
></div>
|
|
7393
7184
|
</div>
|
|
7394
7185
|
<div
|
|
7395
7186
|
class="flex w-full min-w-0 max-w-sm flex-col items-center gap-4 text-balance text-sm"
|
|
7396
7187
|
data-uidex-success-actions
|
|
7188
|
+
${ref(refs.actions)}
|
|
7397
7189
|
>
|
|
7398
7190
|
<a
|
|
7399
7191
|
class=${buttonVariants({ variant: "outline", size: "sm" })}
|
|
7400
7192
|
target="_blank"
|
|
7401
7193
|
rel="noreferrer"
|
|
7402
7194
|
data-uidex-success-link
|
|
7195
|
+
${ref(refs.link)}
|
|
7403
7196
|
></a>
|
|
7404
7197
|
</div>
|
|
7405
7198
|
</div>
|
|
7406
7199
|
`;
|
|
7407
7200
|
}
|
|
7408
|
-
function errorViewTpl() {
|
|
7201
|
+
function errorViewTpl(refs) {
|
|
7409
7202
|
return html`
|
|
7410
|
-
<div class=${EMPTY_ROOT} hidden data-uidex-error-view>
|
|
7203
|
+
<div class=${EMPTY_ROOT} hidden data-uidex-error-view ${ref(refs.root)}>
|
|
7411
7204
|
${iconMediaTpl(icon(CircleX))}
|
|
7412
7205
|
<div class="flex max-w-sm flex-col items-center gap-1 text-center">
|
|
7413
7206
|
<div
|
|
7414
7207
|
class="font-heading text-xl font-semibold"
|
|
7415
7208
|
data-uidex-error-title
|
|
7209
|
+
${ref(refs.title)}
|
|
7416
7210
|
></div>
|
|
7417
7211
|
<p
|
|
7418
7212
|
class="text-muted-foreground text-sm"
|
|
7419
7213
|
data-uidex-error-description
|
|
7214
|
+
${ref(refs.description)}
|
|
7420
7215
|
></p>
|
|
7421
7216
|
</div>
|
|
7422
7217
|
<div
|
|
@@ -7427,6 +7222,7 @@ function errorViewTpl() {
|
|
|
7427
7222
|
class=${buttonVariants({ variant: "outline", size: "sm" })}
|
|
7428
7223
|
data-slot="button"
|
|
7429
7224
|
data-uidex-retry-button
|
|
7225
|
+
${ref(refs.retry)}
|
|
7430
7226
|
>
|
|
7431
7227
|
Try Again
|
|
7432
7228
|
</button>
|
|
@@ -7468,8 +7264,15 @@ function renderFormSurface(surface, ctx, root) {
|
|
|
7468
7264
|
});
|
|
7469
7265
|
}
|
|
7470
7266
|
const formRef = createRef();
|
|
7471
|
-
const
|
|
7472
|
-
const
|
|
7267
|
+
const loadingRef = createRef();
|
|
7268
|
+
const successRef = createRef();
|
|
7269
|
+
const successTitleRef = createRef();
|
|
7270
|
+
const successLinkRef = createRef();
|
|
7271
|
+
const successActionsRef = createRef();
|
|
7272
|
+
const errorRef = createRef();
|
|
7273
|
+
const errorTitleRef = createRef();
|
|
7274
|
+
const errorDescriptionRef = createRef();
|
|
7275
|
+
const retryRef = createRef();
|
|
7473
7276
|
render(
|
|
7474
7277
|
html`
|
|
7475
7278
|
<section
|
|
@@ -7484,7 +7287,19 @@ function renderFormSurface(surface, ctx, root) {
|
|
|
7484
7287
|
novalidate
|
|
7485
7288
|
data-uidex-form=${surface.id}
|
|
7486
7289
|
></form>
|
|
7487
|
-
${loadingViewTpl()}
|
|
7290
|
+
${loadingViewTpl(loadingRef)}
|
|
7291
|
+
${successViewTpl({
|
|
7292
|
+
root: successRef,
|
|
7293
|
+
title: successTitleRef,
|
|
7294
|
+
link: successLinkRef,
|
|
7295
|
+
actions: successActionsRef
|
|
7296
|
+
})}
|
|
7297
|
+
${errorViewTpl({
|
|
7298
|
+
root: errorRef,
|
|
7299
|
+
title: errorTitleRef,
|
|
7300
|
+
description: errorDescriptionRef,
|
|
7301
|
+
retry: retryRef
|
|
7302
|
+
})}
|
|
7488
7303
|
</section>
|
|
7489
7304
|
`,
|
|
7490
7305
|
root
|
|
@@ -7514,32 +7329,15 @@ function renderFormSurface(surface, ctx, root) {
|
|
|
7514
7329
|
}
|
|
7515
7330
|
});
|
|
7516
7331
|
form.append(status);
|
|
7517
|
-
const
|
|
7518
|
-
|
|
7519
|
-
|
|
7520
|
-
const
|
|
7521
|
-
const
|
|
7522
|
-
|
|
7523
|
-
|
|
7524
|
-
const
|
|
7525
|
-
|
|
7526
|
-
);
|
|
7527
|
-
const successLink = sectionEl.querySelector(
|
|
7528
|
-
"[data-uidex-success-link]"
|
|
7529
|
-
);
|
|
7530
|
-
const successActions = successLink.parentElement;
|
|
7531
|
-
const errorView = sectionEl.querySelector(
|
|
7532
|
-
"[data-uidex-error-view]"
|
|
7533
|
-
);
|
|
7534
|
-
const errorTitle = sectionEl.querySelector(
|
|
7535
|
-
"[data-uidex-error-title]"
|
|
7536
|
-
);
|
|
7537
|
-
const errorDescription = sectionEl.querySelector(
|
|
7538
|
-
"[data-uidex-error-description]"
|
|
7539
|
-
);
|
|
7540
|
-
const retryButton = sectionEl.querySelector(
|
|
7541
|
-
"[data-uidex-retry-button]"
|
|
7542
|
-
);
|
|
7332
|
+
const loadingView = loadingRef.value;
|
|
7333
|
+
const successView = successRef.value;
|
|
7334
|
+
const successTitle = successTitleRef.value;
|
|
7335
|
+
const successLink = successLinkRef.value;
|
|
7336
|
+
const successActions = successActionsRef.value;
|
|
7337
|
+
const errorView = errorRef.value;
|
|
7338
|
+
const errorTitle = errorTitleRef.value;
|
|
7339
|
+
const errorDescription = errorDescriptionRef.value;
|
|
7340
|
+
const retryButton = retryRef.value;
|
|
7543
7341
|
function clearAllFieldErrors() {
|
|
7544
7342
|
for (const f of fields) f.setError(null);
|
|
7545
7343
|
}
|
|
@@ -7940,7 +7738,7 @@ function defaultFilter(item, query) {
|
|
|
7940
7738
|
function rowTag(item) {
|
|
7941
7739
|
return item.tag ?? item.value;
|
|
7942
7740
|
}
|
|
7943
|
-
function resolveLeadingTpl(item
|
|
7741
|
+
function resolveLeadingTpl(item) {
|
|
7944
7742
|
if (item.entityChip) return kindIconTileTpl(item.entityChip.entity.kind);
|
|
7945
7743
|
if (item.leading) {
|
|
7946
7744
|
const node = item.leading();
|
|
@@ -8045,7 +7843,7 @@ function buildItemsDom(surface, ctx, filteredItems, allByValue, content) {
|
|
|
8045
7843
|
data-uidex-item-value=${item.value}
|
|
8046
7844
|
>
|
|
8047
7845
|
${rowTpl({
|
|
8048
|
-
leading: resolveLeadingTpl(item
|
|
7846
|
+
leading: resolveLeadingTpl(item),
|
|
8049
7847
|
label: item.label,
|
|
8050
7848
|
subtitle: item.subtitle,
|
|
8051
7849
|
trailing: item.trailing ?? item.shortcut
|
|
@@ -8090,7 +7888,7 @@ function renderListSurface(surface, ctx, root) {
|
|
|
8090
7888
|
return root.ownerDocument ?? document;
|
|
8091
7889
|
};
|
|
8092
7890
|
const hasDefault = surface.defaultHighlight !== void 0 && allByValue.has(surface.defaultHighlight);
|
|
8093
|
-
const {
|
|
7891
|
+
const { scrollRoot, viewport, content } = renderShell(surface, root);
|
|
8094
7892
|
let maps = buildItemsDom(surface, ctx, filteredItems, allByValue, content);
|
|
8095
7893
|
const controller = createListController({
|
|
8096
7894
|
surfaceId: surface.id,
|
|
@@ -8786,52 +8584,16 @@ function sameRef2(a, b) {
|
|
|
8786
8584
|
if (a === null || b === null) return false;
|
|
8787
8585
|
return a.kind === b.kind && a.id === b.id;
|
|
8788
8586
|
}
|
|
8789
|
-
function
|
|
8790
|
-
|
|
8791
|
-
if (!h) return [];
|
|
8792
|
-
if (typeof h === "function") {
|
|
8793
|
-
try {
|
|
8794
|
-
return h(ctx) ?? [];
|
|
8795
|
-
} catch (err) {
|
|
8796
|
-
console.error(`[uidex] view "${view.id}" hints() threw`, err);
|
|
8797
|
-
return [];
|
|
8798
|
-
}
|
|
8799
|
-
}
|
|
8800
|
-
return h;
|
|
8801
|
-
}
|
|
8802
|
-
function resolveTitle(view, ctx) {
|
|
8803
|
-
const t = view.title;
|
|
8804
|
-
if (!t) return "";
|
|
8805
|
-
if (typeof t === "function") {
|
|
8806
|
-
try {
|
|
8807
|
-
return t(ctx) ?? "";
|
|
8808
|
-
} catch (err) {
|
|
8809
|
-
console.error(`[uidex] view "${view.id}" title() threw`, err);
|
|
8810
|
-
return "";
|
|
8811
|
-
}
|
|
8812
|
-
}
|
|
8813
|
-
return t;
|
|
8814
|
-
}
|
|
8815
|
-
function resolveActions(view, ctx, globalActions) {
|
|
8816
|
-
const result = [];
|
|
8817
|
-
const fn = view.actions;
|
|
8818
|
-
if (fn) {
|
|
8819
|
-
try {
|
|
8820
|
-
const viewActions2 = fn(ctx) ?? [];
|
|
8821
|
-
result.push(...viewActions2);
|
|
8822
|
-
} catch (err) {
|
|
8823
|
-
console.error(`[uidex] view "${view.id}" actions() threw`, err);
|
|
8824
|
-
}
|
|
8825
|
-
}
|
|
8826
|
-
if (globalActions) {
|
|
8587
|
+
function resolveProp(view, ctx, value, propName, fallback) {
|
|
8588
|
+
if (typeof value === "function") {
|
|
8827
8589
|
try {
|
|
8828
|
-
|
|
8829
|
-
result.push(...globals);
|
|
8590
|
+
return value(ctx) ?? fallback;
|
|
8830
8591
|
} catch (err) {
|
|
8831
|
-
console.error(`[uidex]
|
|
8592
|
+
console.error(`[uidex] view "${view.id}" ${propName}() threw`, err);
|
|
8593
|
+
return fallback;
|
|
8832
8594
|
}
|
|
8833
8595
|
}
|
|
8834
|
-
return
|
|
8596
|
+
return value ?? fallback;
|
|
8835
8597
|
}
|
|
8836
8598
|
function createViewStack(options) {
|
|
8837
8599
|
const { container, views, session, registry, highlight } = options;
|
|
@@ -8899,39 +8661,40 @@ function createViewStack(options) {
|
|
|
8899
8661
|
color: KIND_STYLE[top.ctx.ref.kind].color
|
|
8900
8662
|
});
|
|
8901
8663
|
}
|
|
8902
|
-
function
|
|
8903
|
-
if (!shell) return;
|
|
8904
|
-
const top = mounted[mounted.length - 1];
|
|
8905
|
-
if (!top) return;
|
|
8664
|
+
function updateNavButtons(shell2, top) {
|
|
8906
8665
|
const atRoot = mounted.length <= 1 && top.view.id === "command-palette";
|
|
8907
|
-
|
|
8908
|
-
|
|
8666
|
+
shell2.backBtn.hidden = atRoot;
|
|
8667
|
+
shell2.searchIcon.hidden = !atRoot;
|
|
8668
|
+
}
|
|
8669
|
+
function updateTitle(shell2, top) {
|
|
8909
8670
|
const searchable = top.view.searchable !== false;
|
|
8910
|
-
|
|
8911
|
-
const titleText = searchable ? "" :
|
|
8912
|
-
|
|
8913
|
-
|
|
8914
|
-
|
|
8671
|
+
shell2.searchInput.hidden = !searchable;
|
|
8672
|
+
const titleText = searchable ? "" : resolveProp(top.view, top.ctx, top.view.title, "title", "");
|
|
8673
|
+
shell2.headerTitle.textContent = titleText;
|
|
8674
|
+
shell2.headerTitle.hidden = searchable || !titleText;
|
|
8675
|
+
}
|
|
8676
|
+
function updateFooterChip(shell2, top) {
|
|
8677
|
+
shell2.footerLeft.replaceChildren();
|
|
8915
8678
|
const refEntity = top.ctx.ref ? top.ctx.registry.get(top.ctx.ref.kind, top.ctx.ref.id) : null;
|
|
8916
8679
|
if (refEntity) {
|
|
8917
|
-
|
|
8680
|
+
shell2.footerLeft.append(
|
|
8918
8681
|
renderKindChip({
|
|
8919
8682
|
entity: refEntity,
|
|
8920
8683
|
withKindName: true
|
|
8921
8684
|
})
|
|
8922
8685
|
);
|
|
8923
8686
|
} else {
|
|
8924
|
-
|
|
8687
|
+
shell2.footerLeft.append(shell2.logo);
|
|
8925
8688
|
}
|
|
8926
|
-
|
|
8927
|
-
|
|
8928
|
-
|
|
8929
|
-
|
|
8930
|
-
|
|
8931
|
-
|
|
8932
|
-
|
|
8933
|
-
|
|
8934
|
-
);
|
|
8689
|
+
}
|
|
8690
|
+
function buildEnterHint(top, footerItems) {
|
|
8691
|
+
const enterHint = resolveProp(
|
|
8692
|
+
top.view,
|
|
8693
|
+
top.ctx,
|
|
8694
|
+
top.view.hints,
|
|
8695
|
+
"hints",
|
|
8696
|
+
[]
|
|
8697
|
+
).find((h) => h.key.includes("\u21B5"));
|
|
8935
8698
|
const src = top.mounted.submitIntent;
|
|
8936
8699
|
if (src) {
|
|
8937
8700
|
const key = enterHint?.key ?? "\u21B5";
|
|
@@ -8952,28 +8715,52 @@ function createViewStack(options) {
|
|
|
8952
8715
|
} else if (enterHint) {
|
|
8953
8716
|
footerItems.push(createHint(enterHint.key, enterHint.label));
|
|
8954
8717
|
}
|
|
8718
|
+
}
|
|
8719
|
+
function buildActions(shell2, top, footerItems) {
|
|
8955
8720
|
const actionsDivider = createFooterDivider();
|
|
8956
|
-
const viewActions2 =
|
|
8721
|
+
const viewActions2 = resolveProp(
|
|
8722
|
+
top.view,
|
|
8723
|
+
top.ctx,
|
|
8724
|
+
top.view.actions,
|
|
8725
|
+
"actions",
|
|
8726
|
+
[]
|
|
8727
|
+
);
|
|
8957
8728
|
const hlSrc = top.mounted.highlightActions;
|
|
8958
8729
|
const syncActions = () => {
|
|
8959
8730
|
const hlActions = hlSrc?.get() ?? [];
|
|
8960
8731
|
const combined = [...hlActions, ...viewActions2];
|
|
8961
|
-
|
|
8732
|
+
shell2.actionsPopup.setActions(combined);
|
|
8962
8733
|
const visible = combined.length > 0;
|
|
8963
|
-
|
|
8734
|
+
shell2.actionsPopup.trigger.hidden = !visible;
|
|
8964
8735
|
actionsDivider.hidden = !visible || footerItems.length === 0;
|
|
8965
8736
|
};
|
|
8966
8737
|
if (hlSrc) {
|
|
8967
8738
|
highlightActionsSub = hlSrc.subscribe(syncActions);
|
|
8968
8739
|
}
|
|
8969
8740
|
for (let i = 0; i < footerItems.length; i++) {
|
|
8970
|
-
if (i > 0)
|
|
8971
|
-
|
|
8741
|
+
if (i > 0) shell2.footerRight.append(createFooterDivider());
|
|
8742
|
+
shell2.footerRight.append(footerItems[i]);
|
|
8972
8743
|
}
|
|
8973
|
-
|
|
8974
|
-
|
|
8744
|
+
shell2.footerRight.append(actionsDivider);
|
|
8745
|
+
shell2.footerRight.append(shell2.actionsPopup.trigger);
|
|
8975
8746
|
syncActions();
|
|
8976
8747
|
}
|
|
8748
|
+
function updateChrome() {
|
|
8749
|
+
if (!shell) return;
|
|
8750
|
+
const top = mounted[mounted.length - 1];
|
|
8751
|
+
if (!top) return;
|
|
8752
|
+
updateNavButtons(shell, top);
|
|
8753
|
+
updateTitle(shell, top);
|
|
8754
|
+
updateFooterChip(shell, top);
|
|
8755
|
+
hintChangeSub?.();
|
|
8756
|
+
hintChangeSub = null;
|
|
8757
|
+
highlightActionsSub?.();
|
|
8758
|
+
highlightActionsSub = null;
|
|
8759
|
+
shell.footerRight.replaceChildren();
|
|
8760
|
+
const footerItems = [];
|
|
8761
|
+
buildEnterHint(top, footerItems);
|
|
8762
|
+
buildActions(shell, top, footerItems);
|
|
8763
|
+
}
|
|
8977
8764
|
function render2() {
|
|
8978
8765
|
if (!container.isConnected) return;
|
|
8979
8766
|
const stack = session.getState().stack;
|
|
@@ -9070,7 +8857,7 @@ function createViewStack(options) {
|
|
|
9070
8857
|
|
|
9071
8858
|
// src/browser/views/built-in/ids.ts
|
|
9072
8859
|
var BUILT_IN_VIEW_IDS = {
|
|
9073
|
-
|
|
8860
|
+
closeReason: "close-reason",
|
|
9074
8861
|
commandPalette: "command-palette",
|
|
9075
8862
|
elements: "elements",
|
|
9076
8863
|
entityReports: "entity-reports",
|
|
@@ -9121,7 +8908,7 @@ function parentDetail(ref2) {
|
|
|
9121
8908
|
return { id: DETAIL_VIEW_FOR_KIND[ref2.kind], ref: ref2 };
|
|
9122
8909
|
}
|
|
9123
8910
|
|
|
9124
|
-
// src/browser/views/built-in/
|
|
8911
|
+
// src/browser/views/built-in/close-reason.ts
|
|
9125
8912
|
import {
|
|
9126
8913
|
Ban,
|
|
9127
8914
|
BugOff,
|
|
@@ -9131,10 +8918,10 @@ import {
|
|
|
9131
8918
|
createElement as createLucideElement6
|
|
9132
8919
|
} from "lucide";
|
|
9133
8920
|
var pendingReportId = null;
|
|
9134
|
-
var
|
|
9135
|
-
function
|
|
8921
|
+
var afterClose = null;
|
|
8922
|
+
function setCloseTarget(reportId, onDone) {
|
|
9136
8923
|
pendingReportId = reportId;
|
|
9137
|
-
|
|
8924
|
+
afterClose = onDone;
|
|
9138
8925
|
}
|
|
9139
8926
|
function leadingIcon(iconNode) {
|
|
9140
8927
|
return () => {
|
|
@@ -9149,16 +8936,16 @@ function spinnerTile() {
|
|
|
9149
8936
|
return createIconTile(spinner);
|
|
9150
8937
|
}
|
|
9151
8938
|
var REASONS = [
|
|
9152
|
-
{ value: "fixed", label: "
|
|
8939
|
+
{ value: "fixed", label: "Resolved", icon: CircleCheck2 },
|
|
9153
8940
|
{ value: "not_a_bug", label: "Not a bug", icon: BugOff },
|
|
9154
8941
|
{ value: "duplicate", label: "Duplicate", icon: Copy2 },
|
|
9155
8942
|
{ value: "wont_fix", label: "Won't fix", icon: Ban }
|
|
9156
8943
|
];
|
|
9157
|
-
var
|
|
9158
|
-
id: BUILT_IN_VIEW_IDS.
|
|
8944
|
+
var closeReasonView = {
|
|
8945
|
+
id: BUILT_IN_VIEW_IDS.closeReason,
|
|
9159
8946
|
matches: () => false,
|
|
9160
8947
|
parent: (ref2) => ref2 ? { id: BUILT_IN_VIEW_IDS.reportDetail, ref: ref2 } : null,
|
|
9161
|
-
title: "
|
|
8948
|
+
title: "Close reason",
|
|
9162
8949
|
searchable: false,
|
|
9163
8950
|
focusTarget: (host) => host.querySelector("[data-uidex-list-content]"),
|
|
9164
8951
|
surface: () => ({ kind: "list", id: "unused", items: [] }),
|
|
@@ -9171,12 +8958,12 @@ var archiveReasonView = {
|
|
|
9171
8958
|
}));
|
|
9172
8959
|
const surface = {
|
|
9173
8960
|
kind: "list",
|
|
9174
|
-
id: "uidex-
|
|
8961
|
+
id: "uidex-close-reason",
|
|
9175
8962
|
searchable: false,
|
|
9176
8963
|
items,
|
|
9177
8964
|
emptyLabel: "No reasons available",
|
|
9178
8965
|
onSelect: async (item) => {
|
|
9179
|
-
if (busy || !pendingReportId || !ctx.registry.
|
|
8966
|
+
if (busy || !pendingReportId || !ctx.registry.closeReport) return;
|
|
9180
8967
|
busy = true;
|
|
9181
8968
|
const row = root.querySelector(
|
|
9182
8969
|
`[data-uidex-item-value="${item.value}"]`
|
|
@@ -9188,13 +8975,10 @@ var archiveReasonView = {
|
|
|
9188
8975
|
row.style.pointerEvents = "none";
|
|
9189
8976
|
}
|
|
9190
8977
|
try {
|
|
9191
|
-
await ctx.registry.
|
|
9192
|
-
|
|
9193
|
-
item.value
|
|
9194
|
-
);
|
|
9195
|
-
const done = afterArchive;
|
|
8978
|
+
await ctx.registry.closeReport(pendingReportId, item.value);
|
|
8979
|
+
const done = afterClose;
|
|
9196
8980
|
pendingReportId = null;
|
|
9197
|
-
|
|
8981
|
+
afterClose = null;
|
|
9198
8982
|
done?.();
|
|
9199
8983
|
} catch {
|
|
9200
8984
|
busy = false;
|
|
@@ -9212,7 +8996,7 @@ var archiveReasonView = {
|
|
|
9212
8996
|
}
|
|
9213
8997
|
const error = document.createElement("p");
|
|
9214
8998
|
error.className = "text-destructive px-4 py-2 text-xs";
|
|
9215
|
-
error.textContent = "
|
|
8999
|
+
error.textContent = "Close failed \u2014 try again";
|
|
9216
9000
|
root.querySelector("[data-uidex-list-content]")?.prepend(error);
|
|
9217
9001
|
setTimeout(() => error.remove(), 3e3);
|
|
9218
9002
|
}
|
|
@@ -9539,7 +9323,8 @@ function createCommandPaletteView(shortcut) {
|
|
|
9539
9323
|
}
|
|
9540
9324
|
|
|
9541
9325
|
// src/browser/internal/screenshot.ts
|
|
9542
|
-
import { domToPng } from "modern-screenshot";
|
|
9326
|
+
import { domToPng, domToWebp } from "modern-screenshot";
|
|
9327
|
+
var WEBP_QUALITY = 0.85;
|
|
9543
9328
|
function resolveBackgroundColor(el2) {
|
|
9544
9329
|
let node = el2;
|
|
9545
9330
|
while (node) {
|
|
@@ -9553,8 +9338,7 @@ function isUidexChrome(node) {
|
|
|
9553
9338
|
if (node.nodeType !== Node.ELEMENT_NODE) return false;
|
|
9554
9339
|
const el2 = node;
|
|
9555
9340
|
if (el2.shadowRoot !== null) return true;
|
|
9556
|
-
|
|
9557
|
-
return cls.contains(SURFACE_HOST_CLASS) || cls.contains(SURFACE_CONTAINER_CLASS);
|
|
9341
|
+
return el2.classList.contains(SURFACE_HOST_CLASS);
|
|
9558
9342
|
}
|
|
9559
9343
|
async function captureScreenshot(options = {}) {
|
|
9560
9344
|
if (typeof document === "undefined") {
|
|
@@ -9566,8 +9350,10 @@ async function captureScreenshot(options = {}) {
|
|
|
9566
9350
|
const scale = options.maxWidth && width > options.maxWidth ? options.maxWidth / width : 1;
|
|
9567
9351
|
const padding = 16;
|
|
9568
9352
|
const height = target.scrollHeight || target.clientHeight;
|
|
9569
|
-
|
|
9353
|
+
const encode = options.format === "png" ? domToPng : domToWebp;
|
|
9354
|
+
return encode(target, {
|
|
9570
9355
|
scale,
|
|
9356
|
+
quality: WEBP_QUALITY,
|
|
9571
9357
|
width: width + padding * 2,
|
|
9572
9358
|
height: height + padding * 2,
|
|
9573
9359
|
backgroundColor: resolveBackgroundColor(target),
|
|
@@ -9623,12 +9409,6 @@ function collectFlowsTouching(ctx, targetId) {
|
|
|
9623
9409
|
}
|
|
9624
9410
|
|
|
9625
9411
|
// src/browser/views/builder/detail-builder.ts
|
|
9626
|
-
var DOM_BACKED_KINDS2 = /* @__PURE__ */ new Set([
|
|
9627
|
-
"element",
|
|
9628
|
-
"region",
|
|
9629
|
-
"widget",
|
|
9630
|
-
"primitive"
|
|
9631
|
-
]);
|
|
9632
9412
|
var DETAIL_HINTS = [{ key: "\u21B5", label: "Open" }];
|
|
9633
9413
|
function copyPathAction(ref2, loc) {
|
|
9634
9414
|
const identifier = `${ref2.kind}:${ref2.id}`;
|
|
@@ -9730,7 +9510,10 @@ function copyScreenshotAction(ref2) {
|
|
|
9730
9510
|
const target = resolveEntityElement(ref2) ?? void 0;
|
|
9731
9511
|
const dataUrl = await captureScreenshot({
|
|
9732
9512
|
target,
|
|
9733
|
-
maxWidth: 1280
|
|
9513
|
+
maxWidth: 1280,
|
|
9514
|
+
// Clipboard write requires PNG — the async Clipboard API rejects
|
|
9515
|
+
// image/webp (`ClipboardItem` throws on Chrome/Safari).
|
|
9516
|
+
format: "png"
|
|
9734
9517
|
});
|
|
9735
9518
|
const res = await fetch(dataUrl);
|
|
9736
9519
|
const blob = await res.blob();
|
|
@@ -9763,12 +9546,11 @@ function createEntityDetailView(config) {
|
|
|
9763
9546
|
if (!ctx.ref || ctx.ref.kind !== kind) {
|
|
9764
9547
|
return { kind: "detail", entityKind: kind };
|
|
9765
9548
|
}
|
|
9766
|
-
const
|
|
9767
|
-
|
|
9768
|
-
|
|
9769
|
-
|
|
9770
|
-
const
|
|
9771
|
-
const meta = metaEntity.meta;
|
|
9549
|
+
const exactEntity = ctx.registry.get(kind, ctx.ref.id);
|
|
9550
|
+
const patternEntity = exactEntity ? void 0 : ctx.registry.matchPattern?.(kind, ctx.ref.id);
|
|
9551
|
+
const entity = exactEntity ?? patternEntity;
|
|
9552
|
+
const metaEntity = entity ? entity : null;
|
|
9553
|
+
const meta = metaEntity?.meta;
|
|
9772
9554
|
const actions = [];
|
|
9773
9555
|
const cloud = ctx.cloud;
|
|
9774
9556
|
actions.push({ ...reportAction(ctx.ref), group: "Report" });
|
|
@@ -9782,18 +9564,20 @@ function createEntityDetailView(config) {
|
|
|
9782
9564
|
if (cloud?.integrations.getCachedConfig()?.hasJira) {
|
|
9783
9565
|
actions.push({ ...jiraAction(ctx.ref), group: "Report" });
|
|
9784
9566
|
}
|
|
9785
|
-
if (
|
|
9567
|
+
if (DOM_BACKED_KINDS.has(kind) && resolveEntityElement(ctx.ref)) {
|
|
9786
9568
|
actions.push({ ...highlightElementAction(ctx.ref), group: "Inspect" });
|
|
9787
9569
|
actions.push({ ...copyScreenshotAction(ctx.ref), group: "Inspect" });
|
|
9788
9570
|
}
|
|
9789
|
-
|
|
9790
|
-
|
|
9791
|
-
|
|
9792
|
-
|
|
9793
|
-
|
|
9794
|
-
|
|
9795
|
-
|
|
9796
|
-
|
|
9571
|
+
if (metaEntity?.loc) {
|
|
9572
|
+
actions.push({
|
|
9573
|
+
...copyPathAction(ctx.ref, metaEntity.loc),
|
|
9574
|
+
group: "Inspect"
|
|
9575
|
+
});
|
|
9576
|
+
actions.push({
|
|
9577
|
+
...copySnapshotAction(ctx.ref, metaEntity.loc),
|
|
9578
|
+
group: "Inspect"
|
|
9579
|
+
});
|
|
9580
|
+
}
|
|
9797
9581
|
const sections = [];
|
|
9798
9582
|
if (meta?.description) {
|
|
9799
9583
|
sections.push({ id: "description", text: meta.description });
|
|
@@ -9801,10 +9585,12 @@ function createEntityDetailView(config) {
|
|
|
9801
9585
|
if (offerAcceptance && meta?.acceptance?.length) {
|
|
9802
9586
|
sections.push({ id: "acceptance", items: meta.acceptance });
|
|
9803
9587
|
}
|
|
9804
|
-
|
|
9805
|
-
|
|
9588
|
+
if (entity) {
|
|
9589
|
+
for (const s of config.extraSections?.(ctx, entity) ?? []) {
|
|
9590
|
+
sections.push(s);
|
|
9591
|
+
}
|
|
9806
9592
|
}
|
|
9807
|
-
if (!
|
|
9593
|
+
if (!DOM_BACKED_KINDS.has(kind)) {
|
|
9808
9594
|
sections.push({
|
|
9809
9595
|
id: "composes",
|
|
9810
9596
|
label: SECTION_LABELS.contains,
|
|
@@ -9812,7 +9598,7 @@ function createEntityDetailView(config) {
|
|
|
9812
9598
|
filterable: true
|
|
9813
9599
|
});
|
|
9814
9600
|
}
|
|
9815
|
-
if (
|
|
9601
|
+
if (DOM_BACKED_KINDS.has(kind) && meta?.features?.length) {
|
|
9816
9602
|
const featureEntities = meta.features.map((fId) => ctx.registry.get("feature", fId)).filter((e) => !!e);
|
|
9817
9603
|
if (featureEntities.length > 0) {
|
|
9818
9604
|
sections.push({
|
|
@@ -9831,8 +9617,9 @@ function createEntityDetailView(config) {
|
|
|
9831
9617
|
return {
|
|
9832
9618
|
kind: "detail",
|
|
9833
9619
|
entityKind: kind,
|
|
9834
|
-
title: displayName(metaEntity),
|
|
9835
|
-
subtitle: config.subtitle?.(ctx,
|
|
9620
|
+
title: patternEntity ? ctx.ref.id : metaEntity ? displayName(metaEntity) : ctx.ref.id,
|
|
9621
|
+
subtitle: exactEntity ? config.subtitle?.(ctx, exactEntity) : void 0,
|
|
9622
|
+
unregistered: !entity,
|
|
9836
9623
|
actions,
|
|
9837
9624
|
sections
|
|
9838
9625
|
};
|
|
@@ -9841,35 +9628,14 @@ function createEntityDetailView(config) {
|
|
|
9841
9628
|
}
|
|
9842
9629
|
|
|
9843
9630
|
// src/browser/views/built-in/entity-detail.ts
|
|
9844
|
-
function
|
|
9845
|
-
|
|
9846
|
-
if (!el2) return [];
|
|
9847
|
-
const parents = [];
|
|
9848
|
-
const seen = /* @__PURE__ */ new Set();
|
|
9849
|
-
let node = el2.parentElement;
|
|
9850
|
-
while (node) {
|
|
9851
|
-
if (node instanceof HTMLElement) {
|
|
9852
|
-
for (const [attr, kind] of UIDEX_ATTR_TO_KIND) {
|
|
9853
|
-
const id = node.getAttribute(attr);
|
|
9854
|
-
if (id) {
|
|
9855
|
-
const key = `${kind}:${id}`;
|
|
9856
|
-
if (!seen.has(key)) {
|
|
9857
|
-
seen.add(key);
|
|
9858
|
-
const entity = ctx.registry.get(kind, id);
|
|
9859
|
-
if (entity) parents.push(entity);
|
|
9860
|
-
}
|
|
9861
|
-
}
|
|
9862
|
-
}
|
|
9863
|
-
}
|
|
9864
|
-
node = node.parentElement;
|
|
9865
|
-
}
|
|
9866
|
-
return parents;
|
|
9631
|
+
function collectFeatureConsumers(ctx, featureId) {
|
|
9632
|
+
return ctx.registry.list("page").filter((page) => page.meta?.features?.includes(featureId));
|
|
9867
9633
|
}
|
|
9868
|
-
function usedBySection(ctx,
|
|
9634
|
+
function usedBySection(ctx, featureId) {
|
|
9869
9635
|
return {
|
|
9870
9636
|
id: "used-by",
|
|
9871
9637
|
label: SECTION_LABELS.usedBy,
|
|
9872
|
-
entities:
|
|
9638
|
+
entities: collectFeatureConsumers(ctx, featureId),
|
|
9873
9639
|
filterable: true
|
|
9874
9640
|
};
|
|
9875
9641
|
}
|
|
@@ -9890,9 +9656,7 @@ var featureDetailView = createEntityDetailView({
|
|
|
9890
9656
|
id: "feature-detail",
|
|
9891
9657
|
kind: "feature",
|
|
9892
9658
|
fallbackTitle: "Feature",
|
|
9893
|
-
extraSections: (ctx, entity) => [
|
|
9894
|
-
usedBySection(ctx, { kind: "feature", id: entity.id })
|
|
9895
|
-
]
|
|
9659
|
+
extraSections: (ctx, entity) => [usedBySection(ctx, entity.id)]
|
|
9896
9660
|
});
|
|
9897
9661
|
var regionDetailView = createEntityDetailView({
|
|
9898
9662
|
id: "region-detail",
|
|
@@ -10020,6 +9784,15 @@ var reportDetailView = {
|
|
|
10020
9784
|
}
|
|
10021
9785
|
if (report.screenshot) {
|
|
10022
9786
|
sections.push({ id: "screenshot", url: report.screenshot });
|
|
9787
|
+
} else {
|
|
9788
|
+
const pins = ctx.cloud?.pins;
|
|
9789
|
+
const fetchScreenshot = pins?.screenshot;
|
|
9790
|
+
if (pins && fetchScreenshot) {
|
|
9791
|
+
sections.push({
|
|
9792
|
+
id: "screenshot",
|
|
9793
|
+
load: () => fetchScreenshot.call(pins, report.id)
|
|
9794
|
+
});
|
|
9795
|
+
}
|
|
10023
9796
|
}
|
|
10024
9797
|
const metaEntries = [];
|
|
10025
9798
|
if (report.url) metaEntries.push({ label: "URL", value: report.url });
|
|
@@ -10030,14 +9803,14 @@ var reportDetailView = {
|
|
|
10030
9803
|
sections.push({ id: "metadata", entries: metaEntries });
|
|
10031
9804
|
}
|
|
10032
9805
|
const actions = [];
|
|
10033
|
-
if (ctx.registry.
|
|
9806
|
+
if (ctx.registry.closeReport) {
|
|
10034
9807
|
actions.push({
|
|
10035
|
-
id: "
|
|
10036
|
-
label: "
|
|
9808
|
+
id: "close",
|
|
9809
|
+
label: "Close",
|
|
10037
9810
|
icon: "archive-x",
|
|
10038
9811
|
run: () => {
|
|
10039
|
-
|
|
10040
|
-
ctx.push({ id: BUILT_IN_VIEW_IDS.
|
|
9812
|
+
setCloseTarget(report.id, () => ctx.pop());
|
|
9813
|
+
ctx.push({ id: BUILT_IN_VIEW_IDS.closeReason });
|
|
10041
9814
|
}
|
|
10042
9815
|
});
|
|
10043
9816
|
}
|
|
@@ -10075,13 +9848,13 @@ function reportToItem(report, ctx) {
|
|
|
10075
9848
|
const label = raw.length > 80 ? raw.slice(0, 80) + "\u2026" : raw;
|
|
10076
9849
|
const kind = ctx.ref?.kind ?? "element";
|
|
10077
9850
|
const actions = [];
|
|
10078
|
-
if (ctx.registry.
|
|
9851
|
+
if (ctx.registry.closeReport) {
|
|
10079
9852
|
actions.push({
|
|
10080
|
-
id: `
|
|
10081
|
-
label: "
|
|
9853
|
+
id: `close-${report.id}`,
|
|
9854
|
+
label: "Close",
|
|
10082
9855
|
perform: () => {
|
|
10083
|
-
|
|
10084
|
-
ctx.push({ id: BUILT_IN_VIEW_IDS.
|
|
9856
|
+
setCloseTarget(report.id, () => ctx.pop());
|
|
9857
|
+
ctx.push({ id: BUILT_IN_VIEW_IDS.closeReason });
|
|
10085
9858
|
}
|
|
10086
9859
|
});
|
|
10087
9860
|
}
|
|
@@ -10234,7 +10007,7 @@ function capitalize2(s) {
|
|
|
10234
10007
|
return s.length === 0 ? s : s[0].toUpperCase() + s.slice(1);
|
|
10235
10008
|
}
|
|
10236
10009
|
function renderPayloadMarkdown(payload) {
|
|
10237
|
-
const heading = payload.title ?? `${capitalize2(payload.type)} Report`;
|
|
10010
|
+
const heading = payload.title ?? `${capitalize2(payload.type ?? "")} Report`;
|
|
10238
10011
|
const ctx = payload.context;
|
|
10239
10012
|
const lines = [
|
|
10240
10013
|
`# ${heading}`,
|
|
@@ -10303,12 +10076,6 @@ var reportFields = [
|
|
|
10303
10076
|
];
|
|
10304
10077
|
|
|
10305
10078
|
// src/browser/views/built-in/report/view-builder.ts
|
|
10306
|
-
var DOM_BACKED_KINDS3 = /* @__PURE__ */ new Set([
|
|
10307
|
-
"element",
|
|
10308
|
-
"region",
|
|
10309
|
-
"widget",
|
|
10310
|
-
"primitive"
|
|
10311
|
-
]);
|
|
10312
10079
|
var KIND_TO_ATTR = new Map(
|
|
10313
10080
|
UIDEX_ATTR_TO_KIND.map(([attr, kind]) => [kind, attr])
|
|
10314
10081
|
);
|
|
@@ -10379,7 +10146,7 @@ function createReportView(config) {
|
|
|
10379
10146
|
const cloud = resolveCloud(ctx);
|
|
10380
10147
|
const extra = extraFields ? extraFields(ctx) : [];
|
|
10381
10148
|
const fields = [...extra, ...baseFields ?? reportFields];
|
|
10382
|
-
const isDomBacked = ctx.ref != null &&
|
|
10149
|
+
const isDomBacked = ctx.ref != null && DOM_BACKED_KINDS.has(ctx.ref.kind);
|
|
10383
10150
|
const targetEl = ctx.ref && isDomBacked ? resolveElement(ctx.ref) : null;
|
|
10384
10151
|
const screenshotPromise = isDomBacked ? captureScreenshot({
|
|
10385
10152
|
target: targetEl ?? void 0,
|
|
@@ -10962,7 +10729,7 @@ var pinSettingsView = {
|
|
|
10962
10729
|
// src/browser/views/built-in/index.ts
|
|
10963
10730
|
function buildDefaultViews(shortcut) {
|
|
10964
10731
|
return [
|
|
10965
|
-
|
|
10732
|
+
closeReasonView,
|
|
10966
10733
|
createCommandPaletteView(shortcut),
|
|
10967
10734
|
explorePageView,
|
|
10968
10735
|
componentDetailView,
|
|
@@ -10990,6 +10757,27 @@ function buildDefaultViews(shortcut) {
|
|
|
10990
10757
|
}
|
|
10991
10758
|
|
|
10992
10759
|
// src/browser/create-uidex.ts
|
|
10760
|
+
function getVisibleEntities() {
|
|
10761
|
+
if (typeof document === "undefined") return [];
|
|
10762
|
+
const selector = UIDEX_ATTR_TO_KIND.map(([a]) => `[${a}]`).join(",");
|
|
10763
|
+
const nodes = document.querySelectorAll(selector);
|
|
10764
|
+
const ids = [];
|
|
10765
|
+
const seen = /* @__PURE__ */ new Set();
|
|
10766
|
+
for (const node of nodes) {
|
|
10767
|
+
if (node.closest(SURFACE_IGNORE_SELECTOR)) continue;
|
|
10768
|
+
for (const [attr, kind] of UIDEX_ATTR_TO_KIND) {
|
|
10769
|
+
const id = node.getAttribute(attr);
|
|
10770
|
+
if (!id) continue;
|
|
10771
|
+
const key = `${kind}:${id}`;
|
|
10772
|
+
if (!seen.has(key)) {
|
|
10773
|
+
seen.add(key);
|
|
10774
|
+
ids.push(key);
|
|
10775
|
+
}
|
|
10776
|
+
break;
|
|
10777
|
+
}
|
|
10778
|
+
}
|
|
10779
|
+
return ids;
|
|
10780
|
+
}
|
|
10993
10781
|
function createUidex(options = {}) {
|
|
10994
10782
|
const registry = createRegistry();
|
|
10995
10783
|
const inspectorRef = { current: null };
|
|
@@ -11024,7 +10812,7 @@ function createUidex(options = {}) {
|
|
|
11024
10812
|
const views = createRouter({ session });
|
|
11025
10813
|
const cloud = options.cloud ?? null;
|
|
11026
10814
|
const ingestOpts = resolveIngestOptions(options.ingest, cloud !== null);
|
|
11027
|
-
const ingest = ingestOpts ? createIngest(
|
|
10815
|
+
const ingest = ingestOpts ? createIngest(ingestOpts) : null;
|
|
11028
10816
|
if (options.defaultViews !== false) {
|
|
11029
10817
|
for (const view of buildDefaultViews(options.shortcut)) views.add(view);
|
|
11030
10818
|
}
|
|
@@ -11034,6 +10822,94 @@ function createUidex(options = {}) {
|
|
|
11034
10822
|
let shadowRoot = null;
|
|
11035
10823
|
const mountCleanup = createCleanupStack();
|
|
11036
10824
|
let mounted = false;
|
|
10825
|
+
function syncReportsToRegistry() {
|
|
10826
|
+
const layer = pinLayerRef.current;
|
|
10827
|
+
if (!layer) return;
|
|
10828
|
+
const byEntity = /* @__PURE__ */ new Map();
|
|
10829
|
+
for (const pin of layer.getAllPins()) {
|
|
10830
|
+
const cid = pin.entity ?? "";
|
|
10831
|
+
if (!cid) continue;
|
|
10832
|
+
const list = byEntity.get(cid);
|
|
10833
|
+
if (list) list.push(pin);
|
|
10834
|
+
else byEntity.set(cid, [pin]);
|
|
10835
|
+
}
|
|
10836
|
+
for (const [cid, pins] of byEntity) {
|
|
10837
|
+
const ref2 = parseComponentRef(cid);
|
|
10838
|
+
registry.setReports(ref2.kind, ref2.id, pins);
|
|
10839
|
+
}
|
|
10840
|
+
}
|
|
10841
|
+
function setupKeyBindings(root, viewStack) {
|
|
10842
|
+
const bindings = bindShadowKeys({
|
|
10843
|
+
shadowRoot: root,
|
|
10844
|
+
session,
|
|
10845
|
+
getActionsPopup: () => viewStack.getActionsPopup(),
|
|
10846
|
+
getPinLayer: () => pinLayerRef.current,
|
|
10847
|
+
shortcut: options.shortcut
|
|
10848
|
+
});
|
|
10849
|
+
mountCleanup.add(bindings);
|
|
10850
|
+
return bindings;
|
|
10851
|
+
}
|
|
10852
|
+
function setupPinLayer(root, shell, channel, getCurrentRoute, getMatchMode, getPathname) {
|
|
10853
|
+
if (cloud) {
|
|
10854
|
+
registry.closeReport = async (reportId, status) => {
|
|
10855
|
+
pinLayerRef.current?.removePin(reportId);
|
|
10856
|
+
await cloud.pins.close(
|
|
10857
|
+
reportId,
|
|
10858
|
+
status
|
|
10859
|
+
);
|
|
10860
|
+
syncReportsToRegistry();
|
|
10861
|
+
};
|
|
10862
|
+
}
|
|
10863
|
+
const pinLayer = createPinLayer({
|
|
10864
|
+
container: root,
|
|
10865
|
+
onOpenPinDetail: (componentId, reportId) => {
|
|
10866
|
+
const ref2 = parseComponentRef(componentId);
|
|
10867
|
+
setSelectedReportId(reportId);
|
|
10868
|
+
const entry = { id: BUILT_IN_VIEW_IDS.reportDetail, ref: ref2 };
|
|
10869
|
+
session.mode.transition.enterViewing(views.buildStack(entry));
|
|
10870
|
+
},
|
|
10871
|
+
onHoverPin: (anchor, componentId) => {
|
|
10872
|
+
const overlay = overlayRef.current;
|
|
10873
|
+
if (!overlay) return;
|
|
10874
|
+
if (!anchor || !componentId) {
|
|
10875
|
+
overlay.hide();
|
|
10876
|
+
return;
|
|
10877
|
+
}
|
|
10878
|
+
overlay.show(anchor, {
|
|
10879
|
+
color: isDarkMode() ? "#e4e4e7" : "#27272a"
|
|
10880
|
+
});
|
|
10881
|
+
},
|
|
10882
|
+
onPinsChanged: syncReportsToRegistry
|
|
10883
|
+
});
|
|
10884
|
+
shell.menuBar.setPinLayer(pinLayer);
|
|
10885
|
+
pinLayerRef.current = pinLayer;
|
|
10886
|
+
mountCleanup.add(() => {
|
|
10887
|
+
pinLayer.destroy();
|
|
10888
|
+
pinLayerRef.current = null;
|
|
10889
|
+
registry.closeReport = void 0;
|
|
10890
|
+
});
|
|
10891
|
+
if (cloud) {
|
|
10892
|
+
const detach = pinLayer.attachCloud({
|
|
10893
|
+
cloud,
|
|
10894
|
+
channel,
|
|
10895
|
+
getRoute: getCurrentRoute,
|
|
10896
|
+
getPathname,
|
|
10897
|
+
getVisibleEntities,
|
|
10898
|
+
getMatchMode,
|
|
10899
|
+
onError: (err) => console.warn("[uidex] pin fetch failed", err)
|
|
10900
|
+
});
|
|
10901
|
+
mountCleanup.add(detach);
|
|
10902
|
+
if (channel && typeof window !== "undefined") {
|
|
10903
|
+
const onRouteChange = () => {
|
|
10904
|
+
const route = getCurrentRoute();
|
|
10905
|
+
channel?.joinRoute(route);
|
|
10906
|
+
void pinLayer.refresh();
|
|
10907
|
+
};
|
|
10908
|
+
const detachRoute = bindRouteChange(onRouteChange);
|
|
10909
|
+
mountCleanup.add(detachRoute);
|
|
10910
|
+
}
|
|
10911
|
+
}
|
|
10912
|
+
}
|
|
11037
10913
|
function mount(target) {
|
|
11038
10914
|
if (mounted) return;
|
|
11039
10915
|
const mountTarget = target ?? (typeof document !== "undefined" ? document.body : null);
|
|
@@ -11042,28 +10918,7 @@ function createUidex(options = {}) {
|
|
|
11042
10918
|
}
|
|
11043
10919
|
const getPathname = () => typeof location !== "undefined" ? location.pathname : "/";
|
|
11044
10920
|
const getCurrentRoute = () => options.getRoute?.() ?? findCurrentRoutePath(registry) ?? getPathname();
|
|
11045
|
-
const
|
|
11046
|
-
if (typeof document === "undefined") return [];
|
|
11047
|
-
const selector = UIDEX_ATTR_TO_KIND.map(([a]) => `[${a}]`).join(",");
|
|
11048
|
-
const nodes = document.querySelectorAll(selector);
|
|
11049
|
-
const ids = [];
|
|
11050
|
-
const seen = /* @__PURE__ */ new Set();
|
|
11051
|
-
for (const node of nodes) {
|
|
11052
|
-
if (node.closest(SURFACE_IGNORE_SELECTOR)) continue;
|
|
11053
|
-
for (const [attr, kind] of UIDEX_ATTR_TO_KIND) {
|
|
11054
|
-
const id = node.getAttribute(attr);
|
|
11055
|
-
if (!id) continue;
|
|
11056
|
-
const key = `${kind}:${id}`;
|
|
11057
|
-
if (!seen.has(key)) {
|
|
11058
|
-
seen.add(key);
|
|
11059
|
-
ids.push(key);
|
|
11060
|
-
}
|
|
11061
|
-
break;
|
|
11062
|
-
}
|
|
11063
|
-
}
|
|
11064
|
-
return ids;
|
|
11065
|
-
};
|
|
11066
|
-
const getMatchMode = () => (typeof localStorage !== "undefined" ? localStorage.getItem("uidex:pin-match-mode") : null) ?? "route";
|
|
10921
|
+
const getMatchMode = () => readMode();
|
|
11067
10922
|
let channel = null;
|
|
11068
10923
|
if (cloud && options.user) {
|
|
11069
10924
|
channel = cloud.realtime.connect({
|
|
@@ -11084,7 +10939,6 @@ function createUidex(options = {}) {
|
|
|
11084
10939
|
onSelect: (match) => {
|
|
11085
10940
|
const route = views.resolve(match.ref);
|
|
11086
10941
|
if (!route) return;
|
|
11087
|
-
session.select(match.ref);
|
|
11088
10942
|
const entry = { id: route.view.id, ref: match.ref };
|
|
11089
10943
|
session.mode.transition.enterViewing(views.buildStack(entry));
|
|
11090
10944
|
}
|
|
@@ -11135,92 +10989,15 @@ function createUidex(options = {}) {
|
|
|
11135
10989
|
});
|
|
11136
10990
|
mountCleanup.add(viewStack);
|
|
11137
10991
|
if (shadowRoot) {
|
|
11138
|
-
keyBindings =
|
|
10992
|
+
keyBindings = setupKeyBindings(shadowRoot, viewStack);
|
|
10993
|
+
setupPinLayer(
|
|
11139
10994
|
shadowRoot,
|
|
11140
|
-
|
|
11141
|
-
|
|
11142
|
-
|
|
11143
|
-
|
|
11144
|
-
|
|
11145
|
-
|
|
11146
|
-
}
|
|
11147
|
-
if (shadowRoot) {
|
|
11148
|
-
const syncReportsToRegistry = () => {
|
|
11149
|
-
const layer = pinLayerRef.current;
|
|
11150
|
-
if (!layer) return;
|
|
11151
|
-
const byEntity = /* @__PURE__ */ new Map();
|
|
11152
|
-
for (const pin of layer.getAllPins()) {
|
|
11153
|
-
const cid = pin.entity ?? "";
|
|
11154
|
-
if (!cid) continue;
|
|
11155
|
-
const list = byEntity.get(cid);
|
|
11156
|
-
if (list) list.push(pin);
|
|
11157
|
-
else byEntity.set(cid, [pin]);
|
|
11158
|
-
}
|
|
11159
|
-
for (const [cid, pins] of byEntity) {
|
|
11160
|
-
const ref2 = parseComponentRef(cid);
|
|
11161
|
-
registry.setReports(ref2.kind, ref2.id, pins);
|
|
11162
|
-
}
|
|
11163
|
-
};
|
|
11164
|
-
if (cloud) {
|
|
11165
|
-
registry.archiveReport = async (reportId, reason) => {
|
|
11166
|
-
pinLayerRef.current?.removePin(reportId);
|
|
11167
|
-
await cloud.pins.archive(
|
|
11168
|
-
reportId,
|
|
11169
|
-
reason
|
|
11170
|
-
);
|
|
11171
|
-
syncReportsToRegistry();
|
|
11172
|
-
};
|
|
11173
|
-
}
|
|
11174
|
-
const pinLayer = createPinLayer({
|
|
11175
|
-
container: shadowRoot,
|
|
11176
|
-
currentBranch: options.git?.branch ?? null,
|
|
11177
|
-
onOpenPinDetail: (componentId, reportId) => {
|
|
11178
|
-
const ref2 = parseComponentRef(componentId);
|
|
11179
|
-
setSelectedReportId(reportId);
|
|
11180
|
-
const entry = { id: BUILT_IN_VIEW_IDS.reportDetail, ref: ref2 };
|
|
11181
|
-
session.mode.transition.enterViewing(views.buildStack(entry));
|
|
11182
|
-
},
|
|
11183
|
-
onHoverPin: (anchor, componentId) => {
|
|
11184
|
-
const overlay = overlayRef.current;
|
|
11185
|
-
if (!overlay) return;
|
|
11186
|
-
if (!anchor || !componentId) {
|
|
11187
|
-
overlay.hide();
|
|
11188
|
-
return;
|
|
11189
|
-
}
|
|
11190
|
-
overlay.show(anchor, {
|
|
11191
|
-
color: isDarkMode() ? "#e4e4e7" : "#27272a"
|
|
11192
|
-
});
|
|
11193
|
-
},
|
|
11194
|
-
onPinsChanged: syncReportsToRegistry
|
|
11195
|
-
});
|
|
11196
|
-
shell.menuBar.setPinLayer(pinLayer);
|
|
11197
|
-
pinLayerRef.current = pinLayer;
|
|
11198
|
-
mountCleanup.add(() => {
|
|
11199
|
-
pinLayer.destroy();
|
|
11200
|
-
pinLayerRef.current = null;
|
|
11201
|
-
registry.archiveReport = void 0;
|
|
11202
|
-
});
|
|
11203
|
-
if (cloud) {
|
|
11204
|
-
const detach = pinLayer.attachCloud({
|
|
11205
|
-
cloud,
|
|
11206
|
-
channel,
|
|
11207
|
-
getRoute: getCurrentRoute,
|
|
11208
|
-
getPathname,
|
|
11209
|
-
getVisibleEntities,
|
|
11210
|
-
getMatchMode,
|
|
11211
|
-
onError: (err) => console.warn("[uidex] pin fetch failed", err)
|
|
11212
|
-
});
|
|
11213
|
-
mountCleanup.add(detach);
|
|
11214
|
-
if (channel && typeof window !== "undefined") {
|
|
11215
|
-
const onRouteChange = () => {
|
|
11216
|
-
const route = getCurrentRoute();
|
|
11217
|
-
channel?.joinRoute(route);
|
|
11218
|
-
void pinLayer.refresh();
|
|
11219
|
-
};
|
|
11220
|
-
const detachRoute = bindRouteChange(onRouteChange);
|
|
11221
|
-
mountCleanup.add(detachRoute);
|
|
11222
|
-
}
|
|
11223
|
-
}
|
|
10995
|
+
shell,
|
|
10996
|
+
channel,
|
|
10997
|
+
getCurrentRoute,
|
|
10998
|
+
getMatchMode,
|
|
10999
|
+
getPathname
|
|
11000
|
+
);
|
|
11224
11001
|
}
|
|
11225
11002
|
if (ingest) {
|
|
11226
11003
|
ingest.start();
|
|
@@ -11259,18 +11036,23 @@ function UidexProvider({
|
|
|
11259
11036
|
config,
|
|
11260
11037
|
children
|
|
11261
11038
|
}) {
|
|
11262
|
-
const [
|
|
11039
|
+
const [owned] = useState(() => {
|
|
11263
11040
|
if (externalInstance) return null;
|
|
11264
|
-
const
|
|
11265
|
-
|
|
11041
|
+
const ownedCloud = cloud === void 0 && projectKey && typeof window !== "undefined" ? createCloud({ projectKey }) : null;
|
|
11042
|
+
const resolvedCloud = cloud !== void 0 ? cloud : ownedCloud;
|
|
11043
|
+
return {
|
|
11044
|
+
instance: createUidex({ ...config, cloud: resolvedCloud, user }),
|
|
11045
|
+
cloud: ownedCloud
|
|
11046
|
+
};
|
|
11266
11047
|
});
|
|
11267
|
-
const instance = externalInstance ??
|
|
11048
|
+
const instance = externalInstance ?? owned.instance;
|
|
11268
11049
|
useEffect(() => {
|
|
11269
|
-
if (!
|
|
11050
|
+
if (!owned) return;
|
|
11270
11051
|
return () => {
|
|
11271
|
-
|
|
11052
|
+
owned.instance.unmount();
|
|
11053
|
+
owned.cloud?.dispose?.();
|
|
11272
11054
|
};
|
|
11273
|
-
}, [
|
|
11055
|
+
}, [owned]);
|
|
11274
11056
|
return /* @__PURE__ */ jsx(UidexContext.Provider, { value: instance, children });
|
|
11275
11057
|
}
|
|
11276
11058
|
|
|
@@ -11405,6 +11187,7 @@ function UidexDevtools({
|
|
|
11405
11187
|
setInstance(inst);
|
|
11406
11188
|
return () => {
|
|
11407
11189
|
inst.unmount();
|
|
11190
|
+
cloud?.dispose?.();
|
|
11408
11191
|
};
|
|
11409
11192
|
}, [projectKey, user?.id]);
|
|
11410
11193
|
if (!instance) return null;
|