uilint-react 0.1.24 → 0.1.25
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/{ElementBadges-T4N3VQRI.js → ElementBadges-2WRRHFLI.js} +29 -51
- package/dist/{InspectionPanel-47JBBKBL.js → InspectionPanel-FRJB6CJ6.js} +2 -2
- package/dist/{LocatorOverlay-ADJUWU2H.js → LocatorOverlay-O4XZCAPC.js} +2 -2
- package/dist/{UILintToolbar-5PG6WVW6.js → UILintToolbar-57XAWTGK.js} +2 -2
- package/dist/{chunk-I4C3NAUH.js → chunk-45MPASAN.js} +318 -264
- package/dist/{chunk-GFURSJEQ.js → chunk-ORYG2TNM.js} +1 -1
- package/dist/{chunk-EB6K2KGR.js → chunk-RA27RIJ2.js} +1 -1
- package/dist/{chunk-FWYNI6JG.js → chunk-SIVHTQ2P.js} +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.js +4 -4
- package/package.json +3 -2
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
"use client";
|
|
3
3
|
import {
|
|
4
4
|
useUILintContext
|
|
5
|
-
} from "./chunk-
|
|
5
|
+
} from "./chunk-45MPASAN.js";
|
|
6
6
|
|
|
7
7
|
// src/components/ui-lint/ElementBadges.tsx
|
|
8
8
|
import React, { useState, useEffect, useCallback, useMemo } from "react";
|
|
@@ -19,7 +19,16 @@ var STYLES = {
|
|
|
19
19
|
font: 'system-ui, -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif',
|
|
20
20
|
shadow: "0 2px 8px rgba(0, 0, 0, 0.3)"
|
|
21
21
|
};
|
|
22
|
-
var
|
|
22
|
+
var NEAR_DISTANCE = 0;
|
|
23
|
+
var FAR_DISTANCE = 150;
|
|
24
|
+
var MIN_SCALE = 0.5;
|
|
25
|
+
var MAX_SCALE = 1;
|
|
26
|
+
function getScaleFromDistance(distance) {
|
|
27
|
+
if (distance <= NEAR_DISTANCE) return MAX_SCALE;
|
|
28
|
+
if (distance >= FAR_DISTANCE) return MIN_SCALE;
|
|
29
|
+
const t = (distance - NEAR_DISTANCE) / (FAR_DISTANCE - NEAR_DISTANCE);
|
|
30
|
+
return MAX_SCALE - t * (MAX_SCALE - MIN_SCALE);
|
|
31
|
+
}
|
|
23
32
|
var CLUSTER_THRESHOLD = 24;
|
|
24
33
|
function getBadgeColor(issueCount) {
|
|
25
34
|
if (issueCount === 0) return STYLES.success;
|
|
@@ -29,7 +38,7 @@ function getBadgeColor(issueCount) {
|
|
|
29
38
|
function ElementBadge({
|
|
30
39
|
element,
|
|
31
40
|
issue,
|
|
32
|
-
|
|
41
|
+
distance,
|
|
33
42
|
onSelect
|
|
34
43
|
}) {
|
|
35
44
|
const [rect, setRect] = useState(null);
|
|
@@ -64,16 +73,17 @@ function ElementBadge({
|
|
|
64
73
|
if (!rect) return null;
|
|
65
74
|
if (rect.top < -50 || rect.top > window.innerHeight + 50) return null;
|
|
66
75
|
if (rect.left < -50 || rect.left > window.innerWidth + 50) return null;
|
|
76
|
+
const scale = isHovered ? 1.1 : getScaleFromDistance(distance);
|
|
67
77
|
const badgeStyle = {
|
|
68
78
|
position: "fixed",
|
|
69
79
|
top: rect.top - 8,
|
|
70
80
|
left: rect.right - 8,
|
|
71
81
|
zIndex: isHovered ? 99999 : 99995,
|
|
72
82
|
cursor: "pointer",
|
|
73
|
-
transition: "transform 0.
|
|
74
|
-
transform:
|
|
83
|
+
transition: "transform 0.1s ease-out",
|
|
84
|
+
transform: `scale(${scale})`,
|
|
85
|
+
transformOrigin: "center center"
|
|
75
86
|
};
|
|
76
|
-
const badgeColor = issue.status === "complete" ? getBadgeColor(issue.issues.length) : issue.status === "error" ? STYLES.error : issue.status === "scanning" ? STYLES.highlight : "rgba(156, 163, 175, 0.5)";
|
|
77
87
|
return /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
78
88
|
isHovered && /* @__PURE__ */ jsx(
|
|
79
89
|
"div",
|
|
@@ -93,7 +103,7 @@ function ElementBadge({
|
|
|
93
103
|
"data-ui-lint": true
|
|
94
104
|
}
|
|
95
105
|
),
|
|
96
|
-
/* @__PURE__ */
|
|
106
|
+
/* @__PURE__ */ jsxs(
|
|
97
107
|
"div",
|
|
98
108
|
{
|
|
99
109
|
style: badgeStyle,
|
|
@@ -101,32 +111,16 @@ function ElementBadge({
|
|
|
101
111
|
onMouseEnter: () => setIsHovered(true),
|
|
102
112
|
onMouseLeave: () => setIsHovered(false),
|
|
103
113
|
onClick: handleClick,
|
|
104
|
-
children:
|
|
114
|
+
children: [
|
|
105
115
|
issue.status === "scanning" && /* @__PURE__ */ jsx(ScanningBadge, {}),
|
|
106
116
|
issue.status === "complete" && /* @__PURE__ */ jsx(IssueBadge, { count: issue.issues.length }),
|
|
107
117
|
issue.status === "error" && /* @__PURE__ */ jsx(ErrorBadge, {}),
|
|
108
118
|
issue.status === "pending" && /* @__PURE__ */ jsx(PendingBadge, {})
|
|
109
|
-
]
|
|
119
|
+
]
|
|
110
120
|
}
|
|
111
121
|
)
|
|
112
122
|
] });
|
|
113
123
|
}
|
|
114
|
-
function MinimizedBadge({ color }) {
|
|
115
|
-
return /* @__PURE__ */ jsx(
|
|
116
|
-
"div",
|
|
117
|
-
{
|
|
118
|
-
style: {
|
|
119
|
-
width: "6px",
|
|
120
|
-
height: "6px",
|
|
121
|
-
borderRadius: "50%",
|
|
122
|
-
backgroundColor: color,
|
|
123
|
-
opacity: 0.7,
|
|
124
|
-
transition: "all 0.15s ease-out",
|
|
125
|
-
boxShadow: STYLES.shadow
|
|
126
|
-
}
|
|
127
|
-
}
|
|
128
|
-
);
|
|
129
|
-
}
|
|
130
124
|
function IssueBadge({ count }) {
|
|
131
125
|
const color = getBadgeColor(count);
|
|
132
126
|
if (count === 0) {
|
|
@@ -357,13 +351,12 @@ function ElementBadges() {
|
|
|
357
351
|
if (cluster.badges.length === 1) {
|
|
358
352
|
const { element, issue, x, y } = cluster.badges[0];
|
|
359
353
|
const distance = Math.hypot(x - cursorPos.x, y - cursorPos.y);
|
|
360
|
-
const isNearCursor = distance <= PROXIMITY_THRESHOLD;
|
|
361
354
|
return /* @__PURE__ */ jsx(
|
|
362
355
|
ElementBadge,
|
|
363
356
|
{
|
|
364
357
|
element,
|
|
365
358
|
issue,
|
|
366
|
-
|
|
359
|
+
distance,
|
|
367
360
|
onSelect: handleSelect
|
|
368
361
|
},
|
|
369
362
|
element.id
|
|
@@ -373,12 +366,11 @@ function ElementBadges() {
|
|
|
373
366
|
cluster.centroidX - cursorPos.x,
|
|
374
367
|
cluster.centroidY - cursorPos.y
|
|
375
368
|
);
|
|
376
|
-
const isNearCursor = distance <= PROXIMITY_THRESHOLD;
|
|
377
369
|
return /* @__PURE__ */ jsx(
|
|
378
370
|
ClusteredBadge,
|
|
379
371
|
{
|
|
380
372
|
cluster,
|
|
381
|
-
|
|
373
|
+
distance,
|
|
382
374
|
onSelect: handleSelect
|
|
383
375
|
},
|
|
384
376
|
cluster.id
|
|
@@ -387,11 +379,7 @@ function ElementBadges() {
|
|
|
387
379
|
}) });
|
|
388
380
|
return createPortal(content, document.body);
|
|
389
381
|
}
|
|
390
|
-
function ClusteredBadge({
|
|
391
|
-
cluster,
|
|
392
|
-
isNearCursor,
|
|
393
|
-
onSelect
|
|
394
|
-
}) {
|
|
382
|
+
function ClusteredBadge({ cluster, distance, onSelect }) {
|
|
395
383
|
const [isExpanded, setIsExpanded] = useState(false);
|
|
396
384
|
const [hoveredIndex, setHoveredIndex] = useState(null);
|
|
397
385
|
const closeTimeoutRef = React.useRef(null);
|
|
@@ -413,17 +401,6 @@ function ClusteredBadge({
|
|
|
413
401
|
}
|
|
414
402
|
});
|
|
415
403
|
}, [cluster.badges]);
|
|
416
|
-
const worstColor = useMemo(() => {
|
|
417
|
-
let worst = 0;
|
|
418
|
-
for (const { issue } of cluster.badges) {
|
|
419
|
-
if (issue.status === "complete") {
|
|
420
|
-
worst = Math.max(worst, issue.issues.length);
|
|
421
|
-
} else if (issue.status === "error") {
|
|
422
|
-
worst = Math.max(worst, 10);
|
|
423
|
-
}
|
|
424
|
-
}
|
|
425
|
-
return getBadgeColor(worst);
|
|
426
|
-
}, [cluster.badges]);
|
|
427
404
|
const handleMouseEnter = useCallback(() => {
|
|
428
405
|
if (closeTimeoutRef.current) {
|
|
429
406
|
clearTimeout(closeTimeoutRef.current);
|
|
@@ -484,12 +461,15 @@ function ClusteredBadge({
|
|
|
484
461
|
top: cluster.centroidY - 9,
|
|
485
462
|
left: cluster.centroidX - 9,
|
|
486
463
|
zIndex: isExpanded ? 99999 : 99995,
|
|
487
|
-
cursor: "pointer"
|
|
464
|
+
cursor: "pointer",
|
|
465
|
+
transition: "transform 0.1s ease-out",
|
|
466
|
+
transform: `scale(${isExpanded ? 1.1 : getScaleFromDistance(distance)})`,
|
|
467
|
+
transformOrigin: "center center"
|
|
488
468
|
},
|
|
489
469
|
"data-ui-lint": true,
|
|
490
470
|
onMouseEnter: handleMouseEnter,
|
|
491
471
|
onMouseLeave: handleMouseLeave,
|
|
492
|
-
children:
|
|
472
|
+
children: /* @__PURE__ */ jsx(
|
|
493
473
|
"div",
|
|
494
474
|
{
|
|
495
475
|
style: {
|
|
@@ -500,9 +480,7 @@ function ClusteredBadge({
|
|
|
500
480
|
backgroundColor: STYLES.bg,
|
|
501
481
|
boxShadow: STYLES.shadow,
|
|
502
482
|
border: `1px solid ${STYLES.border}`,
|
|
503
|
-
overflow: "hidden"
|
|
504
|
-
transition: "transform 0.15s ease-out",
|
|
505
|
-
transform: isExpanded ? "scale(1.1)" : "scale(1)"
|
|
483
|
+
overflow: "hidden"
|
|
506
484
|
},
|
|
507
485
|
children: badgeSegments.map((segment, index) => /* @__PURE__ */ jsxs(
|
|
508
486
|
"div",
|
|
@@ -560,7 +538,7 @@ function ClusteredBadge({
|
|
|
560
538
|
index
|
|
561
539
|
))
|
|
562
540
|
}
|
|
563
|
-
)
|
|
541
|
+
)
|
|
564
542
|
}
|
|
565
543
|
),
|
|
566
544
|
isExpanded && /* @__PURE__ */ jsx(
|
|
@@ -1,44 +1,5 @@
|
|
|
1
1
|
"use client";
|
|
2
2
|
|
|
3
|
-
// src/components/ui-lint/types.ts
|
|
4
|
-
var FILE_COLORS = [
|
|
5
|
-
"#3B82F6",
|
|
6
|
-
// blue
|
|
7
|
-
"#8B5CF6",
|
|
8
|
-
// violet
|
|
9
|
-
"#EC4899",
|
|
10
|
-
// pink
|
|
11
|
-
"#10B981",
|
|
12
|
-
// emerald
|
|
13
|
-
"#F59E0B",
|
|
14
|
-
// amber
|
|
15
|
-
"#06B6D4",
|
|
16
|
-
// cyan
|
|
17
|
-
"#EF4444",
|
|
18
|
-
// red
|
|
19
|
-
"#84CC16",
|
|
20
|
-
// lime
|
|
21
|
-
"#6366F1",
|
|
22
|
-
// indigo
|
|
23
|
-
"#F97316",
|
|
24
|
-
// orange
|
|
25
|
-
"#14B8A6",
|
|
26
|
-
// teal
|
|
27
|
-
"#A855F7"
|
|
28
|
-
// purple
|
|
29
|
-
];
|
|
30
|
-
var DEFAULT_SETTINGS = {
|
|
31
|
-
hideNodeModules: true,
|
|
32
|
-
autoScanEnabled: false
|
|
33
|
-
};
|
|
34
|
-
var DEFAULT_AUTO_SCAN_STATE = {
|
|
35
|
-
status: "idle",
|
|
36
|
-
currentIndex: 0,
|
|
37
|
-
totalElements: 0,
|
|
38
|
-
elements: []
|
|
39
|
-
};
|
|
40
|
-
var DATA_UILINT_ID = "data-ui-lint-id";
|
|
41
|
-
|
|
42
3
|
// src/components/ui-lint/fiber-utils.ts
|
|
43
4
|
var DATA_ATTR = "data-ui-lint-id";
|
|
44
5
|
var COLORS = [
|
|
@@ -66,6 +27,16 @@ var SKIP_TAGS = /* @__PURE__ */ new Set([
|
|
|
66
27
|
"LINK"
|
|
67
28
|
]);
|
|
68
29
|
var elementCounter = 0;
|
|
30
|
+
function generateStableId(element, source) {
|
|
31
|
+
const dataLoc = element.getAttribute("data-loc");
|
|
32
|
+
if (dataLoc) {
|
|
33
|
+
return `loc:${dataLoc}`;
|
|
34
|
+
}
|
|
35
|
+
if (source) {
|
|
36
|
+
return `src:${source.fileName}:${source.lineNumber}:${source.columnNumber ?? 0}`;
|
|
37
|
+
}
|
|
38
|
+
return `uilint-${++elementCounter}`;
|
|
39
|
+
}
|
|
69
40
|
function getFiberFromElement(element) {
|
|
70
41
|
const keys = Object.keys(element);
|
|
71
42
|
const fiberKey = keys.find((k) => k.startsWith("__reactFiber$"));
|
|
@@ -145,9 +116,6 @@ function shouldSkipElement(element) {
|
|
|
145
116
|
if (rect.width === 0 || rect.height === 0) return true;
|
|
146
117
|
return false;
|
|
147
118
|
}
|
|
148
|
-
function generateElementId() {
|
|
149
|
-
return `uilint-${++elementCounter}`;
|
|
150
|
-
}
|
|
151
119
|
function scanDOMForSources(root = document.body, hideNodeModules = true) {
|
|
152
120
|
const elements = [];
|
|
153
121
|
elementCounter = 0;
|
|
@@ -186,7 +154,7 @@ function scanDOMForSources(root = document.body, hideNodeModules = true) {
|
|
|
186
154
|
}
|
|
187
155
|
}
|
|
188
156
|
if (source) {
|
|
189
|
-
const id =
|
|
157
|
+
const id = generateStableId(node, source);
|
|
190
158
|
node.setAttribute(DATA_ATTR, id);
|
|
191
159
|
const scannedElement = {
|
|
192
160
|
id,
|
|
@@ -254,6 +222,45 @@ function buildEditorUrl(source, editor = "cursor") {
|
|
|
254
222
|
)}:${lineNumber}:${column}`;
|
|
255
223
|
}
|
|
256
224
|
|
|
225
|
+
// src/components/ui-lint/types.ts
|
|
226
|
+
var FILE_COLORS = [
|
|
227
|
+
"#3B82F6",
|
|
228
|
+
// blue
|
|
229
|
+
"#8B5CF6",
|
|
230
|
+
// violet
|
|
231
|
+
"#EC4899",
|
|
232
|
+
// pink
|
|
233
|
+
"#10B981",
|
|
234
|
+
// emerald
|
|
235
|
+
"#F59E0B",
|
|
236
|
+
// amber
|
|
237
|
+
"#06B6D4",
|
|
238
|
+
// cyan
|
|
239
|
+
"#EF4444",
|
|
240
|
+
// red
|
|
241
|
+
"#84CC16",
|
|
242
|
+
// lime
|
|
243
|
+
"#6366F1",
|
|
244
|
+
// indigo
|
|
245
|
+
"#F97316",
|
|
246
|
+
// orange
|
|
247
|
+
"#14B8A6",
|
|
248
|
+
// teal
|
|
249
|
+
"#A855F7"
|
|
250
|
+
// purple
|
|
251
|
+
];
|
|
252
|
+
var DEFAULT_SETTINGS = {
|
|
253
|
+
hideNodeModules: true,
|
|
254
|
+
autoScanEnabled: false
|
|
255
|
+
};
|
|
256
|
+
var DEFAULT_AUTO_SCAN_STATE = {
|
|
257
|
+
status: "idle",
|
|
258
|
+
currentIndex: 0,
|
|
259
|
+
totalElements: 0,
|
|
260
|
+
elements: []
|
|
261
|
+
};
|
|
262
|
+
var DATA_UILINT_ID = "data-ui-lint-id";
|
|
263
|
+
|
|
257
264
|
// src/components/ui-lint/UILintProvider.tsx
|
|
258
265
|
import {
|
|
259
266
|
createContext,
|
|
@@ -261,9 +268,210 @@ import {
|
|
|
261
268
|
useState,
|
|
262
269
|
useEffect,
|
|
263
270
|
useCallback,
|
|
264
|
-
useMemo
|
|
265
|
-
useRef
|
|
271
|
+
useMemo
|
|
266
272
|
} from "react";
|
|
273
|
+
|
|
274
|
+
// src/components/ui-lint/store.ts
|
|
275
|
+
import { create } from "zustand";
|
|
276
|
+
async function scanElementForIssues(element) {
|
|
277
|
+
if (!element.source) {
|
|
278
|
+
return {
|
|
279
|
+
elementId: element.id,
|
|
280
|
+
issues: [],
|
|
281
|
+
status: "complete"
|
|
282
|
+
};
|
|
283
|
+
}
|
|
284
|
+
try {
|
|
285
|
+
const sourceResponse = await fetch(
|
|
286
|
+
`/api/.uilint/source?path=${encodeURIComponent(element.source.fileName)}`
|
|
287
|
+
);
|
|
288
|
+
if (!sourceResponse.ok) {
|
|
289
|
+
return {
|
|
290
|
+
elementId: element.id,
|
|
291
|
+
issues: [],
|
|
292
|
+
status: "error"
|
|
293
|
+
};
|
|
294
|
+
}
|
|
295
|
+
const sourceData = await sourceResponse.json();
|
|
296
|
+
const analyzeResponse = await fetch("/api/.uilint/analyze", {
|
|
297
|
+
method: "POST",
|
|
298
|
+
headers: { "Content-Type": "application/json" },
|
|
299
|
+
body: JSON.stringify({
|
|
300
|
+
sourceCode: sourceData.content,
|
|
301
|
+
filePath: sourceData.relativePath || element.source.fileName,
|
|
302
|
+
componentName: element.componentStack[0]?.name || element.tagName,
|
|
303
|
+
componentLine: element.source.lineNumber
|
|
304
|
+
})
|
|
305
|
+
});
|
|
306
|
+
if (!analyzeResponse.ok) {
|
|
307
|
+
return {
|
|
308
|
+
elementId: element.id,
|
|
309
|
+
issues: [],
|
|
310
|
+
status: "error"
|
|
311
|
+
};
|
|
312
|
+
}
|
|
313
|
+
const result = await analyzeResponse.json();
|
|
314
|
+
return {
|
|
315
|
+
elementId: element.id,
|
|
316
|
+
issues: result.issues || [],
|
|
317
|
+
status: "complete"
|
|
318
|
+
};
|
|
319
|
+
} catch {
|
|
320
|
+
return {
|
|
321
|
+
elementId: element.id,
|
|
322
|
+
issues: [],
|
|
323
|
+
status: "error"
|
|
324
|
+
};
|
|
325
|
+
}
|
|
326
|
+
}
|
|
327
|
+
var useUILintStore = create()((set, get) => ({
|
|
328
|
+
// ============ Settings ============
|
|
329
|
+
settings: DEFAULT_SETTINGS,
|
|
330
|
+
updateSettings: (partial) => set((state) => ({
|
|
331
|
+
settings: { ...state.settings, ...partial }
|
|
332
|
+
})),
|
|
333
|
+
// ============ Locator Mode ============
|
|
334
|
+
altKeyHeld: false,
|
|
335
|
+
setAltKeyHeld: (held) => set({ altKeyHeld: held }),
|
|
336
|
+
locatorTarget: null,
|
|
337
|
+
setLocatorTarget: (target) => set({ locatorTarget: target }),
|
|
338
|
+
locatorStackIndex: 0,
|
|
339
|
+
setLocatorStackIndex: (index) => set({ locatorStackIndex: index }),
|
|
340
|
+
locatorGoUp: () => {
|
|
341
|
+
const { locatorTarget, locatorStackIndex } = get();
|
|
342
|
+
if (!locatorTarget) return;
|
|
343
|
+
const maxIndex = locatorTarget.componentStack.length;
|
|
344
|
+
set({ locatorStackIndex: Math.min(locatorStackIndex + 1, maxIndex) });
|
|
345
|
+
},
|
|
346
|
+
locatorGoDown: () => {
|
|
347
|
+
const { locatorStackIndex } = get();
|
|
348
|
+
set({ locatorStackIndex: Math.max(locatorStackIndex - 1, 0) });
|
|
349
|
+
},
|
|
350
|
+
// ============ Inspection ============
|
|
351
|
+
inspectedElement: null,
|
|
352
|
+
setInspectedElement: (el) => set({ inspectedElement: el }),
|
|
353
|
+
// ============ Auto-Scan ============
|
|
354
|
+
autoScanState: DEFAULT_AUTO_SCAN_STATE,
|
|
355
|
+
elementIssuesCache: /* @__PURE__ */ new Map(),
|
|
356
|
+
scanLock: false,
|
|
357
|
+
scanPaused: false,
|
|
358
|
+
scanAborted: false,
|
|
359
|
+
_setScanState: (partial) => set((state) => ({
|
|
360
|
+
autoScanState: { ...state.autoScanState, ...partial }
|
|
361
|
+
})),
|
|
362
|
+
updateElementIssue: (id, issue) => set((state) => {
|
|
363
|
+
const newCache = new Map(state.elementIssuesCache);
|
|
364
|
+
newCache.set(id, issue);
|
|
365
|
+
return { elementIssuesCache: newCache };
|
|
366
|
+
}),
|
|
367
|
+
startAutoScan: async (hideNodeModules) => {
|
|
368
|
+
const state = get();
|
|
369
|
+
if (state.scanLock) {
|
|
370
|
+
console.warn("UILint: Scan already in progress");
|
|
371
|
+
return;
|
|
372
|
+
}
|
|
373
|
+
set({
|
|
374
|
+
scanLock: true,
|
|
375
|
+
scanPaused: false,
|
|
376
|
+
scanAborted: false
|
|
377
|
+
});
|
|
378
|
+
const elements = scanDOMForSources(document.body, hideNodeModules);
|
|
379
|
+
const initialCache = /* @__PURE__ */ new Map();
|
|
380
|
+
for (const el of elements) {
|
|
381
|
+
initialCache.set(el.id, {
|
|
382
|
+
elementId: el.id,
|
|
383
|
+
issues: [],
|
|
384
|
+
status: "pending"
|
|
385
|
+
});
|
|
386
|
+
}
|
|
387
|
+
set({
|
|
388
|
+
elementIssuesCache: initialCache,
|
|
389
|
+
autoScanState: {
|
|
390
|
+
status: "scanning",
|
|
391
|
+
currentIndex: 0,
|
|
392
|
+
totalElements: elements.length,
|
|
393
|
+
elements
|
|
394
|
+
}
|
|
395
|
+
});
|
|
396
|
+
await get()._runScanLoop(elements, 0);
|
|
397
|
+
},
|
|
398
|
+
pauseAutoScan: () => {
|
|
399
|
+
set({ scanPaused: true });
|
|
400
|
+
get()._setScanState({ status: "paused" });
|
|
401
|
+
},
|
|
402
|
+
resumeAutoScan: () => {
|
|
403
|
+
const state = get();
|
|
404
|
+
if (state.autoScanState.status !== "paused") return;
|
|
405
|
+
set({ scanPaused: false });
|
|
406
|
+
get()._setScanState({ status: "scanning" });
|
|
407
|
+
get()._runScanLoop(
|
|
408
|
+
state.autoScanState.elements,
|
|
409
|
+
state.autoScanState.currentIndex
|
|
410
|
+
);
|
|
411
|
+
},
|
|
412
|
+
stopAutoScan: () => {
|
|
413
|
+
set({
|
|
414
|
+
scanAborted: true,
|
|
415
|
+
scanPaused: false,
|
|
416
|
+
scanLock: false,
|
|
417
|
+
autoScanState: DEFAULT_AUTO_SCAN_STATE,
|
|
418
|
+
elementIssuesCache: /* @__PURE__ */ new Map()
|
|
419
|
+
});
|
|
420
|
+
},
|
|
421
|
+
_runScanLoop: async (elements, startIndex) => {
|
|
422
|
+
for (let i = startIndex; i < elements.length; i++) {
|
|
423
|
+
if (get().scanAborted) {
|
|
424
|
+
set({
|
|
425
|
+
scanLock: false,
|
|
426
|
+
autoScanState: { ...get().autoScanState, status: "idle" }
|
|
427
|
+
});
|
|
428
|
+
return;
|
|
429
|
+
}
|
|
430
|
+
while (get().scanPaused) {
|
|
431
|
+
await new Promise((resolve) => setTimeout(resolve, 100));
|
|
432
|
+
if (get().scanAborted) {
|
|
433
|
+
set({
|
|
434
|
+
scanLock: false,
|
|
435
|
+
autoScanState: { ...get().autoScanState, status: "idle" }
|
|
436
|
+
});
|
|
437
|
+
return;
|
|
438
|
+
}
|
|
439
|
+
}
|
|
440
|
+
const element = elements[i];
|
|
441
|
+
get()._setScanState({ currentIndex: i });
|
|
442
|
+
get().updateElementIssue(element.id, {
|
|
443
|
+
elementId: element.id,
|
|
444
|
+
issues: [],
|
|
445
|
+
status: "scanning"
|
|
446
|
+
});
|
|
447
|
+
await new Promise((resolve) => requestAnimationFrame(resolve));
|
|
448
|
+
const result = await scanElementForIssues(element);
|
|
449
|
+
get().updateElementIssue(element.id, result);
|
|
450
|
+
await new Promise((resolve) => requestAnimationFrame(resolve));
|
|
451
|
+
}
|
|
452
|
+
set({
|
|
453
|
+
scanLock: false,
|
|
454
|
+
autoScanState: {
|
|
455
|
+
...get().autoScanState,
|
|
456
|
+
status: "complete",
|
|
457
|
+
currentIndex: elements.length
|
|
458
|
+
}
|
|
459
|
+
});
|
|
460
|
+
}
|
|
461
|
+
}));
|
|
462
|
+
function useEffectiveLocatorTarget() {
|
|
463
|
+
const locatorTarget = useUILintStore((s) => s.locatorTarget);
|
|
464
|
+
const locatorStackIndex = useUILintStore(
|
|
465
|
+
(s) => s.locatorStackIndex
|
|
466
|
+
);
|
|
467
|
+
if (!locatorTarget) return null;
|
|
468
|
+
return {
|
|
469
|
+
...locatorTarget,
|
|
470
|
+
stackIndex: locatorStackIndex
|
|
471
|
+
};
|
|
472
|
+
}
|
|
473
|
+
|
|
474
|
+
// src/components/ui-lint/UILintProvider.tsx
|
|
267
475
|
import { Fragment, jsx, jsxs } from "react/jsx-runtime";
|
|
268
476
|
var UILintContext = createContext(null);
|
|
269
477
|
function useUILintContext() {
|
|
@@ -280,201 +488,37 @@ function UILintProvider({
|
|
|
280
488
|
children,
|
|
281
489
|
enabled = true
|
|
282
490
|
}) {
|
|
283
|
-
const [settings, setSettings] = useState(DEFAULT_SETTINGS);
|
|
284
491
|
const [isMounted, setIsMounted] = useState(false);
|
|
285
|
-
const
|
|
286
|
-
const
|
|
287
|
-
|
|
492
|
+
const settings = useUILintStore((s) => s.settings);
|
|
493
|
+
const updateSettings = useUILintStore((s) => s.updateSettings);
|
|
494
|
+
const altKeyHeld = useUILintStore((s) => s.altKeyHeld);
|
|
495
|
+
const setAltKeyHeld = useUILintStore((s) => s.setAltKeyHeld);
|
|
496
|
+
const setLocatorTarget = useUILintStore(
|
|
497
|
+
(s) => s.setLocatorTarget
|
|
288
498
|
);
|
|
289
|
-
const
|
|
290
|
-
|
|
291
|
-
const [autoScanState, setAutoScanState] = useState(
|
|
292
|
-
DEFAULT_AUTO_SCAN_STATE
|
|
499
|
+
const locatorStackIndex = useUILintStore(
|
|
500
|
+
(s) => s.locatorStackIndex
|
|
293
501
|
);
|
|
294
|
-
const
|
|
295
|
-
|
|
296
|
-
const scanAbortRef = useRef(false);
|
|
297
|
-
const updateSettings = useCallback((partial) => {
|
|
298
|
-
setSettings((prev) => ({ ...prev, ...partial }));
|
|
299
|
-
}, []);
|
|
300
|
-
const scanElementForIssues = useCallback(
|
|
301
|
-
async (element) => {
|
|
302
|
-
if (!element.source) {
|
|
303
|
-
return {
|
|
304
|
-
elementId: element.id,
|
|
305
|
-
issues: [],
|
|
306
|
-
status: "complete"
|
|
307
|
-
};
|
|
308
|
-
}
|
|
309
|
-
try {
|
|
310
|
-
const sourceResponse = await fetch(
|
|
311
|
-
`/api/.uilint/source?path=${encodeURIComponent(
|
|
312
|
-
element.source.fileName
|
|
313
|
-
)}`
|
|
314
|
-
);
|
|
315
|
-
if (!sourceResponse.ok) {
|
|
316
|
-
return {
|
|
317
|
-
elementId: element.id,
|
|
318
|
-
issues: [],
|
|
319
|
-
status: "error"
|
|
320
|
-
};
|
|
321
|
-
}
|
|
322
|
-
const sourceData = await sourceResponse.json();
|
|
323
|
-
const analyzeResponse = await fetch("/api/.uilint/analyze", {
|
|
324
|
-
method: "POST",
|
|
325
|
-
headers: { "Content-Type": "application/json" },
|
|
326
|
-
body: JSON.stringify({
|
|
327
|
-
sourceCode: sourceData.content,
|
|
328
|
-
filePath: sourceData.relativePath || element.source.fileName,
|
|
329
|
-
componentName: element.componentStack[0]?.name || element.tagName,
|
|
330
|
-
componentLine: element.source.lineNumber
|
|
331
|
-
})
|
|
332
|
-
});
|
|
333
|
-
if (!analyzeResponse.ok) {
|
|
334
|
-
return {
|
|
335
|
-
elementId: element.id,
|
|
336
|
-
issues: [],
|
|
337
|
-
status: "error"
|
|
338
|
-
};
|
|
339
|
-
}
|
|
340
|
-
const result = await analyzeResponse.json();
|
|
341
|
-
return {
|
|
342
|
-
elementId: element.id,
|
|
343
|
-
issues: result.issues || [],
|
|
344
|
-
status: "complete"
|
|
345
|
-
};
|
|
346
|
-
} catch {
|
|
347
|
-
return {
|
|
348
|
-
elementId: element.id,
|
|
349
|
-
issues: [],
|
|
350
|
-
status: "error"
|
|
351
|
-
};
|
|
352
|
-
}
|
|
353
|
-
},
|
|
354
|
-
[]
|
|
502
|
+
const setLocatorStackIndex = useUILintStore(
|
|
503
|
+
(s) => s.setLocatorStackIndex
|
|
355
504
|
);
|
|
356
|
-
const
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
for (const el of elements) {
|
|
361
|
-
if (el.source) {
|
|
362
|
-
const file = el.source.fileName;
|
|
363
|
-
const existing = fileToElements.get(file) || [];
|
|
364
|
-
existing.push(el);
|
|
365
|
-
fileToElements.set(file, existing);
|
|
366
|
-
}
|
|
367
|
-
}
|
|
368
|
-
for (let i = startIndex; i < elements.length; i++) {
|
|
369
|
-
if (scanAbortRef.current) {
|
|
370
|
-
setAutoScanState((prev) => ({ ...prev, status: "idle" }));
|
|
371
|
-
return;
|
|
372
|
-
}
|
|
373
|
-
while (scanPausedRef.current) {
|
|
374
|
-
await new Promise((resolve) => setTimeout(resolve, 100));
|
|
375
|
-
if (scanAbortRef.current) {
|
|
376
|
-
setAutoScanState((prev) => ({ ...prev, status: "idle" }));
|
|
377
|
-
return;
|
|
378
|
-
}
|
|
379
|
-
}
|
|
380
|
-
const element = elements[i];
|
|
381
|
-
setAutoScanState((prev) => ({
|
|
382
|
-
...prev,
|
|
383
|
-
currentIndex: i
|
|
384
|
-
}));
|
|
385
|
-
if (element.source && scannedFiles.has(element.source.fileName)) {
|
|
386
|
-
const existingElements = fileToElements.get(element.source.fileName);
|
|
387
|
-
if (existingElements && existingElements.length > 0) {
|
|
388
|
-
const firstId = existingElements[0].id;
|
|
389
|
-
setElementIssuesCache((prev) => {
|
|
390
|
-
const cached = prev.get(firstId);
|
|
391
|
-
if (cached) {
|
|
392
|
-
const newCache = new Map(prev);
|
|
393
|
-
newCache.set(element.id, { ...cached, elementId: element.id });
|
|
394
|
-
return newCache;
|
|
395
|
-
}
|
|
396
|
-
return prev;
|
|
397
|
-
});
|
|
398
|
-
}
|
|
399
|
-
continue;
|
|
400
|
-
}
|
|
401
|
-
setElementIssuesCache((prev) => {
|
|
402
|
-
const newCache = new Map(prev);
|
|
403
|
-
newCache.set(element.id, {
|
|
404
|
-
elementId: element.id,
|
|
405
|
-
issues: [],
|
|
406
|
-
status: "scanning"
|
|
407
|
-
});
|
|
408
|
-
return newCache;
|
|
409
|
-
});
|
|
410
|
-
const result = await scanElementForIssues(element);
|
|
411
|
-
setElementIssuesCache((prev) => {
|
|
412
|
-
const newCache = new Map(prev);
|
|
413
|
-
newCache.set(element.id, result);
|
|
414
|
-
return newCache;
|
|
415
|
-
});
|
|
416
|
-
if (element.source) {
|
|
417
|
-
scannedFiles.add(element.source.fileName);
|
|
418
|
-
}
|
|
419
|
-
await new Promise((resolve) => setTimeout(resolve, 100));
|
|
420
|
-
}
|
|
421
|
-
setAutoScanState((prev) => ({
|
|
422
|
-
...prev,
|
|
423
|
-
status: "complete",
|
|
424
|
-
currentIndex: elements.length
|
|
425
|
-
}));
|
|
426
|
-
},
|
|
427
|
-
[scanElementForIssues]
|
|
505
|
+
const locatorGoUp = useUILintStore((s) => s.locatorGoUp);
|
|
506
|
+
const locatorGoDown = useUILintStore((s) => s.locatorGoDown);
|
|
507
|
+
const inspectedElement = useUILintStore(
|
|
508
|
+
(s) => s.inspectedElement
|
|
428
509
|
);
|
|
429
|
-
const
|
|
430
|
-
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
436
|
-
|
|
437
|
-
|
|
438
|
-
|
|
439
|
-
|
|
440
|
-
|
|
441
|
-
setElementIssuesCache(initialCache);
|
|
442
|
-
setAutoScanState({
|
|
443
|
-
status: "scanning",
|
|
444
|
-
currentIndex: 0,
|
|
445
|
-
totalElements: elements.length,
|
|
446
|
-
elements
|
|
447
|
-
});
|
|
448
|
-
runScanLoop(elements, 0);
|
|
449
|
-
}, [settings.hideNodeModules, runScanLoop]);
|
|
450
|
-
const pauseAutoScan = useCallback(() => {
|
|
451
|
-
scanPausedRef.current = true;
|
|
452
|
-
setAutoScanState((prev) => ({ ...prev, status: "paused" }));
|
|
453
|
-
}, []);
|
|
454
|
-
const resumeAutoScan = useCallback(() => {
|
|
455
|
-
scanPausedRef.current = false;
|
|
456
|
-
setAutoScanState((prev) => {
|
|
457
|
-
if (prev.status === "paused") {
|
|
458
|
-
runScanLoop(prev.elements, prev.currentIndex);
|
|
459
|
-
return { ...prev, status: "scanning" };
|
|
460
|
-
}
|
|
461
|
-
return prev;
|
|
462
|
-
});
|
|
463
|
-
}, [runScanLoop]);
|
|
464
|
-
const stopAutoScan = useCallback(() => {
|
|
465
|
-
scanAbortRef.current = true;
|
|
466
|
-
scanPausedRef.current = false;
|
|
467
|
-
setAutoScanState(DEFAULT_AUTO_SCAN_STATE);
|
|
468
|
-
setElementIssuesCache(/* @__PURE__ */ new Map());
|
|
469
|
-
}, []);
|
|
470
|
-
const locatorGoUp = useCallback(() => {
|
|
471
|
-
if (!locatorTarget) return;
|
|
472
|
-
const maxIndex = locatorTarget.componentStack.length;
|
|
473
|
-
setLocatorStackIndex((prev) => Math.min(prev + 1, maxIndex));
|
|
474
|
-
}, [locatorTarget]);
|
|
475
|
-
const locatorGoDown = useCallback(() => {
|
|
476
|
-
setLocatorStackIndex((prev) => Math.max(prev - 1, 0));
|
|
477
|
-
}, []);
|
|
510
|
+
const setInspectedElement = useUILintStore(
|
|
511
|
+
(s) => s.setInspectedElement
|
|
512
|
+
);
|
|
513
|
+
const autoScanState = useUILintStore((s) => s.autoScanState);
|
|
514
|
+
const elementIssuesCache = useUILintStore(
|
|
515
|
+
(s) => s.elementIssuesCache
|
|
516
|
+
);
|
|
517
|
+
const startAutoScan = useUILintStore((s) => s.startAutoScan);
|
|
518
|
+
const pauseAutoScan = useUILintStore((s) => s.pauseAutoScan);
|
|
519
|
+
const resumeAutoScan = useUILintStore((s) => s.resumeAutoScan);
|
|
520
|
+
const stopAutoScan = useUILintStore((s) => s.stopAutoScan);
|
|
521
|
+
const effectiveLocatorTarget = useEffectiveLocatorTarget();
|
|
478
522
|
const getLocatorTargetFromElement = useCallback(
|
|
479
523
|
(element) => {
|
|
480
524
|
if (element.closest("[data-ui-lint]")) return null;
|
|
@@ -530,31 +574,44 @@ function UILintProvider({
|
|
|
530
574
|
}
|
|
531
575
|
setLocatorTarget(null);
|
|
532
576
|
},
|
|
533
|
-
[
|
|
577
|
+
[
|
|
578
|
+
altKeyHeld,
|
|
579
|
+
inspectedElement,
|
|
580
|
+
getLocatorTargetFromElement,
|
|
581
|
+
setLocatorTarget
|
|
582
|
+
]
|
|
534
583
|
);
|
|
535
584
|
const handleLocatorClick = useCallback(
|
|
536
585
|
(e) => {
|
|
537
|
-
if (!altKeyHeld || !
|
|
586
|
+
if (!altKeyHeld || !effectiveLocatorTarget) return;
|
|
538
587
|
e.preventDefault();
|
|
539
588
|
e.stopPropagation();
|
|
540
|
-
let source =
|
|
541
|
-
if (locatorStackIndex > 0 &&
|
|
542
|
-
const stackItem =
|
|
589
|
+
let source = effectiveLocatorTarget.source;
|
|
590
|
+
if (locatorStackIndex > 0 && effectiveLocatorTarget.componentStack.length > 0) {
|
|
591
|
+
const stackItem = effectiveLocatorTarget.componentStack[locatorStackIndex - 1];
|
|
543
592
|
if (stackItem?.source) {
|
|
544
593
|
source = stackItem.source;
|
|
545
594
|
}
|
|
546
595
|
}
|
|
547
596
|
setInspectedElement({
|
|
548
|
-
element:
|
|
597
|
+
element: effectiveLocatorTarget.element,
|
|
549
598
|
source,
|
|
550
|
-
componentStack:
|
|
551
|
-
rect:
|
|
599
|
+
componentStack: effectiveLocatorTarget.componentStack,
|
|
600
|
+
rect: effectiveLocatorTarget.rect
|
|
552
601
|
});
|
|
553
602
|
setAltKeyHeld(false);
|
|
554
603
|
setLocatorTarget(null);
|
|
555
604
|
setLocatorStackIndex(0);
|
|
556
605
|
},
|
|
557
|
-
[
|
|
606
|
+
[
|
|
607
|
+
altKeyHeld,
|
|
608
|
+
effectiveLocatorTarget,
|
|
609
|
+
locatorStackIndex,
|
|
610
|
+
setInspectedElement,
|
|
611
|
+
setAltKeyHeld,
|
|
612
|
+
setLocatorTarget,
|
|
613
|
+
setLocatorStackIndex
|
|
614
|
+
]
|
|
558
615
|
);
|
|
559
616
|
useEffect(() => {
|
|
560
617
|
if (!isBrowser() || !enabled) return;
|
|
@@ -584,7 +641,7 @@ function UILintProvider({
|
|
|
584
641
|
window.removeEventListener("keyup", handleKeyUp);
|
|
585
642
|
window.removeEventListener("blur", handleBlur);
|
|
586
643
|
};
|
|
587
|
-
}, [enabled]);
|
|
644
|
+
}, [enabled, setAltKeyHeld, setLocatorTarget, setLocatorStackIndex]);
|
|
588
645
|
useEffect(() => {
|
|
589
646
|
if (!isBrowser() || !enabled) return;
|
|
590
647
|
if (!altKeyHeld && !inspectedElement) return;
|
|
@@ -606,7 +663,7 @@ function UILintProvider({
|
|
|
606
663
|
useEffect(() => {
|
|
607
664
|
if (!isBrowser() || !enabled || !altKeyHeld) return;
|
|
608
665
|
const handleWheel = (e) => {
|
|
609
|
-
if (!
|
|
666
|
+
if (!effectiveLocatorTarget) return;
|
|
610
667
|
e.preventDefault();
|
|
611
668
|
if (e.deltaY > 0) {
|
|
612
669
|
locatorGoUp();
|
|
@@ -616,7 +673,7 @@ function UILintProvider({
|
|
|
616
673
|
};
|
|
617
674
|
window.addEventListener("wheel", handleWheel, { passive: false });
|
|
618
675
|
return () => window.removeEventListener("wheel", handleWheel);
|
|
619
|
-
}, [enabled, altKeyHeld,
|
|
676
|
+
}, [enabled, altKeyHeld, effectiveLocatorTarget, locatorGoUp, locatorGoDown]);
|
|
620
677
|
useEffect(() => {
|
|
621
678
|
if (!isBrowser() || !enabled) return;
|
|
622
679
|
const handleKeyDown = (e) => {
|
|
@@ -626,17 +683,13 @@ function UILintProvider({
|
|
|
626
683
|
};
|
|
627
684
|
window.addEventListener("keydown", handleKeyDown);
|
|
628
685
|
return () => window.removeEventListener("keydown", handleKeyDown);
|
|
629
|
-
}, [enabled, inspectedElement]);
|
|
686
|
+
}, [enabled, inspectedElement, setInspectedElement]);
|
|
630
687
|
useEffect(() => {
|
|
631
688
|
setIsMounted(true);
|
|
632
689
|
}, []);
|
|
633
|
-
const
|
|
634
|
-
|
|
635
|
-
|
|
636
|
-
...locatorTarget,
|
|
637
|
-
stackIndex: locatorStackIndex
|
|
638
|
-
};
|
|
639
|
-
}, [locatorTarget, locatorStackIndex]);
|
|
690
|
+
const wrappedStartAutoScan = useCallback(() => {
|
|
691
|
+
startAutoScan(settings.hideNodeModules);
|
|
692
|
+
}, [startAutoScan, settings.hideNodeModules]);
|
|
640
693
|
const contextValue = useMemo(
|
|
641
694
|
() => ({
|
|
642
695
|
settings,
|
|
@@ -649,7 +702,7 @@ function UILintProvider({
|
|
|
649
702
|
setInspectedElement,
|
|
650
703
|
autoScanState,
|
|
651
704
|
elementIssuesCache,
|
|
652
|
-
startAutoScan,
|
|
705
|
+
startAutoScan: wrappedStartAutoScan,
|
|
653
706
|
pauseAutoScan,
|
|
654
707
|
resumeAutoScan,
|
|
655
708
|
stopAutoScan
|
|
@@ -662,9 +715,10 @@ function UILintProvider({
|
|
|
662
715
|
locatorGoUp,
|
|
663
716
|
locatorGoDown,
|
|
664
717
|
inspectedElement,
|
|
718
|
+
setInspectedElement,
|
|
665
719
|
autoScanState,
|
|
666
720
|
elementIssuesCache,
|
|
667
|
-
|
|
721
|
+
wrappedStartAutoScan,
|
|
668
722
|
pauseAutoScan,
|
|
669
723
|
resumeAutoScan,
|
|
670
724
|
stopAutoScan
|
|
@@ -681,10 +735,10 @@ function UILintUI() {
|
|
|
681
735
|
const [components, setComponents] = useState(null);
|
|
682
736
|
useEffect(() => {
|
|
683
737
|
Promise.all([
|
|
684
|
-
import("./UILintToolbar-
|
|
685
|
-
import("./InspectionPanel-
|
|
686
|
-
import("./LocatorOverlay-
|
|
687
|
-
import("./ElementBadges-
|
|
738
|
+
import("./UILintToolbar-57XAWTGK.js"),
|
|
739
|
+
import("./InspectionPanel-FRJB6CJ6.js"),
|
|
740
|
+
import("./LocatorOverlay-O4XZCAPC.js"),
|
|
741
|
+
import("./ElementBadges-2WRRHFLI.js")
|
|
688
742
|
]).then(([toolbar, panel, locator, badges]) => {
|
|
689
743
|
setComponents({
|
|
690
744
|
Toolbar: toolbar.UILintToolbar,
|
|
@@ -710,9 +764,6 @@ function UILintUI() {
|
|
|
710
764
|
}
|
|
711
765
|
|
|
712
766
|
export {
|
|
713
|
-
FILE_COLORS,
|
|
714
|
-
DEFAULT_SETTINGS,
|
|
715
|
-
DATA_UILINT_ID,
|
|
716
767
|
getFiberFromElement,
|
|
717
768
|
getDebugSource,
|
|
718
769
|
getDebugOwner,
|
|
@@ -725,6 +776,9 @@ export {
|
|
|
725
776
|
getElementById,
|
|
726
777
|
updateElementRects,
|
|
727
778
|
buildEditorUrl,
|
|
779
|
+
FILE_COLORS,
|
|
780
|
+
DEFAULT_SETTINGS,
|
|
781
|
+
DATA_UILINT_ID,
|
|
728
782
|
useUILintContext,
|
|
729
783
|
UILintProvider
|
|
730
784
|
};
|
package/dist/index.d.ts
CHANGED
package/dist/index.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
"use client";
|
|
2
2
|
import {
|
|
3
3
|
UILintToolbar
|
|
4
|
-
} from "./chunk-
|
|
4
|
+
} from "./chunk-ORYG2TNM.js";
|
|
5
5
|
import {
|
|
6
6
|
InspectionPanel,
|
|
7
7
|
clearSourceCache,
|
|
@@ -9,10 +9,10 @@ import {
|
|
|
9
9
|
fetchSourceWithContext,
|
|
10
10
|
getCachedSource,
|
|
11
11
|
prefetchSources
|
|
12
|
-
} from "./chunk-
|
|
12
|
+
} from "./chunk-SIVHTQ2P.js";
|
|
13
13
|
import {
|
|
14
14
|
LocatorOverlay
|
|
15
|
-
} from "./chunk-
|
|
15
|
+
} from "./chunk-RA27RIJ2.js";
|
|
16
16
|
import {
|
|
17
17
|
DATA_UILINT_ID,
|
|
18
18
|
DEFAULT_SETTINGS,
|
|
@@ -31,7 +31,7 @@ import {
|
|
|
31
31
|
scanDOMForSources,
|
|
32
32
|
updateElementRects,
|
|
33
33
|
useUILintContext
|
|
34
|
-
} from "./chunk-
|
|
34
|
+
} from "./chunk-45MPASAN.js";
|
|
35
35
|
|
|
36
36
|
// src/consistency/snapshot.ts
|
|
37
37
|
var DATA_ELEMENTS_ATTR = "data-elements";
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "uilint-react",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.25",
|
|
4
4
|
"description": "React component for AI-powered UI consistency checking",
|
|
5
5
|
"author": "Peter Suggate",
|
|
6
6
|
"repository": {
|
|
@@ -34,7 +34,8 @@
|
|
|
34
34
|
"node": ">=20.0.0"
|
|
35
35
|
},
|
|
36
36
|
"dependencies": {
|
|
37
|
-
"uilint-core": "^0.1.
|
|
37
|
+
"uilint-core": "^0.1.25",
|
|
38
|
+
"zustand": "^5.0.5"
|
|
38
39
|
},
|
|
39
40
|
"peerDependencies": {
|
|
40
41
|
"react": "^19.0.0",
|