@ben-million/tweaker 0.7.0 → 0.8.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/dist/index.d.ts.map +1 -1
- package/dist/index.js +125 -36
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","names":[],"sources":["../src/types.ts","../src/tweaker.tsx","../src/gray-scales.ts"],"mappings":";;;UAEiB,SAAA;EACf,KAAA;EACA,MAAA,EAAQ,MAAA;AAAA;AAAA,
|
|
1
|
+
{"version":3,"file":"index.d.ts","names":[],"sources":["../src/types.ts","../src/tweaker.tsx","../src/gray-scales.ts"],"mappings":";;;UAEiB,SAAA;EACf,KAAA;EACA,MAAA,EAAQ,MAAA;AAAA;AAAA,UA0BO,YAAA;EACf,MAAA,GAAS,MAAA,SAAe,SAAA;EACxB,WAAA;AAAA;;;cCVW,OAAA;EAAW,MAAA;EAAA;AAAA,GAAmD,YAAA,KAAY,kBAAA,CAAA,GAAA,CAAA,OAAA;;;cCpB1E,WAAA,EAAa,MAAA,SAAe,SAAA"}
|
package/dist/index.js
CHANGED
|
@@ -262,6 +262,8 @@ const applyModification = (modification, scales, scaleKey) => {
|
|
|
262
262
|
modification.element.style.paddingBottom = `${Math.max(0, paddingY)}px`;
|
|
263
263
|
modification.element.style.marginTop = paddingY < 0 ? `${paddingY}px` : modification.originalInlineMarginTop;
|
|
264
264
|
modification.element.style.marginBottom = paddingY < 0 ? `${paddingY}px` : modification.originalInlineMarginBottom;
|
|
265
|
+
if (modification.translateX !== 0 || modification.translateY !== 0) modification.element.style.transform = `translate(${modification.translateX}px, ${modification.translateY}px)`;
|
|
266
|
+
else modification.element.style.transform = modification.originalInlineTransform;
|
|
265
267
|
};
|
|
266
268
|
const restoreModification = (modification) => {
|
|
267
269
|
modification.element.style.backgroundColor = modification.originalInlineBg;
|
|
@@ -272,18 +274,35 @@ const restoreModification = (modification) => {
|
|
|
272
274
|
modification.element.style.paddingBottom = modification.originalInlinePaddingBottom;
|
|
273
275
|
modification.element.style.marginTop = modification.originalInlineMarginTop;
|
|
274
276
|
modification.element.style.marginBottom = modification.originalInlineMarginBottom;
|
|
277
|
+
modification.element.style.transform = modification.originalInlineTransform;
|
|
275
278
|
};
|
|
276
279
|
const roundToStep = (value) => parseFloat((Math.round(value * 10) / 10).toFixed(1));
|
|
277
280
|
const roundToHalf = (value) => Math.round(value * 2) / 2;
|
|
278
281
|
|
|
279
282
|
//#endregion
|
|
280
283
|
//#region src/utils/prompt.ts
|
|
284
|
+
const getLayoutContext = (element) => {
|
|
285
|
+
const parent = element.parentElement;
|
|
286
|
+
if (!parent) return "no parent";
|
|
287
|
+
const style = getComputedStyle(parent);
|
|
288
|
+
const display = style.display;
|
|
289
|
+
const parts = [display];
|
|
290
|
+
if (display === "flex" || display === "inline-flex") {
|
|
291
|
+
parts.push(style.flexDirection);
|
|
292
|
+
if (style.gap && style.gap !== "normal" && style.gap !== "0px") parts.push(`gap: ${style.gap}`);
|
|
293
|
+
}
|
|
294
|
+
if (display === "grid" || display === "inline-grid") {
|
|
295
|
+
if (style.gap && style.gap !== "normal" && style.gap !== "0px") parts.push(`gap: ${style.gap}`);
|
|
296
|
+
}
|
|
297
|
+
return parts.join(", ");
|
|
298
|
+
};
|
|
281
299
|
const generatePrompt = (modifications, scales, scaleKey) => {
|
|
282
300
|
if (modifications.length === 0) return "";
|
|
283
301
|
const scaleName = scales[scaleKey]?.label || scaleKey;
|
|
284
302
|
const colorLines = [];
|
|
285
303
|
const sizeLines = [];
|
|
286
304
|
const paddingLines = [];
|
|
305
|
+
const positionLines = [];
|
|
287
306
|
modifications.forEach((modification) => {
|
|
288
307
|
const nameParts = [modification.selector];
|
|
289
308
|
if (modification.componentName) nameParts.unshift(`<${modification.componentName}>`);
|
|
@@ -298,6 +317,18 @@ const generatePrompt = (modifications, scales, scaleKey) => {
|
|
|
298
317
|
if (modification.sourceFile) sizeLines.push(` Source: ${modification.sourceFile}`);
|
|
299
318
|
paddingLines.push(`- vertical padding of ${description} → ${Math.round(modification.paddingY)}px`);
|
|
300
319
|
if (modification.sourceFile) paddingLines.push(` Source: ${modification.sourceFile}`);
|
|
320
|
+
if (modification.translateX !== 0 || modification.translateY !== 0) {
|
|
321
|
+
const xPx = Math.abs(Math.round(modification.translateX));
|
|
322
|
+
const yPx = Math.abs(Math.round(modification.translateY));
|
|
323
|
+
const xDir = modification.translateX >= 0 ? "right" : "left";
|
|
324
|
+
const yDir = modification.translateY >= 0 ? "down" : "up";
|
|
325
|
+
const moveParts = [];
|
|
326
|
+
if (xPx > 0) moveParts.push(`${xPx}px ${xDir}`);
|
|
327
|
+
if (yPx > 0) moveParts.push(`${yPx}px ${yDir}`);
|
|
328
|
+
positionLines.push(`- move ${description} → ${moveParts.join(", ")}`);
|
|
329
|
+
positionLines.push(` Parent layout: ${getLayoutContext(modification.element)}`);
|
|
330
|
+
if (modification.sourceFile) positionLines.push(` Source: ${modification.sourceFile}`);
|
|
331
|
+
}
|
|
301
332
|
});
|
|
302
333
|
const sections = [];
|
|
303
334
|
if (colorLines.length > 0) sections.push("Change the following colors using the design system's gray scale:", "", ...colorLines);
|
|
@@ -309,6 +340,10 @@ const generatePrompt = (modifications, scales, scaleKey) => {
|
|
|
309
340
|
if (sections.length > 0) sections.push("");
|
|
310
341
|
sections.push("Change the following padding:", "", ...paddingLines);
|
|
311
342
|
}
|
|
343
|
+
if (positionLines.length > 0) {
|
|
344
|
+
if (sections.length > 0) sections.push("");
|
|
345
|
+
sections.push("Reposition the following elements (use canonical CSS like margin, padding, gap, or flexbox order — do NOT use CSS transforms):", "", ...positionLines);
|
|
346
|
+
}
|
|
312
347
|
return sections.join("\n");
|
|
313
348
|
};
|
|
314
349
|
|
|
@@ -326,6 +361,8 @@ const Tweaker = ({ scales = GRAY_SCALES, activeScale = "neutral" }) => {
|
|
|
326
361
|
const [activeIndex, setActiveIndex] = useState(-1);
|
|
327
362
|
const [inputValue, setInputValue] = useState("");
|
|
328
363
|
const [shiftHeld, setShiftHeld] = useState(false);
|
|
364
|
+
const [spaceHeld, setSpaceHeld] = useState(false);
|
|
365
|
+
const [controlHeld, setControlHeld] = useState(false);
|
|
329
366
|
const typingBuffer = useRef("");
|
|
330
367
|
const typingTimeout = useRef(void 0);
|
|
331
368
|
const activeMod = activeIndex >= 0 ? modifications[activeIndex] : null;
|
|
@@ -355,14 +392,21 @@ const Tweaker = ({ scales = GRAY_SCALES, activeScale = "neutral" }) => {
|
|
|
355
392
|
scales
|
|
356
393
|
]);
|
|
357
394
|
useEffect(() => {
|
|
358
|
-
const
|
|
395
|
+
const handleKeyDown = (event) => {
|
|
359
396
|
setShiftHeld(event.shiftKey);
|
|
397
|
+
if (event.key === " ") setSpaceHeld(true);
|
|
398
|
+
if (event.key === "Control") setControlHeld(true);
|
|
360
399
|
};
|
|
361
|
-
|
|
362
|
-
|
|
400
|
+
const handleKeyUp = (event) => {
|
|
401
|
+
setShiftHeld(event.shiftKey);
|
|
402
|
+
if (event.key === " ") setSpaceHeld(false);
|
|
403
|
+
if (event.key === "Control") setControlHeld(false);
|
|
404
|
+
};
|
|
405
|
+
document.addEventListener("keydown", handleKeyDown);
|
|
406
|
+
document.addEventListener("keyup", handleKeyUp);
|
|
363
407
|
return () => {
|
|
364
|
-
document.removeEventListener("keydown",
|
|
365
|
-
document.removeEventListener("keyup",
|
|
408
|
+
document.removeEventListener("keydown", handleKeyDown);
|
|
409
|
+
document.removeEventListener("keyup", handleKeyUp);
|
|
366
410
|
};
|
|
367
411
|
}, []);
|
|
368
412
|
useEffect(() => {
|
|
@@ -371,11 +415,15 @@ const Tweaker = ({ scales = GRAY_SCALES, activeScale = "neutral" }) => {
|
|
|
371
415
|
if (!document.pointerLockElement) return;
|
|
372
416
|
const index = activeIndexRef.current;
|
|
373
417
|
if (index < 0) return;
|
|
374
|
-
const isPadding = event.shiftKey;
|
|
375
418
|
setModifications((previous) => {
|
|
376
419
|
const updated = [...previous];
|
|
377
420
|
const current = updated[index];
|
|
378
|
-
if (
|
|
421
|
+
if (event.ctrlKey) updated[index] = {
|
|
422
|
+
...current,
|
|
423
|
+
translateX: current.translateX + event.movementX,
|
|
424
|
+
translateY: current.translateY + event.movementY
|
|
425
|
+
};
|
|
426
|
+
else if (event.shiftKey) {
|
|
379
427
|
const newPaddingY = Math.max(PADDING_MIN_PX, Math.min(PADDING_MAX_PX, current.paddingY - event.movementY * MOUSE_PADDING_SENSITIVITY));
|
|
380
428
|
updated[index] = {
|
|
381
429
|
...current,
|
|
@@ -415,7 +463,7 @@ const Tweaker = ({ scales = GRAY_SCALES, activeScale = "neutral" }) => {
|
|
|
415
463
|
setActiveIndex(-1);
|
|
416
464
|
setInputValue("");
|
|
417
465
|
}
|
|
418
|
-
if (event.key === "
|
|
466
|
+
if (event.key === "Enter") {
|
|
419
467
|
event.preventDefault();
|
|
420
468
|
releaseLock();
|
|
421
469
|
const prompt = generatePrompt(modificationsRef.current, scalesRef.current, activeScaleRef.current);
|
|
@@ -544,7 +592,7 @@ const Tweaker = ({ scales = GRAY_SCALES, activeScale = "neutral" }) => {
|
|
|
544
592
|
target.style.outlineOffset = "";
|
|
545
593
|
if (hoveredElement === target) hoveredElement = null;
|
|
546
594
|
};
|
|
547
|
-
const handleClick = (event) => {
|
|
595
|
+
const handleClick = async (event) => {
|
|
548
596
|
event.preventDefault();
|
|
549
597
|
event.stopPropagation();
|
|
550
598
|
const target = event.target;
|
|
@@ -560,11 +608,26 @@ const Tweaker = ({ scales = GRAY_SCALES, activeScale = "neutral" }) => {
|
|
|
560
608
|
const position = findClosestPosition(scales, activeScale, defaultProperty === "bg" ? rgbToOklch(bgRed, bgGreen, bgBlue) : defaultProperty === "border" ? rgbToOklch(borderRed, borderGreen, borderBlue) : rgbToOklch(textRed, textGreen, textBlue));
|
|
561
609
|
const currentSize = parseFloat(computed.fontSize) || 16;
|
|
562
610
|
const currentPaddingY = parseFloat(computed.paddingTop) || 0;
|
|
611
|
+
let componentName = null;
|
|
612
|
+
let sourceFile = null;
|
|
613
|
+
try {
|
|
614
|
+
const reactGrab = window.__REACT_GRAB_MODULE__;
|
|
615
|
+
if (reactGrab?.getStack) {
|
|
616
|
+
const stack = await reactGrab.getStack(target);
|
|
617
|
+
if (stack) {
|
|
618
|
+
for (const frame of stack) if (frame.fileName && !frame.fileName.includes("node_modules")) {
|
|
619
|
+
sourceFile = frame.fileName;
|
|
620
|
+
if (frame.functionName && /^[A-Z]/.test(frame.functionName)) componentName = frame.functionName;
|
|
621
|
+
break;
|
|
622
|
+
}
|
|
623
|
+
}
|
|
624
|
+
}
|
|
625
|
+
} catch {}
|
|
563
626
|
const newModification = {
|
|
564
627
|
element: target,
|
|
565
628
|
selector: getSelector(target),
|
|
566
|
-
componentName
|
|
567
|
-
sourceFile
|
|
629
|
+
componentName,
|
|
630
|
+
sourceFile,
|
|
568
631
|
textPreview: getTextPreview(target),
|
|
569
632
|
originalInlineBg: target.style.backgroundColor,
|
|
570
633
|
originalInlineColor: target.style.color,
|
|
@@ -574,10 +637,13 @@ const Tweaker = ({ scales = GRAY_SCALES, activeScale = "neutral" }) => {
|
|
|
574
637
|
originalInlinePaddingBottom: target.style.paddingBottom,
|
|
575
638
|
originalInlineMarginTop: target.style.marginTop,
|
|
576
639
|
originalInlineMarginBottom: target.style.marginBottom,
|
|
640
|
+
originalInlineTransform: target.style.transform,
|
|
577
641
|
property: defaultProperty,
|
|
578
642
|
position,
|
|
579
643
|
fontSize: currentSize,
|
|
580
|
-
paddingY: currentPaddingY
|
|
644
|
+
paddingY: currentPaddingY,
|
|
645
|
+
translateX: 0,
|
|
646
|
+
translateY: 0
|
|
581
647
|
};
|
|
582
648
|
setModifications((previous) => [...previous, newModification]);
|
|
583
649
|
setActiveIndex(modifications.length);
|
|
@@ -605,7 +671,8 @@ const Tweaker = ({ scales = GRAY_SCALES, activeScale = "neutral" }) => {
|
|
|
605
671
|
const fillColor = activeMod ? oklchToCssString(getColorAtPosition(scales, activeScale, activeMod.position)) : scales[activeScale]?.shades["500"] ?? "rgba(255,255,255,0.3)";
|
|
606
672
|
const propertyLabel = activeMod?.property === "text" ? "F" : activeMod?.property === "border" ? "D" : "B";
|
|
607
673
|
const isPaddingMode = shiftHeld && hasModifications && !picking;
|
|
608
|
-
const
|
|
674
|
+
const isDragMode = controlHeld && hasModifications && !picking;
|
|
675
|
+
const guideRect = activeMod && !picking && !spaceHeld ? activeMod.element.getBoundingClientRect() : null;
|
|
609
676
|
const thumbX = activeMod ? isPaddingMode ? (MINIMAP_WIDTH_PX - THUMB_SIZE_PX) / 2 : (activeMod.fontSize - FONT_SIZE_MIN_PX) / (FONT_SIZE_MAX_PX - FONT_SIZE_MIN_PX) * (MINIMAP_WIDTH_PX - THUMB_SIZE_PX) : 0;
|
|
610
677
|
const thumbY = activeMod ? isPaddingMode ? (1 - (activeMod.paddingY - PADDING_MIN_PX) / (PADDING_MAX_PX - PADDING_MIN_PX)) * (MINIMAP_HEIGHT_PX - THUMB_SIZE_PX) : (1 - activeMod.position / SLIDER_MAX) * (MINIMAP_HEIGHT_PX - THUMB_SIZE_PX) : MINIMAP_HEIGHT_PX - THUMB_SIZE_PX;
|
|
611
678
|
return /* @__PURE__ */ jsxs(Fragment, { children: [guideRect && activeMod && /* @__PURE__ */ jsxs("div", {
|
|
@@ -649,21 +716,36 @@ const Tweaker = ({ scales = GRAY_SCALES, activeScale = "neutral" }) => {
|
|
|
649
716
|
gap: 4,
|
|
650
717
|
pointerEvents: "none"
|
|
651
718
|
},
|
|
652
|
-
children: [
|
|
653
|
-
|
|
654
|
-
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
658
|
-
|
|
659
|
-
|
|
660
|
-
|
|
661
|
-
|
|
662
|
-
|
|
663
|
-
|
|
664
|
-
|
|
665
|
-
|
|
666
|
-
|
|
719
|
+
children: [
|
|
720
|
+
/* @__PURE__ */ jsxs("span", {
|
|
721
|
+
style: guidelineLabelStyle,
|
|
722
|
+
children: [
|
|
723
|
+
"↕ ",
|
|
724
|
+
activeMod.paddingY,
|
|
725
|
+
"px"
|
|
726
|
+
]
|
|
727
|
+
}),
|
|
728
|
+
/* @__PURE__ */ jsxs("span", {
|
|
729
|
+
style: {
|
|
730
|
+
...guidelineLabelStyle,
|
|
731
|
+
color: "rgba(59, 130, 246, 0.8)",
|
|
732
|
+
background: "rgba(59, 130, 246, 0.06)"
|
|
733
|
+
},
|
|
734
|
+
children: [activeMod.fontSize, "px"]
|
|
735
|
+
}),
|
|
736
|
+
(activeMod.translateX !== 0 || activeMod.translateY !== 0) && /* @__PURE__ */ jsxs("span", {
|
|
737
|
+
style: {
|
|
738
|
+
...guidelineLabelStyle,
|
|
739
|
+
color: "rgba(168, 85, 247, 0.9)",
|
|
740
|
+
background: "rgba(168, 85, 247, 0.08)"
|
|
741
|
+
},
|
|
742
|
+
children: [
|
|
743
|
+
Math.round(activeMod.translateX),
|
|
744
|
+
", ",
|
|
745
|
+
Math.round(activeMod.translateY)
|
|
746
|
+
]
|
|
747
|
+
})
|
|
748
|
+
]
|
|
667
749
|
})
|
|
668
750
|
]
|
|
669
751
|
}), /* @__PURE__ */ jsx(AnimatePresence, { children: (hasModifications || picking) && /* @__PURE__ */ jsxs(motion.div, {
|
|
@@ -702,18 +784,25 @@ const Tweaker = ({ scales = GRAY_SCALES, activeScale = "neutral" }) => {
|
|
|
702
784
|
style: minimapModeStyle,
|
|
703
785
|
children: /* @__PURE__ */ jsx("span", {
|
|
704
786
|
style: minimapLabelStyle,
|
|
705
|
-
children: isPaddingMode ? "⇧ Padding" : "Style"
|
|
787
|
+
children: isDragMode ? "⌃ Move" : isPaddingMode ? "⇧ Padding" : "Style"
|
|
706
788
|
})
|
|
707
789
|
}),
|
|
708
790
|
/* @__PURE__ */ jsxs("div", {
|
|
709
791
|
style: minimapValuesStyle,
|
|
710
|
-
children: [
|
|
711
|
-
|
|
712
|
-
|
|
713
|
-
|
|
714
|
-
|
|
715
|
-
|
|
716
|
-
|
|
792
|
+
children: [
|
|
793
|
+
/* @__PURE__ */ jsx("span", {
|
|
794
|
+
style: minimapLabelStyle,
|
|
795
|
+
children: picking ? "Picking…" : isDragMode ? `x: ${activeMod?.translateX ?? 0}` : isPaddingMode ? `↕ ${activeMod?.paddingY ?? 0}px` : `${propertyLabel} ${inputValue || "0"}`
|
|
796
|
+
}),
|
|
797
|
+
!picking && activeMod && isDragMode && /* @__PURE__ */ jsx("span", {
|
|
798
|
+
style: minimapLabelStyle,
|
|
799
|
+
children: `y: ${activeMod.translateY}`
|
|
800
|
+
}),
|
|
801
|
+
!picking && activeMod && !isPaddingMode && !isDragMode && /* @__PURE__ */ jsx("span", {
|
|
802
|
+
style: minimapLabelStyle,
|
|
803
|
+
children: `${activeMod.fontSize}px`
|
|
804
|
+
})
|
|
805
|
+
]
|
|
717
806
|
})
|
|
718
807
|
]
|
|
719
808
|
}, "minimap") })] });
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","names":[],"sources":["../src/gray-scales.ts","../src/constants.ts","../src/utils/color.ts","../src/utils/dom.ts","../src/utils/modification.ts","../src/utils/prompt.ts","../src/tweaker.tsx"],"sourcesContent":["import type { GrayScale } from \"./types\";\n\nexport const GRAY_SCALES: Record<string, GrayScale> = {\n neutral: {\n label: \"Neutral\",\n shades: {\n \"50\": \"oklch(0.985 0 0)\",\n \"100\": \"oklch(0.97 0 0)\",\n \"200\": \"oklch(0.922 0 0)\",\n \"300\": \"oklch(0.87 0 0)\",\n \"400\": \"oklch(0.708 0 0)\",\n \"500\": \"oklch(0.556 0 0)\",\n \"600\": \"oklch(0.439 0 0)\",\n \"700\": \"oklch(0.371 0 0)\",\n \"800\": \"oklch(0.269 0 0)\",\n \"900\": \"oklch(0.205 0 0)\",\n \"950\": \"oklch(0.145 0 0)\",\n },\n },\n slate: {\n label: \"Slate\",\n shades: {\n \"50\": \"oklch(0.984 0.003 247.858)\",\n \"100\": \"oklch(0.968 0.007 247.896)\",\n \"200\": \"oklch(0.929 0.013 255.508)\",\n \"300\": \"oklch(0.869 0.022 252.894)\",\n \"400\": \"oklch(0.704 0.04 256.788)\",\n \"500\": \"oklch(0.554 0.046 257.417)\",\n \"600\": \"oklch(0.446 0.043 257.281)\",\n \"700\": \"oklch(0.372 0.044 257.287)\",\n \"800\": \"oklch(0.279 0.041 260.031)\",\n \"900\": \"oklch(0.208 0.042 265.755)\",\n \"950\": \"oklch(0.129 0.042 264.695)\",\n },\n },\n gray: {\n label: \"Gray\",\n shades: {\n \"50\": \"oklch(0.985 0.002 247.839)\",\n \"100\": \"oklch(0.967 0.003 264.542)\",\n \"200\": \"oklch(0.928 0.006 264.531)\",\n \"300\": \"oklch(0.872 0.01 258.338)\",\n \"400\": \"oklch(0.707 0.022 261.325)\",\n \"500\": \"oklch(0.551 0.027 264.364)\",\n \"600\": \"oklch(0.446 0.03 256.802)\",\n \"700\": \"oklch(0.373 0.034 259.733)\",\n \"800\": \"oklch(0.278 0.033 256.848)\",\n \"900\": \"oklch(0.21 0.034 264.665)\",\n \"950\": \"oklch(0.13 0.028 261.692)\",\n },\n },\n zinc: {\n label: \"Zinc\",\n shades: {\n \"50\": \"oklch(0.985 0 0)\",\n \"100\": \"oklch(0.967 0.001 286.375)\",\n \"200\": \"oklch(0.92 0.004 286.32)\",\n \"300\": \"oklch(0.871 0.006 286.286)\",\n \"400\": \"oklch(0.705 0.015 286.067)\",\n \"500\": \"oklch(0.552 0.016 285.938)\",\n \"600\": \"oklch(0.442 0.017 285.786)\",\n \"700\": \"oklch(0.37 0.013 285.805)\",\n \"800\": \"oklch(0.274 0.006 286.033)\",\n \"900\": \"oklch(0.21 0.006 285.885)\",\n \"950\": \"oklch(0.141 0.005 285.823)\",\n },\n },\n stone: {\n label: \"Stone\",\n shades: {\n \"50\": \"oklch(0.985 0.001 106.423)\",\n \"100\": \"oklch(0.97 0.001 106.424)\",\n \"200\": \"oklch(0.923 0.003 48.717)\",\n \"300\": \"oklch(0.869 0.005 56.366)\",\n \"400\": \"oklch(0.709 0.01 56.259)\",\n \"500\": \"oklch(0.553 0.013 58.071)\",\n \"600\": \"oklch(0.444 0.011 73.639)\",\n \"700\": \"oklch(0.374 0.01 67.558)\",\n \"800\": \"oklch(0.268 0.007 34.298)\",\n \"900\": \"oklch(0.216 0.006 56.043)\",\n \"950\": \"oklch(0.147 0.004 49.25)\",\n },\n },\n mauve: {\n label: \"Mauve\",\n shades: {\n \"50\": \"oklch(0.985 0.003 310)\",\n \"100\": \"oklch(0.968 0.006 310)\",\n \"200\": \"oklch(0.925 0.011 310)\",\n \"300\": \"oklch(0.87 0.017 310)\",\n \"400\": \"oklch(0.708 0.03 310)\",\n \"500\": \"oklch(0.556 0.03 310)\",\n \"600\": \"oklch(0.44 0.028 310)\",\n \"700\": \"oklch(0.372 0.025 310)\",\n \"800\": \"oklch(0.27 0.02 310)\",\n \"900\": \"oklch(0.208 0.018 310)\",\n \"950\": \"oklch(0.145 0.014 310)\",\n },\n },\n olive: {\n label: \"Olive\",\n shades: {\n \"50\": \"oklch(0.985 0.003 130)\",\n \"100\": \"oklch(0.968 0.006 130)\",\n \"200\": \"oklch(0.925 0.011 130)\",\n \"300\": \"oklch(0.87 0.017 130)\",\n \"400\": \"oklch(0.708 0.028 130)\",\n \"500\": \"oklch(0.556 0.028 130)\",\n \"600\": \"oklch(0.44 0.024 130)\",\n \"700\": \"oklch(0.372 0.02 130)\",\n \"800\": \"oklch(0.27 0.016 130)\",\n \"900\": \"oklch(0.208 0.014 130)\",\n \"950\": \"oklch(0.145 0.01 130)\",\n },\n },\n};\n","export const SLIDER_MAX = 10;\nexport const TEXT_PREVIEW_MAX_LENGTH = 30;\nexport const TYPING_RESET_DELAY_MS = 1500;\nexport const SHADE_KEYS = [\"50\", \"100\", \"200\", \"300\", \"400\", \"500\", \"600\", \"700\", \"800\", \"900\", \"950\"];\nexport const FONT_SIZE_MIN_PX = 1;\nexport const FONT_SIZE_MAX_PX = 200;\nexport const PADDING_MIN_PX = -200;\nexport const PADDING_MAX_PX = 200;\nexport const MOUSE_COLOR_SENSITIVITY = 0.02;\nexport const MOUSE_SIZE_SENSITIVITY = 0.1;\nexport const MOUSE_PADDING_SENSITIVITY = 0.2;\nexport const MINIMAP_WIDTH_PX = 160;\nexport const MINIMAP_HEIGHT_PX = 100;\nexport const THUMB_SIZE_PX = 10;\n","import type { OKLCH } from \"../types\";\nimport { SHADE_KEYS, SLIDER_MAX } from \"../constants\";\nimport type { GrayScale } from \"../types\";\n\nexport const parseOklch = (oklchStr: string): OKLCH => {\n const match = oklchStr.match(/oklch\\(([\\d.]+)\\s+([\\d.]+)\\s+([\\d.]+)\\)/);\n if (!match) return [0, 0, 0];\n return [Number(match[1]), Number(match[2]), Number(match[3])];\n};\n\nexport const lerpOklch = (colorA: OKLCH, colorB: OKLCH, interpolation: number): OKLCH => [\n colorA[0] + (colorB[0] - colorA[0]) * interpolation,\n colorA[1] + (colorB[1] - colorA[1]) * interpolation,\n colorA[2] + (colorB[2] - colorA[2]) * interpolation,\n];\n\nexport const formatOklch = (oklch: OKLCH): string =>\n `oklch(${oklch[0].toFixed(3)} ${oklch[1].toFixed(3)} ${oklch[2].toFixed(1)})`;\n\nexport const oklchToCssString = (oklch: OKLCH): string =>\n `oklch(${oklch[0]} ${oklch[1]} ${oklch[2]})`;\n\nexport const getColorAtPosition = (scales: Record<string, GrayScale>, scaleKey: string, position: number): OKLCH => {\n const scale = scales[scaleKey];\n if (!scale) return [0.5, 0, 0];\n\n const inverted = SLIDER_MAX - position;\n const segment = (inverted / SLIDER_MAX) * (SHADE_KEYS.length - 1);\n const index = Math.min(Math.floor(segment), SHADE_KEYS.length - 2);\n const interpolation = segment - index;\n\n const lower = parseOklch(scale.shades[SHADE_KEYS[index]]);\n const upper = parseOklch(scale.shades[SHADE_KEYS[index + 1]]);\n\n return lerpOklch(lower, upper, interpolation);\n};\n\nexport const getClosestShadeLabel = (position: number): string => {\n const inverted = SLIDER_MAX - position;\n const segment = (inverted / SLIDER_MAX) * (SHADE_KEYS.length - 1);\n const index = Math.round(segment);\n return SHADE_KEYS[Math.min(index, SHADE_KEYS.length - 1)];\n};\n\nexport const parseRgb = (color: string): [number, number, number, number] => {\n const match = color.match(\n /rgba?\\(\\s*([\\d.]+),\\s*([\\d.]+),\\s*([\\d.]+)(?:,\\s*([\\d.]+))?\\s*\\)/\n );\n if (!match) return [0, 0, 0, 0];\n return [\n Number(match[1]),\n Number(match[2]),\n Number(match[3]),\n match[4] !== undefined ? Number(match[4]) : 1,\n ];\n};\n\nexport const rgbToOklch = (red: number, green: number, blue: number): OKLCH => {\n const linearize = (channel: number): number => {\n const normalized = channel / 255;\n return normalized <= 0.04045\n ? normalized / 12.92\n : Math.pow((normalized + 0.055) / 1.055, 2.4);\n };\n const linearRed = linearize(red);\n const linearGreen = linearize(green);\n const linearBlue = linearize(blue);\n\n const lmsL = Math.cbrt(0.4122214708 * linearRed + 0.5363325363 * linearGreen + 0.0514459929 * linearBlue);\n const lmsM = Math.cbrt(0.2119034982 * linearRed + 0.6806995451 * linearGreen + 0.1073969566 * linearBlue);\n const lmsS = Math.cbrt(0.0883024619 * linearRed + 0.2817188376 * linearGreen + 0.6299787005 * linearBlue);\n\n const lightness = 0.2104542553 * lmsL + 0.793617785 * lmsM - 0.0040720468 * lmsS;\n const labA = 1.9779984951 * lmsL - 2.428592205 * lmsM + 0.4505937099 * lmsS;\n const labB = 0.0259040371 * lmsL + 0.7827717662 * lmsM - 0.808675766 * lmsS;\n\n const chroma = Math.sqrt(labA * labA + labB * labB);\n const hue = Math.atan2(labB, labA) * (180 / Math.PI);\n\n return [lightness, chroma, hue < 0 ? hue + 360 : hue];\n};\n\nexport const findClosestPosition = (scales: Record<string, GrayScale>, scaleKey: string, targetOklch: OKLCH): number => {\n let bestPosition = 0;\n let bestDistance = Infinity;\n\n for (let position = 0; position <= SLIDER_MAX; position++) {\n const color = getColorAtPosition(scales, scaleKey, position);\n const distance =\n (color[0] - targetOklch[0]) ** 2 +\n (color[1] - targetOklch[1]) ** 2 +\n ((color[2] - targetOklch[2]) / 360) ** 2;\n if (distance < bestDistance) {\n bestDistance = distance;\n bestPosition = position;\n }\n }\n\n return bestPosition;\n};\n","import { TEXT_PREVIEW_MAX_LENGTH } from \"../constants\";\n\nexport const getSelector = (element: HTMLElement): string => {\n const tag = element.tagName.toLowerCase();\n const classes = Array.from(element.classList)\n .filter((className) => !className.startsWith(\"__\"))\n .slice(0, 2)\n .join(\".\");\n return classes ? `${tag}.${classes}` : tag;\n};\n\nexport const getTextPreview = (element: HTMLElement): string => {\n const text = element.textContent?.trim() || \"\";\n return text.length > TEXT_PREVIEW_MAX_LENGTH\n ? `${text.slice(0, TEXT_PREVIEW_MAX_LENGTH)}…`\n : text;\n};\n","import type { GrayScale, Modification } from \"../types\";\nimport { getColorAtPosition, oklchToCssString } from \"./color\";\n\nexport const applyModification = (\n modification: Modification,\n scales: Record<string, GrayScale>,\n scaleKey: string,\n) => {\n const oklch = getColorAtPosition(scales, scaleKey, modification.position);\n const colorValue = oklchToCssString(oklch);\n if (modification.property === \"bg\") {\n modification.element.style.backgroundColor = colorValue;\n } else if (modification.property === \"text\") {\n modification.element.style.color = colorValue;\n } else {\n modification.element.style.borderColor = colorValue;\n }\n modification.element.style.fontSize = `${modification.fontSize}px`;\n\n const paddingY = Math.round(modification.paddingY);\n\n modification.element.style.paddingTop = `${Math.max(0, paddingY)}px`;\n modification.element.style.paddingBottom = `${Math.max(0, paddingY)}px`;\n\n modification.element.style.marginTop = paddingY < 0 ? `${paddingY}px` : modification.originalInlineMarginTop;\n modification.element.style.marginBottom = paddingY < 0 ? `${paddingY}px` : modification.originalInlineMarginBottom;\n};\n\nexport const restoreModification = (modification: Modification) => {\n modification.element.style.backgroundColor = modification.originalInlineBg;\n modification.element.style.color = modification.originalInlineColor;\n modification.element.style.borderColor = modification.originalInlineBorderColor;\n modification.element.style.fontSize = modification.originalInlineFontSize;\n modification.element.style.paddingTop = modification.originalInlinePaddingTop;\n modification.element.style.paddingBottom = modification.originalInlinePaddingBottom;\n modification.element.style.marginTop = modification.originalInlineMarginTop;\n modification.element.style.marginBottom = modification.originalInlineMarginBottom;\n};\n\nexport const roundToStep = (value: number): number =>\n parseFloat((Math.round(value * 10) / 10).toFixed(1));\n\nexport const roundToHalf = (value: number): number =>\n Math.round(value * 2) / 2;\n","import type { GrayScale, Modification } from \"../types\";\nimport { formatOklch, getColorAtPosition, getClosestShadeLabel } from \"./color\";\n\nexport const generatePrompt = (\n modifications: Modification[],\n scales: Record<string, GrayScale>,\n scaleKey: string,\n): string => {\n if (modifications.length === 0) return \"\";\n\n const scaleName = scales[scaleKey]?.label || scaleKey;\n const colorLines: string[] = [];\n const sizeLines: string[] = [];\n const paddingLines: string[] = [];\n\n modifications.forEach((modification) => {\n const nameParts = [modification.selector];\n if (modification.componentName) nameParts.unshift(`<${modification.componentName}>`);\n if (modification.textPreview) nameParts.push(`(\"${modification.textPreview}\")`);\n const description = nameParts.join(\" \");\n\n const shade = getClosestShadeLabel(modification.position);\n const oklch = getColorAtPosition(scales, scaleKey, modification.position);\n const property =\n modification.property === \"bg\"\n ? \"background color\"\n : modification.property === \"text\"\n ? \"text color\"\n : \"border color\";\n colorLines.push(`- ${property} of ${description} → ${scaleName} ${shade} (${formatOklch(oklch)})`);\n if (modification.sourceFile) colorLines.push(` Source: ${modification.sourceFile}`);\n\n sizeLines.push(`- font-size of ${description} → ${modification.fontSize}px`);\n if (modification.sourceFile) sizeLines.push(` Source: ${modification.sourceFile}`);\n\n paddingLines.push(`- vertical padding of ${description} → ${Math.round(modification.paddingY)}px`);\n if (modification.sourceFile) paddingLines.push(` Source: ${modification.sourceFile}`);\n });\n\n const sections: string[] = [];\n\n if (colorLines.length > 0) {\n sections.push(\n \"Change the following colors using the design system's gray scale:\",\n \"\",\n ...colorLines,\n );\n }\n\n if (sizeLines.length > 0) {\n if (sections.length > 0) sections.push(\"\");\n sections.push(\"Change the following font sizes:\", \"\", ...sizeLines);\n }\n\n if (paddingLines.length > 0) {\n if (sections.length > 0) sections.push(\"\");\n sections.push(\"Change the following padding:\", \"\", ...paddingLines);\n }\n\n return sections.join(\"\\n\");\n};\n","import { useState, useCallback, useEffect, useRef } from \"react\";\nimport { motion, AnimatePresence } from \"motion/react\";\nimport type { Modification, TweakerProps } from \"./types\";\nimport { GRAY_SCALES } from \"./gray-scales\";\nimport { SLIDER_MAX, TYPING_RESET_DELAY_MS, FONT_SIZE_MIN_PX, FONT_SIZE_MAX_PX, PADDING_MIN_PX, PADDING_MAX_PX, MOUSE_COLOR_SENSITIVITY, MOUSE_SIZE_SENSITIVITY, MOUSE_PADDING_SENSITIVITY, MINIMAP_WIDTH_PX, MINIMAP_HEIGHT_PX, THUMB_SIZE_PX } from \"./constants\";\nimport { getColorAtPosition, oklchToCssString, parseRgb, rgbToOklch, findClosestPosition } from \"./utils/color\";\nimport { getSelector, getTextPreview } from \"./utils/dom\";\nimport { applyModification, restoreModification, roundToStep, roundToHalf } from \"./utils/modification\";\nimport { generatePrompt } from \"./utils/prompt\";\n\nconst requestLock = () => {\n if (!document.pointerLockElement) {\n document.body.requestPointerLock();\n }\n};\n\nconst releaseLock = () => {\n if (document.pointerLockElement) {\n document.exitPointerLock();\n }\n};\n\nexport const Tweaker = ({ scales = GRAY_SCALES, activeScale = \"neutral\" }: TweakerProps) => {\n const [picking, setPicking] = useState(false);\n const [modifications, setModifications] = useState<Modification[]>([]);\n const [activeIndex, setActiveIndex] = useState(-1);\n const [inputValue, setInputValue] = useState(\"\");\n const [shiftHeld, setShiftHeld] = useState(false);\n const typingBuffer = useRef(\"\");\n const typingTimeout = useRef<ReturnType<typeof setTimeout>>(undefined);\n\n const activeMod = activeIndex >= 0 ? modifications[activeIndex] : null;\n const hasModifications = modifications.length > 0;\n\n const activeIndexRef = useRef(activeIndex);\n const activeScaleRef = useRef(activeScale);\n const modificationsRef = useRef(modifications);\n const scalesRef = useRef(scales);\n activeIndexRef.current = activeIndex;\n activeScaleRef.current = activeScale;\n modificationsRef.current = modifications;\n scalesRef.current = scales;\n\n const updateActivePosition = useCallback(\n (newPosition: number) => {\n if (activeIndex < 0) return;\n setModifications((previous) => {\n const updated = [...previous];\n updated[activeIndex] = { ...updated[activeIndex], position: newPosition };\n applyModification(updated[activeIndex], scales, activeScale);\n return updated;\n });\n },\n [activeIndex, activeScale, scales],\n );\n\n useEffect(() => {\n const handleShift = (event: KeyboardEvent) => {\n setShiftHeld(event.shiftKey);\n };\n document.addEventListener(\"keydown\", handleShift);\n document.addEventListener(\"keyup\", handleShift);\n return () => {\n document.removeEventListener(\"keydown\", handleShift);\n document.removeEventListener(\"keyup\", handleShift);\n };\n }, []);\n\n useEffect(() => {\n if (!hasModifications || picking) return;\n\n const handleMouseMove = (event: MouseEvent) => {\n if (!document.pointerLockElement) return;\n const index = activeIndexRef.current;\n if (index < 0) return;\n\n const isPadding = event.shiftKey;\n\n setModifications((previous) => {\n const updated = [...previous];\n const current = updated[index];\n\n if (isPadding) {\n const newPaddingY = Math.max(PADDING_MIN_PX, Math.min(PADDING_MAX_PX, current.paddingY - event.movementY * MOUSE_PADDING_SENSITIVITY));\n updated[index] = { ...current, paddingY: Math.round(newPaddingY) };\n } else {\n const newPosition = Math.max(0, Math.min(SLIDER_MAX, current.position - event.movementY * MOUSE_COLOR_SENSITIVITY));\n const newSize = Math.max(FONT_SIZE_MIN_PX, Math.min(FONT_SIZE_MAX_PX, current.fontSize + event.movementX * MOUSE_SIZE_SENSITIVITY));\n updated[index] = { ...current, position: roundToStep(newPosition), fontSize: roundToHalf(newSize) };\n }\n\n applyModification(updated[index], scalesRef.current, activeScaleRef.current);\n setInputValue(String(updated[index].position));\n return updated;\n });\n };\n\n requestLock();\n document.addEventListener(\"mousemove\", handleMouseMove, true);\n return () => {\n document.removeEventListener(\"mousemove\", handleMouseMove, true);\n releaseLock();\n };\n }, [hasModifications, picking]);\n\n useEffect(() => {\n if (!hasModifications) return;\n\n const handleKeyDown = (event: KeyboardEvent) => {\n if (event.key === \"Escape\") {\n event.preventDefault();\n releaseLock();\n const prompt = generatePrompt(modificationsRef.current, scalesRef.current, activeScaleRef.current);\n navigator.clipboard.writeText(prompt);\n modificationsRef.current.forEach(restoreModification);\n setModifications([]);\n setActiveIndex(-1);\n setInputValue(\"\");\n }\n\n if (event.key === \" \") {\n event.preventDefault();\n releaseLock();\n const prompt = generatePrompt(modificationsRef.current, scalesRef.current, activeScaleRef.current);\n navigator.clipboard.writeText(prompt);\n setPicking(true);\n }\n };\n\n document.addEventListener(\"keydown\", handleKeyDown);\n return () => document.removeEventListener(\"keydown\", handleKeyDown);\n }, [hasModifications]);\n\n useEffect(() => {\n if (!activeMod || picking) return;\n\n const handleKeyDown = (event: KeyboardEvent) => {\n const target = event.target as HTMLElement;\n if (target.tagName === \"INPUT\" || target.tagName === \"TEXTAREA\") return;\n if (event.key === \"Escape\") return;\n\n if ((event.key >= \"0\" && event.key <= \"9\") || event.key === \".\") {\n event.preventDefault();\n const next = typingBuffer.current + event.key;\n\n if (event.key === \".\" && typingBuffer.current.includes(\".\")) return;\n\n const hasDecimal = typingBuffer.current.includes(\".\");\n if (hasDecimal && event.key !== \".\" && typingBuffer.current.split(\".\")[1]?.length >= 1) {\n return;\n }\n\n const parsed = parseFloat(next);\n if (!isNaN(parsed) && parsed > SLIDER_MAX) {\n typingBuffer.current = event.key === \".\" ? \".\" : event.key;\n } else {\n typingBuffer.current = next;\n }\n\n const value = parseFloat(typingBuffer.current);\n if (!isNaN(value)) {\n const clamped = Math.min(SLIDER_MAX, value);\n updateActivePosition(clamped);\n setInputValue(typingBuffer.current);\n }\n\n clearTimeout(typingTimeout.current);\n typingTimeout.current = setTimeout(() => {\n typingBuffer.current = \"\";\n }, TYPING_RESET_DELAY_MS);\n }\n\n if (event.key === \"Backspace\") {\n event.preventDefault();\n typingBuffer.current = typingBuffer.current.slice(0, -1);\n if (typingBuffer.current && typingBuffer.current !== \".\") {\n const value = Math.min(SLIDER_MAX, parseFloat(typingBuffer.current));\n updateActivePosition(value);\n setInputValue(typingBuffer.current);\n }\n clearTimeout(typingTimeout.current);\n typingTimeout.current = setTimeout(() => {\n typingBuffer.current = \"\";\n }, TYPING_RESET_DELAY_MS);\n }\n };\n\n document.addEventListener(\"keydown\", handleKeyDown);\n return () => {\n document.removeEventListener(\"keydown\", handleKeyDown);\n clearTimeout(typingTimeout.current);\n };\n }, [activeMod, picking, activeIndex, updateActivePosition]);\n\n useEffect(() => {\n const handleKeyDown = (event: KeyboardEvent) => {\n const target = event.target as HTMLElement;\n if (target.tagName === \"INPUT\" || target.tagName === \"TEXTAREA\") return;\n if (event.key === \"t\") {\n event.preventDefault();\n setPicking(true);\n }\n if (hasModifications && (event.key === \"b\" || event.key === \"f\" || event.key === \"d\")) {\n event.preventDefault();\n const property: \"bg\" | \"text\" | \"border\" =\n event.key === \"b\" ? \"bg\" : event.key === \"f\" ? \"text\" : \"border\";\n const index = activeIndexRef.current;\n if (index < 0) return;\n setModifications((previous) => {\n const updated = [...previous];\n restoreModification(updated[index]);\n updated[index] = { ...updated[index], property };\n applyModification(updated[index], scalesRef.current, activeScaleRef.current);\n return updated;\n });\n }\n };\n\n const handleMiddleClick = (event: MouseEvent) => {\n if (event.button !== 1) return;\n event.preventDefault();\n setPicking(true);\n };\n\n document.addEventListener(\"keydown\", handleKeyDown);\n document.addEventListener(\"mousedown\", handleMiddleClick, true);\n document.addEventListener(\"auxclick\", handleMiddleClick, true);\n return () => {\n document.removeEventListener(\"keydown\", handleKeyDown);\n document.removeEventListener(\"mousedown\", handleMiddleClick, true);\n document.removeEventListener(\"auxclick\", handleMiddleClick, true);\n };\n }, [hasModifications]);\n\n useEffect(() => {\n return () => {\n modifications.forEach(restoreModification);\n releaseLock();\n };\n }, []);\n\n useEffect(() => {\n if (activeMod) {\n applyModification(activeMod, scales, activeScale);\n }\n }, [activeMod?.position, activeMod?.fontSize, activeMod?.paddingY, activeScale, scales]);\n\n useEffect(() => {\n if (!picking) return;\n\n let hoveredElement: HTMLElement | null = null;\n\n const handleMouseOver = (event: MouseEvent) => {\n const target = event.target as HTMLElement;\n if (target.closest(\"[data-tweaker]\")) return;\n hoveredElement = target;\n target.style.outline = \"2px solid #3b82f6\";\n target.style.outlineOffset = \"2px\";\n };\n\n const handleMouseOut = (event: MouseEvent) => {\n const target = event.target as HTMLElement;\n target.style.outline = \"\";\n target.style.outlineOffset = \"\";\n if (hoveredElement === target) hoveredElement = null;\n };\n\n const handleClick = (event: MouseEvent) => {\n event.preventDefault();\n event.stopPropagation();\n const target = event.target as HTMLElement;\n if (target.closest(\"[data-tweaker]\")) return;\n\n target.style.outline = \"\";\n target.style.outlineOffset = \"\";\n\n const computed = getComputedStyle(target);\n const [bgRed, bgGreen, bgBlue, bgAlpha] = parseRgb(computed.backgroundColor);\n const [textRed, textGreen, textBlue] = parseRgb(computed.color);\n const [borderRed, borderGreen, borderBlue, borderAlpha] = parseRgb(computed.borderColor);\n const hasBorder = borderAlpha > 0 && parseFloat(computed.borderWidth) > 0;\n\n const hasBackground = bgAlpha > 0;\n const defaultProperty: \"bg\" | \"text\" | \"border\" = hasBackground ? \"bg\" : hasBorder ? \"border\" : \"text\";\n const targetOklch =\n defaultProperty === \"bg\"\n ? rgbToOklch(bgRed, bgGreen, bgBlue)\n : defaultProperty === \"border\"\n ? rgbToOklch(borderRed, borderGreen, borderBlue)\n : rgbToOklch(textRed, textGreen, textBlue);\n\n const position = findClosestPosition(scales, activeScale, targetOklch);\n const currentSize = parseFloat(computed.fontSize) || 16;\n const currentPaddingY = parseFloat(computed.paddingTop) || 0;\n\n const newModification: Modification = {\n element: target,\n selector: getSelector(target),\n componentName: null,\n sourceFile: null,\n textPreview: getTextPreview(target),\n originalInlineBg: target.style.backgroundColor,\n originalInlineColor: target.style.color,\n originalInlineBorderColor: target.style.borderColor,\n originalInlineFontSize: target.style.fontSize,\n originalInlinePaddingTop: target.style.paddingTop,\n originalInlinePaddingBottom: target.style.paddingBottom,\n originalInlineMarginTop: target.style.marginTop,\n originalInlineMarginBottom: target.style.marginBottom,\n property: defaultProperty,\n position,\n fontSize: currentSize,\n paddingY: currentPaddingY,\n };\n\n setModifications((previous) => [...previous, newModification]);\n setActiveIndex(modifications.length);\n setInputValue(String(position));\n setPicking(false);\n };\n\n document.addEventListener(\"mouseover\", handleMouseOver, true);\n document.addEventListener(\"mouseout\", handleMouseOut, true);\n document.addEventListener(\"click\", handleClick, true);\n\n return () => {\n document.removeEventListener(\"mouseover\", handleMouseOver, true);\n document.removeEventListener(\"mouseout\", handleMouseOut, true);\n document.removeEventListener(\"click\", handleClick, true);\n if (hoveredElement) {\n hoveredElement.style.outline = \"\";\n hoveredElement.style.outlineOffset = \"\";\n }\n };\n }, [picking, activeScale, scales, modifications.length]);\n\n const fillColor = activeMod\n ? oklchToCssString(getColorAtPosition(scales, activeScale, activeMod.position))\n : scales[activeScale]?.shades[\"500\"] ?? \"rgba(255,255,255,0.3)\";\n\n const propertyLabel =\n activeMod?.property === \"text\" ? \"F\" : activeMod?.property === \"border\" ? \"D\" : \"B\";\n\n const isPaddingMode = shiftHeld && hasModifications && !picking;\n\n const guideRect = activeMod && !picking ? activeMod.element.getBoundingClientRect() : null;\n\n const thumbX = activeMod\n ? isPaddingMode\n ? (MINIMAP_WIDTH_PX - THUMB_SIZE_PX) / 2\n : ((activeMod.fontSize - FONT_SIZE_MIN_PX) / (FONT_SIZE_MAX_PX - FONT_SIZE_MIN_PX)) * (MINIMAP_WIDTH_PX - THUMB_SIZE_PX)\n : 0;\n const thumbY = activeMod\n ? isPaddingMode\n ? (1 - (activeMod.paddingY - PADDING_MIN_PX) / (PADDING_MAX_PX - PADDING_MIN_PX)) * (MINIMAP_HEIGHT_PX - THUMB_SIZE_PX)\n : (1 - activeMod.position / SLIDER_MAX) * (MINIMAP_HEIGHT_PX - THUMB_SIZE_PX)\n : MINIMAP_HEIGHT_PX - THUMB_SIZE_PX;\n\n return (\n <>\n {guideRect && activeMod && (\n <div data-tweaker style={guidelinesContainerStyle}>\n <div\n style={{\n position: \"absolute\",\n left: guideRect.left,\n top: guideRect.top,\n width: guideRect.width,\n height: guideRect.height,\n boxSizing: \"border-box\",\n border: \"1px solid rgba(59, 130, 246, 0.5)\",\n borderRadius: 1,\n }}\n />\n {activeMod.paddingY > 0 && (\n <>\n <div\n style={{\n position: \"absolute\",\n left: guideRect.left,\n top: guideRect.top,\n width: guideRect.width,\n height: Math.min(activeMod.paddingY, guideRect.height / 2),\n background: \"rgba(255, 99, 132, 0.1)\",\n borderBottom: \"1px dashed rgba(255, 99, 132, 0.35)\",\n }}\n />\n <div\n style={{\n position: \"absolute\",\n left: guideRect.left,\n top: guideRect.bottom - Math.min(activeMod.paddingY, guideRect.height / 2),\n width: guideRect.width,\n height: Math.min(activeMod.paddingY, guideRect.height / 2),\n background: \"rgba(255, 99, 132, 0.1)\",\n borderTop: \"1px dashed rgba(255, 99, 132, 0.35)\",\n }}\n />\n </>\n )}\n <div\n style={{\n position: \"absolute\",\n left: guideRect.right + 8,\n top: guideRect.top,\n display: \"flex\",\n flexDirection: \"column\",\n gap: 4,\n pointerEvents: \"none\",\n }}\n >\n <span style={guidelineLabelStyle}>\n ↕ {activeMod.paddingY}px\n </span>\n <span style={{ ...guidelineLabelStyle, color: \"rgba(59, 130, 246, 0.8)\", background: \"rgba(59, 130, 246, 0.06)\" }}>\n {activeMod.fontSize}px\n </span>\n </div>\n </div>\n )}\n <AnimatePresence>\n {(hasModifications || picking) && (\n <motion.div\n key=\"minimap\"\n data-tweaker\n initial={{ opacity: 0, y: 8 }}\n animate={{ opacity: 1, y: 0 }}\n exit={{ opacity: 0, y: 8 }}\n transition={{ duration: 0.2 }}\n style={minimapContainerStyle}\n >\n <div style={minimapFieldStyle}>\n <div\n style={{\n position: \"absolute\",\n left: thumbX,\n top: thumbY,\n width: THUMB_SIZE_PX,\n height: THUMB_SIZE_PX,\n borderRadius: \"50%\",\n background: fillColor,\n border: \"2px solid rgba(255,255,255,0.9)\",\n boxShadow: \"0 1px 4px rgba(0,0,0,0.4)\",\n transition: \"left 50ms, top 50ms\",\n }}\n />\n </div>\n <div style={minimapModeStyle}>\n <span style={minimapLabelStyle}>\n {isPaddingMode ? \"⇧ Padding\" : \"Style\"}\n </span>\n </div>\n <div style={minimapValuesStyle}>\n <span style={minimapLabelStyle}>\n {picking\n ? \"Picking…\"\n : isPaddingMode\n ? `↕ ${activeMod?.paddingY ?? 0}px`\n : `${propertyLabel} ${inputValue || \"0\"}`}\n </span>\n {!picking && activeMod && !isPaddingMode && (\n <span style={minimapLabelStyle}>\n {`${activeMod.fontSize}px`}\n </span>\n )}\n </div>\n </motion.div>\n )}\n </AnimatePresence>\n </>\n );\n};\n\nconst baseTextStyle: React.CSSProperties = {\n fontFamily: \"system-ui, sans-serif\",\n fontWeight: 500,\n letterSpacing: \"-0.03em\",\n fontSynthesis: \"none\",\n WebkitFontSmoothing: \"antialiased\",\n};\n\nconst minimapContainerStyle: React.CSSProperties = {\n position: \"fixed\",\n left: 16,\n bottom: 16,\n zIndex: 9999,\n display: \"flex\",\n flexDirection: \"column\",\n gap: 6,\n};\n\nconst minimapFieldStyle: React.CSSProperties = {\n position: \"relative\",\n width: MINIMAP_WIDTH_PX,\n height: MINIMAP_HEIGHT_PX,\n borderRadius: 8,\n background: \"rgba(0,0,0,0.25)\",\n backdropFilter: \"blur(12px)\",\n WebkitBackdropFilter: \"blur(12px)\",\n boxShadow: \"0 0 0 1px rgba(255,255,255,0.08) inset\",\n overflow: \"hidden\",\n pointerEvents: \"none\",\n};\n\nconst minimapModeStyle: React.CSSProperties = {\n padding: \"0 2px\",\n pointerEvents: \"none\",\n};\n\nconst minimapValuesStyle: React.CSSProperties = {\n display: \"flex\",\n justifyContent: \"space-between\",\n padding: \"0 2px\",\n pointerEvents: \"none\",\n};\n\nconst minimapLabelStyle: React.CSSProperties = {\n ...baseTextStyle,\n fontSize: 11,\n color: \"rgba(255,255,255,0.6)\",\n whiteSpace: \"nowrap\",\n};\n\nconst guidelinesContainerStyle: React.CSSProperties = {\n position: \"fixed\",\n inset: 0,\n zIndex: 9998,\n pointerEvents: \"none\",\n};\n\nconst guidelineLabelStyle: React.CSSProperties = {\n ...baseTextStyle,\n fontSize: 10,\n lineHeight: \"16px\",\n color: \"rgba(255, 99, 132, 0.9)\",\n background: \"rgba(255, 99, 132, 0.08)\",\n padding: \"0 5px\",\n borderRadius: 3,\n whiteSpace: \"nowrap\",\n};\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"index.js","names":[],"sources":["../src/gray-scales.ts","../src/constants.ts","../src/utils/color.ts","../src/utils/dom.ts","../src/utils/modification.ts","../src/utils/prompt.ts","../src/tweaker.tsx"],"sourcesContent":["import type { GrayScale } from \"./types\";\n\nexport const GRAY_SCALES: Record<string, GrayScale> = {\n neutral: {\n label: \"Neutral\",\n shades: {\n \"50\": \"oklch(0.985 0 0)\",\n \"100\": \"oklch(0.97 0 0)\",\n \"200\": \"oklch(0.922 0 0)\",\n \"300\": \"oklch(0.87 0 0)\",\n \"400\": \"oklch(0.708 0 0)\",\n \"500\": \"oklch(0.556 0 0)\",\n \"600\": \"oklch(0.439 0 0)\",\n \"700\": \"oklch(0.371 0 0)\",\n \"800\": \"oklch(0.269 0 0)\",\n \"900\": \"oklch(0.205 0 0)\",\n \"950\": \"oklch(0.145 0 0)\",\n },\n },\n slate: {\n label: \"Slate\",\n shades: {\n \"50\": \"oklch(0.984 0.003 247.858)\",\n \"100\": \"oklch(0.968 0.007 247.896)\",\n \"200\": \"oklch(0.929 0.013 255.508)\",\n \"300\": \"oklch(0.869 0.022 252.894)\",\n \"400\": \"oklch(0.704 0.04 256.788)\",\n \"500\": \"oklch(0.554 0.046 257.417)\",\n \"600\": \"oklch(0.446 0.043 257.281)\",\n \"700\": \"oklch(0.372 0.044 257.287)\",\n \"800\": \"oklch(0.279 0.041 260.031)\",\n \"900\": \"oklch(0.208 0.042 265.755)\",\n \"950\": \"oklch(0.129 0.042 264.695)\",\n },\n },\n gray: {\n label: \"Gray\",\n shades: {\n \"50\": \"oklch(0.985 0.002 247.839)\",\n \"100\": \"oklch(0.967 0.003 264.542)\",\n \"200\": \"oklch(0.928 0.006 264.531)\",\n \"300\": \"oklch(0.872 0.01 258.338)\",\n \"400\": \"oklch(0.707 0.022 261.325)\",\n \"500\": \"oklch(0.551 0.027 264.364)\",\n \"600\": \"oklch(0.446 0.03 256.802)\",\n \"700\": \"oklch(0.373 0.034 259.733)\",\n \"800\": \"oklch(0.278 0.033 256.848)\",\n \"900\": \"oklch(0.21 0.034 264.665)\",\n \"950\": \"oklch(0.13 0.028 261.692)\",\n },\n },\n zinc: {\n label: \"Zinc\",\n shades: {\n \"50\": \"oklch(0.985 0 0)\",\n \"100\": \"oklch(0.967 0.001 286.375)\",\n \"200\": \"oklch(0.92 0.004 286.32)\",\n \"300\": \"oklch(0.871 0.006 286.286)\",\n \"400\": \"oklch(0.705 0.015 286.067)\",\n \"500\": \"oklch(0.552 0.016 285.938)\",\n \"600\": \"oklch(0.442 0.017 285.786)\",\n \"700\": \"oklch(0.37 0.013 285.805)\",\n \"800\": \"oklch(0.274 0.006 286.033)\",\n \"900\": \"oklch(0.21 0.006 285.885)\",\n \"950\": \"oklch(0.141 0.005 285.823)\",\n },\n },\n stone: {\n label: \"Stone\",\n shades: {\n \"50\": \"oklch(0.985 0.001 106.423)\",\n \"100\": \"oklch(0.97 0.001 106.424)\",\n \"200\": \"oklch(0.923 0.003 48.717)\",\n \"300\": \"oklch(0.869 0.005 56.366)\",\n \"400\": \"oklch(0.709 0.01 56.259)\",\n \"500\": \"oklch(0.553 0.013 58.071)\",\n \"600\": \"oklch(0.444 0.011 73.639)\",\n \"700\": \"oklch(0.374 0.01 67.558)\",\n \"800\": \"oklch(0.268 0.007 34.298)\",\n \"900\": \"oklch(0.216 0.006 56.043)\",\n \"950\": \"oklch(0.147 0.004 49.25)\",\n },\n },\n mauve: {\n label: \"Mauve\",\n shades: {\n \"50\": \"oklch(0.985 0.003 310)\",\n \"100\": \"oklch(0.968 0.006 310)\",\n \"200\": \"oklch(0.925 0.011 310)\",\n \"300\": \"oklch(0.87 0.017 310)\",\n \"400\": \"oklch(0.708 0.03 310)\",\n \"500\": \"oklch(0.556 0.03 310)\",\n \"600\": \"oklch(0.44 0.028 310)\",\n \"700\": \"oklch(0.372 0.025 310)\",\n \"800\": \"oklch(0.27 0.02 310)\",\n \"900\": \"oklch(0.208 0.018 310)\",\n \"950\": \"oklch(0.145 0.014 310)\",\n },\n },\n olive: {\n label: \"Olive\",\n shades: {\n \"50\": \"oklch(0.985 0.003 130)\",\n \"100\": \"oklch(0.968 0.006 130)\",\n \"200\": \"oklch(0.925 0.011 130)\",\n \"300\": \"oklch(0.87 0.017 130)\",\n \"400\": \"oklch(0.708 0.028 130)\",\n \"500\": \"oklch(0.556 0.028 130)\",\n \"600\": \"oklch(0.44 0.024 130)\",\n \"700\": \"oklch(0.372 0.02 130)\",\n \"800\": \"oklch(0.27 0.016 130)\",\n \"900\": \"oklch(0.208 0.014 130)\",\n \"950\": \"oklch(0.145 0.01 130)\",\n },\n },\n};\n","export const SLIDER_MAX = 10;\nexport const TEXT_PREVIEW_MAX_LENGTH = 30;\nexport const TYPING_RESET_DELAY_MS = 1500;\nexport const SHADE_KEYS = [\"50\", \"100\", \"200\", \"300\", \"400\", \"500\", \"600\", \"700\", \"800\", \"900\", \"950\"];\nexport const FONT_SIZE_MIN_PX = 1;\nexport const FONT_SIZE_MAX_PX = 200;\nexport const PADDING_MIN_PX = -200;\nexport const PADDING_MAX_PX = 200;\nexport const MOUSE_COLOR_SENSITIVITY = 0.02;\nexport const MOUSE_SIZE_SENSITIVITY = 0.1;\nexport const MOUSE_PADDING_SENSITIVITY = 0.2;\nexport const MINIMAP_WIDTH_PX = 160;\nexport const MINIMAP_HEIGHT_PX = 100;\nexport const THUMB_SIZE_PX = 10;\n","import type { OKLCH } from \"../types\";\nimport { SHADE_KEYS, SLIDER_MAX } from \"../constants\";\nimport type { GrayScale } from \"../types\";\n\nexport const parseOklch = (oklchStr: string): OKLCH => {\n const match = oklchStr.match(/oklch\\(([\\d.]+)\\s+([\\d.]+)\\s+([\\d.]+)\\)/);\n if (!match) return [0, 0, 0];\n return [Number(match[1]), Number(match[2]), Number(match[3])];\n};\n\nexport const lerpOklch = (colorA: OKLCH, colorB: OKLCH, interpolation: number): OKLCH => [\n colorA[0] + (colorB[0] - colorA[0]) * interpolation,\n colorA[1] + (colorB[1] - colorA[1]) * interpolation,\n colorA[2] + (colorB[2] - colorA[2]) * interpolation,\n];\n\nexport const formatOklch = (oklch: OKLCH): string =>\n `oklch(${oklch[0].toFixed(3)} ${oklch[1].toFixed(3)} ${oklch[2].toFixed(1)})`;\n\nexport const oklchToCssString = (oklch: OKLCH): string =>\n `oklch(${oklch[0]} ${oklch[1]} ${oklch[2]})`;\n\nexport const getColorAtPosition = (scales: Record<string, GrayScale>, scaleKey: string, position: number): OKLCH => {\n const scale = scales[scaleKey];\n if (!scale) return [0.5, 0, 0];\n\n const inverted = SLIDER_MAX - position;\n const segment = (inverted / SLIDER_MAX) * (SHADE_KEYS.length - 1);\n const index = Math.min(Math.floor(segment), SHADE_KEYS.length - 2);\n const interpolation = segment - index;\n\n const lower = parseOklch(scale.shades[SHADE_KEYS[index]]);\n const upper = parseOklch(scale.shades[SHADE_KEYS[index + 1]]);\n\n return lerpOklch(lower, upper, interpolation);\n};\n\nexport const getClosestShadeLabel = (position: number): string => {\n const inverted = SLIDER_MAX - position;\n const segment = (inverted / SLIDER_MAX) * (SHADE_KEYS.length - 1);\n const index = Math.round(segment);\n return SHADE_KEYS[Math.min(index, SHADE_KEYS.length - 1)];\n};\n\nexport const parseRgb = (color: string): [number, number, number, number] => {\n const match = color.match(\n /rgba?\\(\\s*([\\d.]+),\\s*([\\d.]+),\\s*([\\d.]+)(?:,\\s*([\\d.]+))?\\s*\\)/\n );\n if (!match) return [0, 0, 0, 0];\n return [\n Number(match[1]),\n Number(match[2]),\n Number(match[3]),\n match[4] !== undefined ? Number(match[4]) : 1,\n ];\n};\n\nexport const rgbToOklch = (red: number, green: number, blue: number): OKLCH => {\n const linearize = (channel: number): number => {\n const normalized = channel / 255;\n return normalized <= 0.04045\n ? normalized / 12.92\n : Math.pow((normalized + 0.055) / 1.055, 2.4);\n };\n const linearRed = linearize(red);\n const linearGreen = linearize(green);\n const linearBlue = linearize(blue);\n\n const lmsL = Math.cbrt(0.4122214708 * linearRed + 0.5363325363 * linearGreen + 0.0514459929 * linearBlue);\n const lmsM = Math.cbrt(0.2119034982 * linearRed + 0.6806995451 * linearGreen + 0.1073969566 * linearBlue);\n const lmsS = Math.cbrt(0.0883024619 * linearRed + 0.2817188376 * linearGreen + 0.6299787005 * linearBlue);\n\n const lightness = 0.2104542553 * lmsL + 0.793617785 * lmsM - 0.0040720468 * lmsS;\n const labA = 1.9779984951 * lmsL - 2.428592205 * lmsM + 0.4505937099 * lmsS;\n const labB = 0.0259040371 * lmsL + 0.7827717662 * lmsM - 0.808675766 * lmsS;\n\n const chroma = Math.sqrt(labA * labA + labB * labB);\n const hue = Math.atan2(labB, labA) * (180 / Math.PI);\n\n return [lightness, chroma, hue < 0 ? hue + 360 : hue];\n};\n\nexport const findClosestPosition = (scales: Record<string, GrayScale>, scaleKey: string, targetOklch: OKLCH): number => {\n let bestPosition = 0;\n let bestDistance = Infinity;\n\n for (let position = 0; position <= SLIDER_MAX; position++) {\n const color = getColorAtPosition(scales, scaleKey, position);\n const distance =\n (color[0] - targetOklch[0]) ** 2 +\n (color[1] - targetOklch[1]) ** 2 +\n ((color[2] - targetOklch[2]) / 360) ** 2;\n if (distance < bestDistance) {\n bestDistance = distance;\n bestPosition = position;\n }\n }\n\n return bestPosition;\n};\n","import { TEXT_PREVIEW_MAX_LENGTH } from \"../constants\";\n\nexport const getSelector = (element: HTMLElement): string => {\n const tag = element.tagName.toLowerCase();\n const classes = Array.from(element.classList)\n .filter((className) => !className.startsWith(\"__\"))\n .slice(0, 2)\n .join(\".\");\n return classes ? `${tag}.${classes}` : tag;\n};\n\nexport const getTextPreview = (element: HTMLElement): string => {\n const text = element.textContent?.trim() || \"\";\n return text.length > TEXT_PREVIEW_MAX_LENGTH\n ? `${text.slice(0, TEXT_PREVIEW_MAX_LENGTH)}…`\n : text;\n};\n","import type { GrayScale, Modification } from \"../types\";\nimport { getColorAtPosition, oklchToCssString } from \"./color\";\n\nexport const applyModification = (\n modification: Modification,\n scales: Record<string, GrayScale>,\n scaleKey: string,\n) => {\n const oklch = getColorAtPosition(scales, scaleKey, modification.position);\n const colorValue = oklchToCssString(oklch);\n if (modification.property === \"bg\") {\n modification.element.style.backgroundColor = colorValue;\n } else if (modification.property === \"text\") {\n modification.element.style.color = colorValue;\n } else {\n modification.element.style.borderColor = colorValue;\n }\n modification.element.style.fontSize = `${modification.fontSize}px`;\n\n const paddingY = Math.round(modification.paddingY);\n\n modification.element.style.paddingTop = `${Math.max(0, paddingY)}px`;\n modification.element.style.paddingBottom = `${Math.max(0, paddingY)}px`;\n\n modification.element.style.marginTop = paddingY < 0 ? `${paddingY}px` : modification.originalInlineMarginTop;\n modification.element.style.marginBottom = paddingY < 0 ? `${paddingY}px` : modification.originalInlineMarginBottom;\n\n if (modification.translateX !== 0 || modification.translateY !== 0) {\n modification.element.style.transform = `translate(${modification.translateX}px, ${modification.translateY}px)`;\n } else {\n modification.element.style.transform = modification.originalInlineTransform;\n }\n};\n\nexport const restoreModification = (modification: Modification) => {\n modification.element.style.backgroundColor = modification.originalInlineBg;\n modification.element.style.color = modification.originalInlineColor;\n modification.element.style.borderColor = modification.originalInlineBorderColor;\n modification.element.style.fontSize = modification.originalInlineFontSize;\n modification.element.style.paddingTop = modification.originalInlinePaddingTop;\n modification.element.style.paddingBottom = modification.originalInlinePaddingBottom;\n modification.element.style.marginTop = modification.originalInlineMarginTop;\n modification.element.style.marginBottom = modification.originalInlineMarginBottom;\n modification.element.style.transform = modification.originalInlineTransform;\n};\n\nexport const roundToStep = (value: number): number =>\n parseFloat((Math.round(value * 10) / 10).toFixed(1));\n\nexport const roundToHalf = (value: number): number =>\n Math.round(value * 2) / 2;\n","import type { GrayScale, Modification } from \"../types\";\nimport { formatOklch, getColorAtPosition, getClosestShadeLabel } from \"./color\";\n\nconst getLayoutContext = (element: HTMLElement): string => {\n const parent = element.parentElement;\n if (!parent) return \"no parent\";\n\n const style = getComputedStyle(parent);\n const display = style.display;\n const parts: string[] = [display];\n\n if (display === \"flex\" || display === \"inline-flex\") {\n parts.push(style.flexDirection);\n if (style.gap && style.gap !== \"normal\" && style.gap !== \"0px\") {\n parts.push(`gap: ${style.gap}`);\n }\n }\n\n if (display === \"grid\" || display === \"inline-grid\") {\n if (style.gap && style.gap !== \"normal\" && style.gap !== \"0px\") {\n parts.push(`gap: ${style.gap}`);\n }\n }\n\n return parts.join(\", \");\n};\n\nexport const generatePrompt = (\n modifications: Modification[],\n scales: Record<string, GrayScale>,\n scaleKey: string,\n): string => {\n if (modifications.length === 0) return \"\";\n\n const scaleName = scales[scaleKey]?.label || scaleKey;\n const colorLines: string[] = [];\n const sizeLines: string[] = [];\n const paddingLines: string[] = [];\n const positionLines: string[] = [];\n\n modifications.forEach((modification) => {\n const nameParts = [modification.selector];\n if (modification.componentName) nameParts.unshift(`<${modification.componentName}>`);\n if (modification.textPreview) nameParts.push(`(\"${modification.textPreview}\")`);\n const description = nameParts.join(\" \");\n\n const shade = getClosestShadeLabel(modification.position);\n const oklch = getColorAtPosition(scales, scaleKey, modification.position);\n const property =\n modification.property === \"bg\"\n ? \"background color\"\n : modification.property === \"text\"\n ? \"text color\"\n : \"border color\";\n colorLines.push(`- ${property} of ${description} → ${scaleName} ${shade} (${formatOklch(oklch)})`);\n if (modification.sourceFile) colorLines.push(` Source: ${modification.sourceFile}`);\n\n sizeLines.push(`- font-size of ${description} → ${modification.fontSize}px`);\n if (modification.sourceFile) sizeLines.push(` Source: ${modification.sourceFile}`);\n\n paddingLines.push(`- vertical padding of ${description} → ${Math.round(modification.paddingY)}px`);\n if (modification.sourceFile) paddingLines.push(` Source: ${modification.sourceFile}`);\n\n if (modification.translateX !== 0 || modification.translateY !== 0) {\n const xPx = Math.abs(Math.round(modification.translateX));\n const yPx = Math.abs(Math.round(modification.translateY));\n const xDir = modification.translateX >= 0 ? \"right\" : \"left\";\n const yDir = modification.translateY >= 0 ? \"down\" : \"up\";\n\n const moveParts: string[] = [];\n if (xPx > 0) moveParts.push(`${xPx}px ${xDir}`);\n if (yPx > 0) moveParts.push(`${yPx}px ${yDir}`);\n\n positionLines.push(`- move ${description} → ${moveParts.join(\", \")}`);\n positionLines.push(` Parent layout: ${getLayoutContext(modification.element)}`);\n if (modification.sourceFile) positionLines.push(` Source: ${modification.sourceFile}`);\n }\n });\n\n const sections: string[] = [];\n\n if (colorLines.length > 0) {\n sections.push(\n \"Change the following colors using the design system's gray scale:\",\n \"\",\n ...colorLines,\n );\n }\n\n if (sizeLines.length > 0) {\n if (sections.length > 0) sections.push(\"\");\n sections.push(\"Change the following font sizes:\", \"\", ...sizeLines);\n }\n\n if (paddingLines.length > 0) {\n if (sections.length > 0) sections.push(\"\");\n sections.push(\"Change the following padding:\", \"\", ...paddingLines);\n }\n\n if (positionLines.length > 0) {\n if (sections.length > 0) sections.push(\"\");\n sections.push(\n \"Reposition the following elements (use canonical CSS like margin, padding, gap, or flexbox order — do NOT use CSS transforms):\",\n \"\",\n ...positionLines,\n );\n }\n\n return sections.join(\"\\n\");\n};\n","import { useState, useCallback, useEffect, useRef } from \"react\";\nimport { motion, AnimatePresence } from \"motion/react\";\nimport type { Modification, TweakerProps } from \"./types\";\nimport { GRAY_SCALES } from \"./gray-scales\";\nimport { SLIDER_MAX, TYPING_RESET_DELAY_MS, FONT_SIZE_MIN_PX, FONT_SIZE_MAX_PX, PADDING_MIN_PX, PADDING_MAX_PX, MOUSE_COLOR_SENSITIVITY, MOUSE_SIZE_SENSITIVITY, MOUSE_PADDING_SENSITIVITY, MINIMAP_WIDTH_PX, MINIMAP_HEIGHT_PX, THUMB_SIZE_PX } from \"./constants\";\nimport { getColorAtPosition, oklchToCssString, parseRgb, rgbToOklch, findClosestPosition } from \"./utils/color\";\nimport { getSelector, getTextPreview } from \"./utils/dom\";\nimport { applyModification, restoreModification, roundToStep, roundToHalf } from \"./utils/modification\";\nimport { generatePrompt } from \"./utils/prompt\";\n\nconst requestLock = () => {\n if (!document.pointerLockElement) {\n document.body.requestPointerLock();\n }\n};\n\nconst releaseLock = () => {\n if (document.pointerLockElement) {\n document.exitPointerLock();\n }\n};\n\nexport const Tweaker = ({ scales = GRAY_SCALES, activeScale = \"neutral\" }: TweakerProps) => {\n const [picking, setPicking] = useState(false);\n const [modifications, setModifications] = useState<Modification[]>([]);\n const [activeIndex, setActiveIndex] = useState(-1);\n const [inputValue, setInputValue] = useState(\"\");\n const [shiftHeld, setShiftHeld] = useState(false);\n const [spaceHeld, setSpaceHeld] = useState(false);\n const [controlHeld, setControlHeld] = useState(false);\n const typingBuffer = useRef(\"\");\n const typingTimeout = useRef<ReturnType<typeof setTimeout>>(undefined);\n\n const activeMod = activeIndex >= 0 ? modifications[activeIndex] : null;\n const hasModifications = modifications.length > 0;\n\n const activeIndexRef = useRef(activeIndex);\n const activeScaleRef = useRef(activeScale);\n const modificationsRef = useRef(modifications);\n const scalesRef = useRef(scales);\n activeIndexRef.current = activeIndex;\n activeScaleRef.current = activeScale;\n modificationsRef.current = modifications;\n scalesRef.current = scales;\n\n const updateActivePosition = useCallback(\n (newPosition: number) => {\n if (activeIndex < 0) return;\n setModifications((previous) => {\n const updated = [...previous];\n updated[activeIndex] = { ...updated[activeIndex], position: newPosition };\n applyModification(updated[activeIndex], scales, activeScale);\n return updated;\n });\n },\n [activeIndex, activeScale, scales],\n );\n\n useEffect(() => {\n const handleKeyDown = (event: KeyboardEvent) => {\n setShiftHeld(event.shiftKey);\n if (event.key === \" \") setSpaceHeld(true);\n if (event.key === \"Control\") setControlHeld(true);\n };\n const handleKeyUp = (event: KeyboardEvent) => {\n setShiftHeld(event.shiftKey);\n if (event.key === \" \") setSpaceHeld(false);\n if (event.key === \"Control\") setControlHeld(false);\n };\n document.addEventListener(\"keydown\", handleKeyDown);\n document.addEventListener(\"keyup\", handleKeyUp);\n return () => {\n document.removeEventListener(\"keydown\", handleKeyDown);\n document.removeEventListener(\"keyup\", handleKeyUp);\n };\n }, []);\n\n useEffect(() => {\n if (!hasModifications || picking) return;\n\n const handleMouseMove = (event: MouseEvent) => {\n if (!document.pointerLockElement) return;\n const index = activeIndexRef.current;\n if (index < 0) return;\n\n setModifications((previous) => {\n const updated = [...previous];\n const current = updated[index];\n\n if (event.ctrlKey) {\n updated[index] = {\n ...current,\n translateX: current.translateX + event.movementX,\n translateY: current.translateY + event.movementY,\n };\n } else if (event.shiftKey) {\n const newPaddingY = Math.max(PADDING_MIN_PX, Math.min(PADDING_MAX_PX, current.paddingY - event.movementY * MOUSE_PADDING_SENSITIVITY));\n updated[index] = { ...current, paddingY: Math.round(newPaddingY) };\n } else {\n const newPosition = Math.max(0, Math.min(SLIDER_MAX, current.position - event.movementY * MOUSE_COLOR_SENSITIVITY));\n const newSize = Math.max(FONT_SIZE_MIN_PX, Math.min(FONT_SIZE_MAX_PX, current.fontSize + event.movementX * MOUSE_SIZE_SENSITIVITY));\n updated[index] = { ...current, position: roundToStep(newPosition), fontSize: roundToHalf(newSize) };\n }\n\n applyModification(updated[index], scalesRef.current, activeScaleRef.current);\n setInputValue(String(updated[index].position));\n return updated;\n });\n };\n\n requestLock();\n document.addEventListener(\"mousemove\", handleMouseMove, true);\n return () => {\n document.removeEventListener(\"mousemove\", handleMouseMove, true);\n releaseLock();\n };\n }, [hasModifications, picking]);\n\n useEffect(() => {\n if (!hasModifications) return;\n\n const handleKeyDown = (event: KeyboardEvent) => {\n if (event.key === \"Escape\") {\n event.preventDefault();\n releaseLock();\n const prompt = generatePrompt(modificationsRef.current, scalesRef.current, activeScaleRef.current);\n navigator.clipboard.writeText(prompt);\n modificationsRef.current.forEach(restoreModification);\n setModifications([]);\n setActiveIndex(-1);\n setInputValue(\"\");\n }\n\n if (event.key === \"Enter\") {\n event.preventDefault();\n releaseLock();\n const prompt = generatePrompt(modificationsRef.current, scalesRef.current, activeScaleRef.current);\n navigator.clipboard.writeText(prompt);\n setPicking(true);\n }\n };\n\n document.addEventListener(\"keydown\", handleKeyDown);\n return () => document.removeEventListener(\"keydown\", handleKeyDown);\n }, [hasModifications]);\n\n useEffect(() => {\n if (!activeMod || picking) return;\n\n const handleKeyDown = (event: KeyboardEvent) => {\n const target = event.target as HTMLElement;\n if (target.tagName === \"INPUT\" || target.tagName === \"TEXTAREA\") return;\n if (event.key === \"Escape\") return;\n\n if ((event.key >= \"0\" && event.key <= \"9\") || event.key === \".\") {\n event.preventDefault();\n const next = typingBuffer.current + event.key;\n\n if (event.key === \".\" && typingBuffer.current.includes(\".\")) return;\n\n const hasDecimal = typingBuffer.current.includes(\".\");\n if (hasDecimal && event.key !== \".\" && typingBuffer.current.split(\".\")[1]?.length >= 1) {\n return;\n }\n\n const parsed = parseFloat(next);\n if (!isNaN(parsed) && parsed > SLIDER_MAX) {\n typingBuffer.current = event.key === \".\" ? \".\" : event.key;\n } else {\n typingBuffer.current = next;\n }\n\n const value = parseFloat(typingBuffer.current);\n if (!isNaN(value)) {\n const clamped = Math.min(SLIDER_MAX, value);\n updateActivePosition(clamped);\n setInputValue(typingBuffer.current);\n }\n\n clearTimeout(typingTimeout.current);\n typingTimeout.current = setTimeout(() => {\n typingBuffer.current = \"\";\n }, TYPING_RESET_DELAY_MS);\n }\n\n if (event.key === \"Backspace\") {\n event.preventDefault();\n typingBuffer.current = typingBuffer.current.slice(0, -1);\n if (typingBuffer.current && typingBuffer.current !== \".\") {\n const value = Math.min(SLIDER_MAX, parseFloat(typingBuffer.current));\n updateActivePosition(value);\n setInputValue(typingBuffer.current);\n }\n clearTimeout(typingTimeout.current);\n typingTimeout.current = setTimeout(() => {\n typingBuffer.current = \"\";\n }, TYPING_RESET_DELAY_MS);\n }\n };\n\n document.addEventListener(\"keydown\", handleKeyDown);\n return () => {\n document.removeEventListener(\"keydown\", handleKeyDown);\n clearTimeout(typingTimeout.current);\n };\n }, [activeMod, picking, activeIndex, updateActivePosition]);\n\n useEffect(() => {\n const handleKeyDown = (event: KeyboardEvent) => {\n const target = event.target as HTMLElement;\n if (target.tagName === \"INPUT\" || target.tagName === \"TEXTAREA\") return;\n if (event.key === \"t\") {\n event.preventDefault();\n setPicking(true);\n }\n if (hasModifications && (event.key === \"b\" || event.key === \"f\" || event.key === \"d\")) {\n event.preventDefault();\n const property: \"bg\" | \"text\" | \"border\" =\n event.key === \"b\" ? \"bg\" : event.key === \"f\" ? \"text\" : \"border\";\n const index = activeIndexRef.current;\n if (index < 0) return;\n setModifications((previous) => {\n const updated = [...previous];\n restoreModification(updated[index]);\n updated[index] = { ...updated[index], property };\n applyModification(updated[index], scalesRef.current, activeScaleRef.current);\n return updated;\n });\n }\n };\n\n const handleMiddleClick = (event: MouseEvent) => {\n if (event.button !== 1) return;\n event.preventDefault();\n setPicking(true);\n };\n\n document.addEventListener(\"keydown\", handleKeyDown);\n document.addEventListener(\"mousedown\", handleMiddleClick, true);\n document.addEventListener(\"auxclick\", handleMiddleClick, true);\n return () => {\n document.removeEventListener(\"keydown\", handleKeyDown);\n document.removeEventListener(\"mousedown\", handleMiddleClick, true);\n document.removeEventListener(\"auxclick\", handleMiddleClick, true);\n };\n }, [hasModifications]);\n\n useEffect(() => {\n return () => {\n modifications.forEach(restoreModification);\n releaseLock();\n };\n }, []);\n\n useEffect(() => {\n if (activeMod) {\n applyModification(activeMod, scales, activeScale);\n }\n }, [activeMod?.position, activeMod?.fontSize, activeMod?.paddingY, activeScale, scales]);\n\n useEffect(() => {\n if (!picking) return;\n\n let hoveredElement: HTMLElement | null = null;\n\n const handleMouseOver = (event: MouseEvent) => {\n const target = event.target as HTMLElement;\n if (target.closest(\"[data-tweaker]\")) return;\n hoveredElement = target;\n target.style.outline = \"2px solid #3b82f6\";\n target.style.outlineOffset = \"2px\";\n };\n\n const handleMouseOut = (event: MouseEvent) => {\n const target = event.target as HTMLElement;\n target.style.outline = \"\";\n target.style.outlineOffset = \"\";\n if (hoveredElement === target) hoveredElement = null;\n };\n\n const handleClick = async (event: MouseEvent) => {\n event.preventDefault();\n event.stopPropagation();\n const target = event.target as HTMLElement;\n if (target.closest(\"[data-tweaker]\")) return;\n\n target.style.outline = \"\";\n target.style.outlineOffset = \"\";\n\n const computed = getComputedStyle(target);\n const [bgRed, bgGreen, bgBlue, bgAlpha] = parseRgb(computed.backgroundColor);\n const [textRed, textGreen, textBlue] = parseRgb(computed.color);\n const [borderRed, borderGreen, borderBlue, borderAlpha] = parseRgb(computed.borderColor);\n const hasBorder = borderAlpha > 0 && parseFloat(computed.borderWidth) > 0;\n\n const hasBackground = bgAlpha > 0;\n const defaultProperty: \"bg\" | \"text\" | \"border\" = hasBackground ? \"bg\" : hasBorder ? \"border\" : \"text\";\n const targetOklch =\n defaultProperty === \"bg\"\n ? rgbToOklch(bgRed, bgGreen, bgBlue)\n : defaultProperty === \"border\"\n ? rgbToOklch(borderRed, borderGreen, borderBlue)\n : rgbToOklch(textRed, textGreen, textBlue);\n\n const position = findClosestPosition(scales, activeScale, targetOklch);\n const currentSize = parseFloat(computed.fontSize) || 16;\n const currentPaddingY = parseFloat(computed.paddingTop) || 0;\n\n let componentName: string | null = null;\n let sourceFile: string | null = null;\n try {\n const reactGrab = (window as unknown as Record<string, unknown>).__REACT_GRAB_MODULE__ as {\n getStack: (element: Element) => Promise<Array<{ fileName?: string; lineNumber?: number; functionName?: string }>>;\n } | undefined;\n if (reactGrab?.getStack) {\n const stack = await reactGrab.getStack(target);\n if (stack) {\n for (const frame of stack) {\n if (frame.fileName && !frame.fileName.includes(\"node_modules\")) {\n sourceFile = frame.fileName;\n if (frame.functionName && /^[A-Z]/.test(frame.functionName)) {\n componentName = frame.functionName;\n }\n break;\n }\n }\n }\n }\n } catch {}\n\n const newModification: Modification = {\n element: target,\n selector: getSelector(target),\n componentName,\n sourceFile,\n textPreview: getTextPreview(target),\n originalInlineBg: target.style.backgroundColor,\n originalInlineColor: target.style.color,\n originalInlineBorderColor: target.style.borderColor,\n originalInlineFontSize: target.style.fontSize,\n originalInlinePaddingTop: target.style.paddingTop,\n originalInlinePaddingBottom: target.style.paddingBottom,\n originalInlineMarginTop: target.style.marginTop,\n originalInlineMarginBottom: target.style.marginBottom,\n originalInlineTransform: target.style.transform,\n property: defaultProperty,\n position,\n fontSize: currentSize,\n paddingY: currentPaddingY,\n translateX: 0,\n translateY: 0,\n };\n\n setModifications((previous) => [...previous, newModification]);\n setActiveIndex(modifications.length);\n setInputValue(String(position));\n setPicking(false);\n };\n\n document.addEventListener(\"mouseover\", handleMouseOver, true);\n document.addEventListener(\"mouseout\", handleMouseOut, true);\n document.addEventListener(\"click\", handleClick, true);\n\n return () => {\n document.removeEventListener(\"mouseover\", handleMouseOver, true);\n document.removeEventListener(\"mouseout\", handleMouseOut, true);\n document.removeEventListener(\"click\", handleClick, true);\n if (hoveredElement) {\n hoveredElement.style.outline = \"\";\n hoveredElement.style.outlineOffset = \"\";\n }\n };\n }, [picking, activeScale, scales, modifications.length]);\n\n const fillColor = activeMod\n ? oklchToCssString(getColorAtPosition(scales, activeScale, activeMod.position))\n : scales[activeScale]?.shades[\"500\"] ?? \"rgba(255,255,255,0.3)\";\n\n const propertyLabel =\n activeMod?.property === \"text\" ? \"F\" : activeMod?.property === \"border\" ? \"D\" : \"B\";\n\n const isPaddingMode = shiftHeld && hasModifications && !picking;\n const isDragMode = controlHeld && hasModifications && !picking;\n\n const guideRect = activeMod && !picking && !spaceHeld ? activeMod.element.getBoundingClientRect() : null;\n\n const thumbX = activeMod\n ? isPaddingMode\n ? (MINIMAP_WIDTH_PX - THUMB_SIZE_PX) / 2\n : ((activeMod.fontSize - FONT_SIZE_MIN_PX) / (FONT_SIZE_MAX_PX - FONT_SIZE_MIN_PX)) * (MINIMAP_WIDTH_PX - THUMB_SIZE_PX)\n : 0;\n const thumbY = activeMod\n ? isPaddingMode\n ? (1 - (activeMod.paddingY - PADDING_MIN_PX) / (PADDING_MAX_PX - PADDING_MIN_PX)) * (MINIMAP_HEIGHT_PX - THUMB_SIZE_PX)\n : (1 - activeMod.position / SLIDER_MAX) * (MINIMAP_HEIGHT_PX - THUMB_SIZE_PX)\n : MINIMAP_HEIGHT_PX - THUMB_SIZE_PX;\n\n return (\n <>\n {guideRect && activeMod && (\n <div data-tweaker style={guidelinesContainerStyle}>\n <div\n style={{\n position: \"absolute\",\n left: guideRect.left,\n top: guideRect.top,\n width: guideRect.width,\n height: guideRect.height,\n boxSizing: \"border-box\",\n border: \"1px solid rgba(59, 130, 246, 0.5)\",\n borderRadius: 1,\n }}\n />\n {activeMod.paddingY > 0 && (\n <>\n <div\n style={{\n position: \"absolute\",\n left: guideRect.left,\n top: guideRect.top,\n width: guideRect.width,\n height: Math.min(activeMod.paddingY, guideRect.height / 2),\n background: \"rgba(255, 99, 132, 0.1)\",\n borderBottom: \"1px dashed rgba(255, 99, 132, 0.35)\",\n }}\n />\n <div\n style={{\n position: \"absolute\",\n left: guideRect.left,\n top: guideRect.bottom - Math.min(activeMod.paddingY, guideRect.height / 2),\n width: guideRect.width,\n height: Math.min(activeMod.paddingY, guideRect.height / 2),\n background: \"rgba(255, 99, 132, 0.1)\",\n borderTop: \"1px dashed rgba(255, 99, 132, 0.35)\",\n }}\n />\n </>\n )}\n <div\n style={{\n position: \"absolute\",\n left: guideRect.right + 8,\n top: guideRect.top,\n display: \"flex\",\n flexDirection: \"column\",\n gap: 4,\n pointerEvents: \"none\",\n }}\n >\n <span style={guidelineLabelStyle}>\n ↕ {activeMod.paddingY}px\n </span>\n <span style={{ ...guidelineLabelStyle, color: \"rgba(59, 130, 246, 0.8)\", background: \"rgba(59, 130, 246, 0.06)\" }}>\n {activeMod.fontSize}px\n </span>\n {(activeMod.translateX !== 0 || activeMod.translateY !== 0) && (\n <span style={{ ...guidelineLabelStyle, color: \"rgba(168, 85, 247, 0.9)\", background: \"rgba(168, 85, 247, 0.08)\" }}>\n {Math.round(activeMod.translateX)}, {Math.round(activeMod.translateY)}\n </span>\n )}\n </div>\n </div>\n )}\n <AnimatePresence>\n {(hasModifications || picking) && (\n <motion.div\n key=\"minimap\"\n data-tweaker\n initial={{ opacity: 0, y: 8 }}\n animate={{ opacity: 1, y: 0 }}\n exit={{ opacity: 0, y: 8 }}\n transition={{ duration: 0.2 }}\n style={minimapContainerStyle}\n >\n <div style={minimapFieldStyle}>\n <div\n style={{\n position: \"absolute\",\n left: thumbX,\n top: thumbY,\n width: THUMB_SIZE_PX,\n height: THUMB_SIZE_PX,\n borderRadius: \"50%\",\n background: fillColor,\n border: \"2px solid rgba(255,255,255,0.9)\",\n boxShadow: \"0 1px 4px rgba(0,0,0,0.4)\",\n transition: \"left 50ms, top 50ms\",\n }}\n />\n </div>\n <div style={minimapModeStyle}>\n <span style={minimapLabelStyle}>\n {isDragMode ? \"⌃ Move\" : isPaddingMode ? \"⇧ Padding\" : \"Style\"}\n </span>\n </div>\n <div style={minimapValuesStyle}>\n <span style={minimapLabelStyle}>\n {picking\n ? \"Picking…\"\n : isDragMode\n ? `x: ${activeMod?.translateX ?? 0}`\n : isPaddingMode\n ? `↕ ${activeMod?.paddingY ?? 0}px`\n : `${propertyLabel} ${inputValue || \"0\"}`}\n </span>\n {!picking && activeMod && isDragMode && (\n <span style={minimapLabelStyle}>\n {`y: ${activeMod.translateY}`}\n </span>\n )}\n {!picking && activeMod && !isPaddingMode && !isDragMode && (\n <span style={minimapLabelStyle}>\n {`${activeMod.fontSize}px`}\n </span>\n )}\n </div>\n </motion.div>\n )}\n </AnimatePresence>\n </>\n );\n};\n\nconst baseTextStyle: React.CSSProperties = {\n fontFamily: \"system-ui, sans-serif\",\n fontWeight: 500,\n letterSpacing: \"-0.03em\",\n fontSynthesis: \"none\",\n WebkitFontSmoothing: \"antialiased\",\n};\n\nconst minimapContainerStyle: React.CSSProperties = {\n position: \"fixed\",\n left: 16,\n bottom: 16,\n zIndex: 9999,\n display: \"flex\",\n flexDirection: \"column\",\n gap: 6,\n};\n\nconst minimapFieldStyle: React.CSSProperties = {\n position: \"relative\",\n width: MINIMAP_WIDTH_PX,\n height: MINIMAP_HEIGHT_PX,\n borderRadius: 8,\n background: \"rgba(0,0,0,0.25)\",\n backdropFilter: \"blur(12px)\",\n WebkitBackdropFilter: \"blur(12px)\",\n boxShadow: \"0 0 0 1px rgba(255,255,255,0.08) inset\",\n overflow: \"hidden\",\n pointerEvents: \"none\",\n};\n\nconst minimapModeStyle: React.CSSProperties = {\n padding: \"0 2px\",\n pointerEvents: \"none\",\n};\n\nconst minimapValuesStyle: React.CSSProperties = {\n display: \"flex\",\n justifyContent: \"space-between\",\n padding: \"0 2px\",\n pointerEvents: \"none\",\n};\n\nconst minimapLabelStyle: React.CSSProperties = {\n ...baseTextStyle,\n fontSize: 11,\n color: \"rgba(255,255,255,0.6)\",\n whiteSpace: \"nowrap\",\n};\n\nconst guidelinesContainerStyle: React.CSSProperties = {\n position: \"fixed\",\n inset: 0,\n zIndex: 9998,\n pointerEvents: \"none\",\n};\n\nconst guidelineLabelStyle: React.CSSProperties = {\n ...baseTextStyle,\n fontSize: 10,\n lineHeight: \"16px\",\n color: \"rgba(255, 99, 132, 0.9)\",\n background: \"rgba(255, 99, 132, 0.08)\",\n padding: \"0 5px\",\n borderRadius: 3,\n whiteSpace: \"nowrap\",\n};\n"],"mappings":"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"}
|