@pixerate/editor-react 0.16.0 → 0.17.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (46) hide show
  1. package/README.md +2 -2
  2. package/dist/canvas/index.cjs +406 -142
  3. package/dist/canvas/index.cjs.map +1 -1
  4. package/dist/canvas/index.d.cts +66 -3
  5. package/dist/canvas/index.d.ts +66 -3
  6. package/dist/canvas/index.js +277 -0
  7. package/dist/canvas/index.js.map +1 -1
  8. package/dist/chunk-I3E4KSA2.js +515 -0
  9. package/dist/chunk-I3E4KSA2.js.map +1 -0
  10. package/dist/chunk-JR5ZBDR7.js +2012 -0
  11. package/dist/chunk-JR5ZBDR7.js.map +1 -0
  12. package/dist/{chunk-XTFR3IMK.js → chunk-ZU54BMDC.js} +473 -160
  13. package/dist/chunk-ZU54BMDC.js.map +1 -0
  14. package/dist/generation/index.cjs +290 -0
  15. package/dist/generation/index.cjs.map +1 -1
  16. package/dist/generation/index.d.cts +66 -2
  17. package/dist/generation/index.d.ts +66 -2
  18. package/dist/generation/index.js +7 -1
  19. package/dist/image-editor/index.cjs +490 -187
  20. package/dist/image-editor/index.cjs.map +1 -1
  21. package/dist/image-editor/index.d.cts +34 -2
  22. package/dist/image-editor/index.d.ts +34 -2
  23. package/dist/image-editor/index.js +5 -1
  24. package/dist/index.cjs +2372 -731
  25. package/dist/index.cjs.map +1 -1
  26. package/dist/index.d.cts +88 -6
  27. package/dist/index.d.ts +88 -6
  28. package/dist/index.js +334 -96
  29. package/dist/index.js.map +1 -1
  30. package/dist/spreadsheet/index.cjs +943 -112
  31. package/dist/spreadsheet/index.cjs.map +1 -1
  32. package/dist/spreadsheet/index.d.cts +119 -7
  33. package/dist/spreadsheet/index.d.ts +119 -7
  34. package/dist/spreadsheet/index.js +11 -1
  35. package/dist/tokens/index.cjs +395 -0
  36. package/dist/tokens/index.cjs.map +1 -0
  37. package/dist/tokens/index.d.cts +54 -0
  38. package/dist/tokens/index.d.ts +54 -0
  39. package/dist/tokens/index.js +375 -0
  40. package/dist/tokens/index.js.map +1 -0
  41. package/package.json +10 -2
  42. package/dist/chunk-7SPRQZ6H.js +0 -216
  43. package/dist/chunk-7SPRQZ6H.js.map +0 -1
  44. package/dist/chunk-FYIPXHAE.js +0 -1169
  45. package/dist/chunk-FYIPXHAE.js.map +0 -1
  46. package/dist/chunk-XTFR3IMK.js.map +0 -1
@@ -159,7 +159,7 @@ function useImageEditor(options = {}) {
159
159
  }
160
160
 
161
161
  // src/image-editor/ImageEditor.tsx
162
- import React4, { useRef as useRef3, useEffect as useEffect4, useState as useState5, useCallback as useCallback2 } from "react";
162
+ import React6, { useRef as useRef3, useEffect as useEffect4, useState as useState7, useCallback as useCallback2 } from "react";
163
163
  import {
164
164
  canvasToImagePoint,
165
165
  hitTestCrop,
@@ -169,7 +169,9 @@ import {
169
169
  normalizeProcessVersion,
170
170
  LATEST_PROCESS_VERSION,
171
171
  IMAGE_ADJUSTMENT_CONTROLS,
172
- readAdjustmentControls
172
+ readAdjustmentControls,
173
+ DEFAULT_SELECTION_TOOL_OPTIONS,
174
+ SelectionGesture
173
175
  } from "@pixerate/editor/image-editor";
174
176
 
175
177
  // src/image-editor/ControlSlider.tsx
@@ -620,8 +622,258 @@ var AdjustmentLayersPanel = ({ controller, layers: layersProp, histogram }) => {
620
622
  ] });
621
623
  };
622
624
 
625
+ // src/image-editor/SelectionOptionsBar.tsx
626
+ import { useState as useState5 } from "react";
627
+ import {
628
+ SELECTION_MODES,
629
+ SELECTION_MODE_LABELS,
630
+ SELECTION_TOOLS,
631
+ describeSelection
632
+ } from "@pixerate/editor/image-editor";
633
+ import { jsx as jsx5, jsxs as jsxs5 } from "react/jsx-runtime";
634
+ var MODIFY_OPS = [
635
+ { op: "grow", label: "Grow" },
636
+ { op: "shrink", label: "Shrink" },
637
+ { op: "feather", label: "Feather" },
638
+ { op: "border", label: "Border" },
639
+ { op: "smooth", label: "Smooth" }
640
+ ];
641
+ var btn = (on) => `px-2 py-1 rounded-md border text-[11px] transition-colors ${on ? "bg-indigo-600 border-indigo-500 text-white" : "bg-slate-950 border-slate-800 text-slate-300 hover:text-white"}`;
642
+ var SelectionOptionsBar = ({
643
+ controller,
644
+ options,
645
+ onOptionsChange,
646
+ selection,
647
+ quickMask,
648
+ className = ""
649
+ }) => {
650
+ const [radius, setRadius] = useState5(2);
651
+ const set = (patch) => onOptionsChange({ ...options, ...patch });
652
+ const sel = selection === void 0 ? controller.getSelection() : selection;
653
+ const qm = quickMask ?? Boolean(controller.getState().quickMask);
654
+ return /* @__PURE__ */ jsxs5("div", { "data-testid": "selection-options-bar", className: `flex flex-col gap-3 text-xs ${className}`, children: [
655
+ /* @__PURE__ */ jsx5("div", { role: "group", "aria-label": "Selection tool", className: "flex flex-wrap gap-1", children: SELECTION_TOOLS.map((t) => /* @__PURE__ */ jsx5("button", { type: "button", "aria-pressed": options.tool === t.id, className: btn(options.tool === t.id), onClick: () => set({ tool: t.id }), children: t.label }, t.id)) }),
656
+ /* @__PURE__ */ jsx5("div", { role: "group", "aria-label": "Selection mode", className: "flex flex-wrap gap-1", children: SELECTION_MODES.map((m) => /* @__PURE__ */ jsx5("button", { type: "button", "aria-pressed": options.mode === m, className: btn(options.mode === m), onClick: () => set({ mode: m }), children: SELECTION_MODE_LABELS[m] }, m)) }),
657
+ options.tool === "wand" && /* @__PURE__ */ jsxs5("div", { className: "flex flex-col gap-2", children: [
658
+ /* @__PURE__ */ jsxs5("label", { className: "flex flex-col gap-1", children: [
659
+ /* @__PURE__ */ jsxs5("span", { className: "flex justify-between text-slate-400", children: [
660
+ /* @__PURE__ */ jsx5("span", { children: "Tolerance" }),
661
+ /* @__PURE__ */ jsx5("span", { className: "font-mono", children: options.tolerance })
662
+ ] }),
663
+ /* @__PURE__ */ jsx5(
664
+ "input",
665
+ {
666
+ type: "range",
667
+ min: 0,
668
+ max: 255,
669
+ step: 1,
670
+ "aria-label": "Tolerance",
671
+ value: options.tolerance,
672
+ onChange: (e) => set({ tolerance: Number(e.target.value) }),
673
+ className: "w-full accent-indigo-500"
674
+ }
675
+ )
676
+ ] }),
677
+ /* @__PURE__ */ jsxs5("label", { className: "flex items-center gap-2 text-slate-300", children: [
678
+ /* @__PURE__ */ jsx5("input", { type: "checkbox", checked: options.contiguous, onChange: (e) => set({ contiguous: e.target.checked }) }),
679
+ "Contiguous"
680
+ ] }),
681
+ /* @__PURE__ */ jsxs5("label", { className: "flex items-center gap-2 text-slate-300", children: [
682
+ /* @__PURE__ */ jsx5("input", { type: "checkbox", checked: options.sampleMerged, onChange: (e) => set({ sampleMerged: e.target.checked }) }),
683
+ "Sample adjusted image"
684
+ ] })
685
+ ] }),
686
+ /* @__PURE__ */ jsxs5("label", { className: "flex items-center gap-2 text-slate-300", children: [
687
+ /* @__PURE__ */ jsx5("input", { type: "checkbox", checked: options.antiAlias, onChange: (e) => set({ antiAlias: e.target.checked }) }),
688
+ "Anti-alias"
689
+ ] }),
690
+ /* @__PURE__ */ jsxs5("div", { className: "flex flex-wrap gap-1", children: [
691
+ /* @__PURE__ */ jsx5("button", { type: "button", className: btn(false), onClick: () => controller.selectAll(), children: "Select All" }),
692
+ /* @__PURE__ */ jsx5("button", { type: "button", className: btn(false), disabled: !sel, onClick: () => controller.deselect(), children: "Deselect" }),
693
+ /* @__PURE__ */ jsx5("button", { type: "button", className: btn(false), onClick: () => controller.invertSelection(), children: "Inverse" }),
694
+ /* @__PURE__ */ jsx5("button", { type: "button", "aria-pressed": qm, className: btn(qm), onClick: () => controller.setQuickMask(!qm), children: "Quick Mask" })
695
+ ] }),
696
+ /* @__PURE__ */ jsxs5("div", { className: "flex flex-wrap items-center gap-1", children: [
697
+ /* @__PURE__ */ jsxs5("label", { className: "flex items-center gap-1 text-slate-400", children: [
698
+ "Radius",
699
+ /* @__PURE__ */ jsx5(
700
+ "input",
701
+ {
702
+ type: "number",
703
+ min: 0,
704
+ max: 500,
705
+ step: 1,
706
+ "aria-label": "Modify radius",
707
+ value: radius,
708
+ onChange: (e) => setRadius(Math.max(0, Number(e.target.value) || 0)),
709
+ className: "w-14 bg-slate-950 border border-slate-800 rounded px-1 py-0.5 text-slate-200"
710
+ }
711
+ )
712
+ ] }),
713
+ MODIFY_OPS.map(({ op, label }) => /* @__PURE__ */ jsx5("button", { type: "button", className: btn(false), disabled: !sel, onClick: () => controller.modifySelection(op, radius), children: label }, op))
714
+ ] }),
715
+ /* @__PURE__ */ jsx5("p", { "data-testid": "selection-status", className: "text-slate-400", children: describeSelection(sel) })
716
+ ] });
717
+ };
718
+
719
+ // src/image-editor/RefineEdgePanel.tsx
720
+ import { useState as useState6 } from "react";
721
+ import {
722
+ ADJUSTMENT_KINDS as ADJUSTMENT_KINDS2,
723
+ REFINE_EDGE_CONTROLS,
724
+ adjustmentKindLabel as adjustmentKindLabel2,
725
+ layerMaskFromSelection
726
+ } from "@pixerate/editor/image-editor";
727
+ import { Fragment, jsx as jsx6, jsxs as jsxs6 } from "react/jsx-runtime";
728
+ var DEFAULT_PARAMS = { radius: 8, smartRadius: false, smooth: 0, feather: 0, contrast: 0, shiftEdge: 0 };
729
+ var button = "px-2 py-1 rounded-md border border-slate-800 bg-slate-950 text-[11px] text-slate-200 hover:text-white disabled:opacity-40";
730
+ var RefineEdgePanel = ({ controller, selection, layers, className = "" }) => {
731
+ const [params, setParams] = useState6(DEFAULT_PARAMS);
732
+ const [busy, setBusy] = useState6(false);
733
+ const [error, setError] = useState6(null);
734
+ const [layerId, setLayerId] = useState6("");
735
+ const [newKind, setNewKind] = useState6("hueSaturation");
736
+ const sel = selection === void 0 ? controller.getSelection() : selection;
737
+ const list = layers ?? controller.getAdjustmentLayers();
738
+ const target = list.find((l) => l.id === layerId) ?? list[list.length - 1];
739
+ const refine = async () => {
740
+ setBusy(true);
741
+ setError(null);
742
+ try {
743
+ await controller.refineSelection(params);
744
+ } catch (err) {
745
+ setError(err instanceof Error ? err.message : String(err));
746
+ } finally {
747
+ setBusy(false);
748
+ }
749
+ };
750
+ return /* @__PURE__ */ jsxs6("div", { "data-testid": "refine-edge-panel", className: `flex flex-col gap-3 text-xs ${className}`, children: [
751
+ /* @__PURE__ */ jsx6("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Refine Edge" }),
752
+ REFINE_EDGE_CONTROLS.map((c) => /* @__PURE__ */ jsxs6("label", { className: "flex flex-col gap-1", children: [
753
+ /* @__PURE__ */ jsxs6("span", { className: "flex justify-between text-slate-400", children: [
754
+ /* @__PURE__ */ jsx6("span", { children: c.label }),
755
+ /* @__PURE__ */ jsxs6("span", { className: "font-mono", children: [
756
+ params[c.id],
757
+ c.unit
758
+ ] })
759
+ ] }),
760
+ /* @__PURE__ */ jsx6(
761
+ "input",
762
+ {
763
+ type: "range",
764
+ min: c.min,
765
+ max: c.max,
766
+ step: c.step,
767
+ "aria-label": c.label,
768
+ value: params[c.id],
769
+ onChange: (e) => setParams({ ...params, [c.id]: Number(e.target.value) }),
770
+ className: "w-full accent-indigo-500"
771
+ }
772
+ )
773
+ ] }, c.id)),
774
+ /* @__PURE__ */ jsxs6("label", { className: "flex items-center gap-2 text-slate-300", children: [
775
+ /* @__PURE__ */ jsx6("input", { type: "checkbox", checked: params.smartRadius, onChange: (e) => setParams({ ...params, smartRadius: e.target.checked }) }),
776
+ "Smart Radius"
777
+ ] }),
778
+ /* @__PURE__ */ jsxs6("div", { className: "flex gap-1", children: [
779
+ /* @__PURE__ */ jsx6("button", { type: "button", className: button, disabled: !sel || busy, onClick: refine, children: "Refine Edge" }),
780
+ /* @__PURE__ */ jsx6("button", { type: "button", className: button, onClick: () => setParams(DEFAULT_PARAMS), children: "Reset" })
781
+ ] }),
782
+ error && /* @__PURE__ */ jsx6("p", { role: "alert", className: "text-rose-400", children: error }),
783
+ /* @__PURE__ */ jsx6("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px] mt-2", children: "Layer Mask" }),
784
+ /* @__PURE__ */ jsxs6("div", { className: "flex gap-1 items-center", children: [
785
+ /* @__PURE__ */ jsx6(
786
+ "select",
787
+ {
788
+ "aria-label": "New masked layer kind",
789
+ value: newKind,
790
+ onChange: (e) => setNewKind(e.target.value),
791
+ className: "flex-1 bg-slate-950 border border-slate-800 rounded px-1 py-1 text-slate-200",
792
+ children: ADJUSTMENT_KINDS2.map((k) => /* @__PURE__ */ jsx6("option", { value: k.kind, children: k.label }, k.kind))
793
+ }
794
+ ),
795
+ /* @__PURE__ */ jsx6(
796
+ "button",
797
+ {
798
+ type: "button",
799
+ className: button,
800
+ disabled: !sel,
801
+ onClick: () => sel && setLayerId(controller.addAdjustmentLayer({ kind: newKind, mask: layerMaskFromSelection(sel) })),
802
+ children: "New Masked Layer"
803
+ }
804
+ )
805
+ ] }),
806
+ list.length > 0 && target && /* @__PURE__ */ jsxs6("div", { className: "flex flex-col gap-2", children: [
807
+ /* @__PURE__ */ jsx6(
808
+ "select",
809
+ {
810
+ "aria-label": "Mask layer",
811
+ value: target.id,
812
+ onChange: (e) => setLayerId(e.target.value),
813
+ className: "bg-slate-950 border border-slate-800 rounded px-1 py-1 text-slate-200",
814
+ children: list.map((l) => /* @__PURE__ */ jsxs6("option", { value: l.id, children: [
815
+ l.name || adjustmentKindLabel2(l.kind),
816
+ l.mask ? " (masked)" : ""
817
+ ] }, l.id))
818
+ }
819
+ ),
820
+ /* @__PURE__ */ jsxs6("div", { className: "flex flex-wrap gap-1", children: [
821
+ /* @__PURE__ */ jsx6("button", { type: "button", className: button, disabled: !sel, onClick: () => controller.applySelectionAsLayerMask(target.id), children: "Mask with Selection" }),
822
+ /* @__PURE__ */ jsx6("button", { type: "button", className: button, disabled: !target.mask, onClick: () => controller.selectionFromLayerMask(target.id), children: "Load as Selection" }),
823
+ /* @__PURE__ */ jsx6("button", { type: "button", className: button, disabled: !target.mask, onClick: () => controller.setAdjustmentLayerMask(target.id, null), children: "Remove Mask" })
824
+ ] }),
825
+ target.mask && /* @__PURE__ */ jsxs6(Fragment, { children: [
826
+ /* @__PURE__ */ jsxs6("label", { className: "flex flex-col gap-1", children: [
827
+ /* @__PURE__ */ jsxs6("span", { className: "flex justify-between text-slate-400", children: [
828
+ /* @__PURE__ */ jsx6("span", { children: "Density" }),
829
+ /* @__PURE__ */ jsxs6("span", { className: "font-mono", children: [
830
+ Math.round((target.mask.density ?? 1) * 100),
831
+ "%"
832
+ ] })
833
+ ] }),
834
+ /* @__PURE__ */ jsx6(
835
+ "input",
836
+ {
837
+ type: "range",
838
+ min: 0,
839
+ max: 100,
840
+ step: 1,
841
+ "aria-label": "Mask density",
842
+ value: Math.round((target.mask.density ?? 1) * 100),
843
+ onChange: (e) => controller.setAdjustmentLayerMaskProps(target.id, { density: Number(e.target.value) / 100 }),
844
+ className: "w-full accent-indigo-500"
845
+ }
846
+ )
847
+ ] }),
848
+ /* @__PURE__ */ jsxs6("label", { className: "flex flex-col gap-1", children: [
849
+ /* @__PURE__ */ jsxs6("span", { className: "flex justify-between text-slate-400", children: [
850
+ /* @__PURE__ */ jsx6("span", { children: "Mask Feather" }),
851
+ /* @__PURE__ */ jsxs6("span", { className: "font-mono", children: [
852
+ target.mask.feather ?? 0,
853
+ "px"
854
+ ] })
855
+ ] }),
856
+ /* @__PURE__ */ jsx6(
857
+ "input",
858
+ {
859
+ type: "range",
860
+ min: 0,
861
+ max: 50,
862
+ step: 0.5,
863
+ "aria-label": "Mask feather",
864
+ value: target.mask.feather ?? 0,
865
+ onChange: (e) => controller.setAdjustmentLayerMaskProps(target.id, { feather: Number(e.target.value) }),
866
+ className: "w-full accent-indigo-500"
867
+ }
868
+ )
869
+ ] })
870
+ ] })
871
+ ] })
872
+ ] });
873
+ };
874
+
623
875
  // src/image-editor/ImageEditor.tsx
624
- import { Fragment, jsx as jsx5, jsxs as jsxs5 } from "react/jsx-runtime";
876
+ import { Fragment as Fragment2, jsx as jsx7, jsxs as jsxs7 } from "react/jsx-runtime";
625
877
  var ImageEditor = ({
626
878
  editor: externalEditor,
627
879
  src,
@@ -639,14 +891,23 @@ var ImageEditor = ({
639
891
  const legacyProcess = normalizeProcessVersion(state.adjustments.process) < LATEST_PROCESS_VERSION;
640
892
  const canvasRef = useRef3(null);
641
893
  const containerRef = useRef3(null);
642
- const [activeTab, setActiveTab] = useState5("crop");
643
- const [activeCropRatio, setActiveCropRatio] = useState5(null);
644
- const [inpaintPrompt, setInpaintPrompt] = useState5("");
645
- const [inpaintMaskMode, setInpaintMaskMode] = useState5("annotations");
646
- const [isRemovingBg, setIsRemovingBg] = useState5(false);
647
- const [isInpainting, setIsInpainting] = useState5(false);
648
- const [aiError, setAiError] = useState5(null);
649
- const [aiSuccess, setAiSuccess] = useState5(null);
894
+ const [activeTab, setActiveTab] = useState7("crop");
895
+ const [activeCropRatio, setActiveCropRatio] = useState7(null);
896
+ const [selectionOptions, setSelectionOptions] = useState7(DEFAULT_SELECTION_TOOL_OPTIONS);
897
+ const selectionOptionsRef = useRef3(selectionOptions);
898
+ selectionOptionsRef.current = selectionOptions;
899
+ const selectionGestureRef = useRef3(null);
900
+ if (!selectionGestureRef.current || selectionGestureRef.current.controller !== controller) {
901
+ selectionGestureRef.current = new SelectionGesture(controller, () => selectionOptionsRef.current);
902
+ }
903
+ const selectionDraftRef = useRef3(null);
904
+ const [selectionError, setSelectionError] = useState7(null);
905
+ const [inpaintPrompt, setInpaintPrompt] = useState7("");
906
+ const [inpaintMaskMode, setInpaintMaskMode] = useState7("annotations");
907
+ const [isRemovingBg, setIsRemovingBg] = useState7(false);
908
+ const [isInpainting, setIsInpainting] = useState7(false);
909
+ const [aiError, setAiError] = useState7(null);
910
+ const [aiSuccess, setAiSuccess] = useState7(null);
650
911
  const effectiveOnInpaint = onInpaint || aiHooks?.onInpaint;
651
912
  const effectiveOnRemoveBg = onRemoveBackground || aiHooks?.onRemoveBackground;
652
913
  const handleRemoveBackground = async () => {
@@ -708,10 +969,10 @@ var ImageEditor = ({
708
969
  setIsInpainting(false);
709
970
  }
710
971
  };
711
- const [activeColor, setActiveColor] = useState5("#ef4444");
712
- const [strokeWidth, setStrokeWidth] = useState5(3);
713
- const [fontSize, setFontSize] = useState5(24);
714
- const [textInput, setTextInput] = useState5("");
972
+ const [activeColor, setActiveColor] = useState7("#ef4444");
973
+ const [strokeWidth, setStrokeWidth] = useState7(3);
974
+ const [fontSize, setFontSize] = useState7(24);
975
+ const [textInput, setTextInput] = useState7("");
715
976
  const draftAnnotationRef = useRef3(null);
716
977
  const draftCropRef = useRef3(null);
717
978
  const cropDragInfoRef = useRef3(null);
@@ -733,7 +994,8 @@ var ImageEditor = ({
733
994
  showSelectionOverlay: true,
734
995
  interactive: true,
735
996
  draftAnnotation: draftAnnotation !== void 0 ? draftAnnotation : draftAnnotationRef.current,
736
- draftCrop: draftCrop !== void 0 ? draftCrop : draftCropRef.current
997
+ draftCrop: draftCrop !== void 0 ? draftCrop : draftCropRef.current,
998
+ draftSelectionPath: selectionDraftRef.current
737
999
  });
738
1000
  },
739
1001
  [controller, activeTab]
@@ -781,6 +1043,12 @@ var ImageEditor = ({
781
1043
  const canvas = canvasRef.current;
782
1044
  if (!canvas) return;
783
1045
  const canvasPt = getCanvasEventPoint(e);
1046
+ if (activeTab === "select") {
1047
+ const gesture = selectionGestureRef.current;
1048
+ const imgPt = canvasToImagePoint(canvasPt, state, canvas.width, canvas.height, false);
1049
+ void gesture.begin(imgPt, e).then(() => setSelectionError(gesture.error));
1050
+ return;
1051
+ }
784
1052
  if (activeTab === "crop") {
785
1053
  const activeCrop = draftCropRef.current || state.crop || {
786
1054
  x: 0,
@@ -847,6 +1115,14 @@ var ImageEditor = ({
847
1115
  const canvas = canvasRef.current;
848
1116
  if (!canvas) return;
849
1117
  const canvasPt = getCanvasEventPoint(e);
1118
+ if (activeTab === "select") {
1119
+ const gesture = selectionGestureRef.current;
1120
+ if (gesture.active && gesture.move(canvasToImagePoint(canvasPt, state, canvas.width, canvas.height, false))) {
1121
+ selectionDraftRef.current = gesture.draftPath;
1122
+ renderCanvas();
1123
+ }
1124
+ return;
1125
+ }
850
1126
  if (activeTab === "crop") {
851
1127
  const drag = cropDragInfoRef.current;
852
1128
  if (drag) {
@@ -995,6 +1271,15 @@ var ImageEditor = ({
995
1271
  const canvas = canvasRef.current;
996
1272
  if (!canvas) return;
997
1273
  const canvasPt = getCanvasEventPoint(e);
1274
+ if (activeTab === "select") {
1275
+ const gesture = selectionGestureRef.current;
1276
+ if (gesture.active) {
1277
+ gesture.end(canvasToImagePoint(canvasPt, state, canvas.width, canvas.height, false), e);
1278
+ selectionDraftRef.current = null;
1279
+ renderCanvas();
1280
+ }
1281
+ return;
1282
+ }
998
1283
  if (activeTab === "crop") {
999
1284
  if (cropDragInfoRef.current) {
1000
1285
  if (draftCropRef.current && draftCropRef.current.width >= 20 && draftCropRef.current.height >= 20) {
@@ -1109,15 +1394,15 @@ var ImageEditor = ({
1109
1394
  link.click();
1110
1395
  }
1111
1396
  };
1112
- return /* @__PURE__ */ jsxs5(
1397
+ return /* @__PURE__ */ jsxs7(
1113
1398
  "div",
1114
1399
  {
1115
1400
  className: `flex flex-col bg-slate-900 border border-slate-800 rounded-xl overflow-hidden shadow-2xl text-slate-100 ${className}`,
1116
1401
  style,
1117
1402
  children: [
1118
- /* @__PURE__ */ jsxs5("div", { className: "flex flex-wrap items-center justify-between px-4 py-3 bg-slate-950/80 border-b border-slate-800 gap-3", children: [
1119
- /* @__PURE__ */ jsxs5("div", { className: "flex items-center gap-1 bg-slate-900 p-1 rounded-lg border border-slate-800 text-xs", children: [
1120
- /* @__PURE__ */ jsx5(
1403
+ /* @__PURE__ */ jsxs7("div", { className: "flex flex-wrap items-center justify-between px-4 py-3 bg-slate-950/80 border-b border-slate-800 gap-3", children: [
1404
+ /* @__PURE__ */ jsxs7("div", { className: "flex items-center gap-1 bg-slate-900 p-1 rounded-lg border border-slate-800 text-xs", children: [
1405
+ /* @__PURE__ */ jsx7(
1121
1406
  "button",
1122
1407
  {
1123
1408
  type: "button",
@@ -1129,7 +1414,7 @@ var ImageEditor = ({
1129
1414
  children: "Transform & Crop"
1130
1415
  }
1131
1416
  ),
1132
- /* @__PURE__ */ jsx5(
1417
+ /* @__PURE__ */ jsx7(
1133
1418
  "button",
1134
1419
  {
1135
1420
  type: "button",
@@ -1141,7 +1426,19 @@ var ImageEditor = ({
1141
1426
  children: "Adjustments"
1142
1427
  }
1143
1428
  ),
1144
- /* @__PURE__ */ jsx5(
1429
+ /* @__PURE__ */ jsx7(
1430
+ "button",
1431
+ {
1432
+ type: "button",
1433
+ onClick: () => {
1434
+ setActiveTab("select");
1435
+ editor.setTool("select");
1436
+ },
1437
+ className: `px-3 py-1.5 rounded-md font-medium transition-colors ${activeTab === "select" ? "bg-indigo-600 text-white shadow" : "text-slate-400 hover:text-slate-200"}`,
1438
+ children: "Select & Mask"
1439
+ }
1440
+ ),
1441
+ /* @__PURE__ */ jsx7(
1145
1442
  "button",
1146
1443
  {
1147
1444
  type: "button",
@@ -1153,7 +1450,7 @@ var ImageEditor = ({
1153
1450
  children: "Annotations"
1154
1451
  }
1155
1452
  ),
1156
- /* @__PURE__ */ jsx5(
1453
+ /* @__PURE__ */ jsx7(
1157
1454
  "button",
1158
1455
  {
1159
1456
  type: "button",
@@ -1165,7 +1462,7 @@ var ImageEditor = ({
1165
1462
  children: "Depth Mask"
1166
1463
  }
1167
1464
  ),
1168
- /* @__PURE__ */ jsxs5(
1465
+ /* @__PURE__ */ jsxs7(
1169
1466
  "button",
1170
1467
  {
1171
1468
  type: "button",
@@ -1175,14 +1472,14 @@ var ImageEditor = ({
1175
1472
  },
1176
1473
  className: `px-3 py-1.5 rounded-md font-medium transition-colors flex items-center gap-1.5 ${activeTab === "ai" ? "bg-indigo-600 text-white shadow" : "text-slate-400 hover:text-slate-200"}`,
1177
1474
  children: [
1178
- /* @__PURE__ */ jsx5("svg", { className: "w-3.5 h-3.5", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: /* @__PURE__ */ jsx5("path", { d: "M12 2v4M12 18v4M4.93 4.93l2.83 2.83M16.24 16.24l2.83 2.83M2 12h4M18 12h4M4.93 19.07l2.83-2.83M16.24 7.76l2.83-2.83" }) }),
1475
+ /* @__PURE__ */ jsx7("svg", { className: "w-3.5 h-3.5", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: /* @__PURE__ */ jsx7("path", { d: "M12 2v4M12 18v4M4.93 4.93l2.83 2.83M16.24 16.24l2.83 2.83M2 12h4M18 12h4M4.93 19.07l2.83-2.83M16.24 7.76l2.83-2.83" }) }),
1179
1476
  "AI Tools"
1180
1477
  ]
1181
1478
  }
1182
1479
  )
1183
1480
  ] }),
1184
- /* @__PURE__ */ jsxs5("div", { className: "flex items-center gap-2 text-xs", children: [
1185
- /* @__PURE__ */ jsx5(
1481
+ /* @__PURE__ */ jsxs7("div", { className: "flex items-center gap-2 text-xs", children: [
1482
+ /* @__PURE__ */ jsx7(
1186
1483
  "button",
1187
1484
  {
1188
1485
  type: "button",
@@ -1193,7 +1490,7 @@ var ImageEditor = ({
1193
1490
  children: "\u21A9"
1194
1491
  }
1195
1492
  ),
1196
- /* @__PURE__ */ jsx5(
1493
+ /* @__PURE__ */ jsx7(
1197
1494
  "button",
1198
1495
  {
1199
1496
  type: "button",
@@ -1204,7 +1501,7 @@ var ImageEditor = ({
1204
1501
  children: "\u21AA"
1205
1502
  }
1206
1503
  ),
1207
- /* @__PURE__ */ jsx5(
1504
+ /* @__PURE__ */ jsx7(
1208
1505
  "button",
1209
1506
  {
1210
1507
  type: "button",
@@ -1213,8 +1510,8 @@ var ImageEditor = ({
1213
1510
  children: "Reset"
1214
1511
  }
1215
1512
  ),
1216
- /* @__PURE__ */ jsx5("div", { className: "h-4 w-px bg-slate-800 mx-1" }),
1217
- /* @__PURE__ */ jsx5(
1513
+ /* @__PURE__ */ jsx7("div", { className: "h-4 w-px bg-slate-800 mx-1" }),
1514
+ /* @__PURE__ */ jsx7(
1218
1515
  "button",
1219
1516
  {
1220
1517
  type: "button",
@@ -1224,11 +1521,11 @@ var ImageEditor = ({
1224
1521
  children: "-"
1225
1522
  }
1226
1523
  ),
1227
- /* @__PURE__ */ jsxs5("span", { className: "font-mono text-slate-400 w-10 text-center", children: [
1524
+ /* @__PURE__ */ jsxs7("span", { className: "font-mono text-slate-400 w-10 text-center", children: [
1228
1525
  Math.round(state.zoom * 100),
1229
1526
  "%"
1230
1527
  ] }),
1231
- /* @__PURE__ */ jsx5(
1528
+ /* @__PURE__ */ jsx7(
1232
1529
  "button",
1233
1530
  {
1234
1531
  type: "button",
@@ -1238,8 +1535,8 @@ var ImageEditor = ({
1238
1535
  children: "+"
1239
1536
  }
1240
1537
  ),
1241
- /* @__PURE__ */ jsx5("div", { className: "h-4 w-px bg-slate-800 mx-1" }),
1242
- /* @__PURE__ */ jsx5(
1538
+ /* @__PURE__ */ jsx7("div", { className: "h-4 w-px bg-slate-800 mx-1" }),
1539
+ /* @__PURE__ */ jsx7(
1243
1540
  "button",
1244
1541
  {
1245
1542
  type: "button",
@@ -1250,7 +1547,7 @@ var ImageEditor = ({
1250
1547
  children: "Hold Compare"
1251
1548
  }
1252
1549
  ),
1253
- /* @__PURE__ */ jsx5(
1550
+ /* @__PURE__ */ jsx7(
1254
1551
  "button",
1255
1552
  {
1256
1553
  type: "button",
@@ -1261,13 +1558,13 @@ var ImageEditor = ({
1261
1558
  )
1262
1559
  ] })
1263
1560
  ] }),
1264
- /* @__PURE__ */ jsxs5("div", { className: "flex flex-col md:flex-row flex-1 min-h-[520px] md:h-[560px]", children: [
1265
- /* @__PURE__ */ jsx5(
1561
+ /* @__PURE__ */ jsxs7("div", { className: "flex flex-col md:flex-row flex-1 min-h-[520px] md:h-[560px]", children: [
1562
+ /* @__PURE__ */ jsx7(
1266
1563
  "div",
1267
1564
  {
1268
1565
  ref: containerRef,
1269
1566
  className: "relative flex-1 h-[360px] md:h-full min-h-[320px] bg-slate-950 overflow-hidden select-none",
1270
- children: /* @__PURE__ */ jsx5(
1567
+ children: /* @__PURE__ */ jsx7(
1271
1568
  "canvas",
1272
1569
  {
1273
1570
  ref: canvasRef,
@@ -1280,11 +1577,11 @@ var ImageEditor = ({
1280
1577
  )
1281
1578
  }
1282
1579
  ),
1283
- /* @__PURE__ */ jsxs5("div", { className: "w-full md:w-80 bg-slate-900/90 border-t md:border-t-0 md:border-l border-slate-800 p-4 overflow-y-auto h-auto md:h-full md:max-h-[560px]", children: [
1284
- activeTab === "crop" && /* @__PURE__ */ jsxs5("div", { className: "flex flex-col gap-4 text-xs", children: [
1285
- /* @__PURE__ */ jsx5("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Aspect Ratio Presets" }),
1286
- /* @__PURE__ */ jsxs5("div", { className: "grid grid-cols-3 gap-2", children: [
1287
- /* @__PURE__ */ jsx5(
1580
+ /* @__PURE__ */ jsxs7("div", { className: "w-full md:w-80 bg-slate-900/90 border-t md:border-t-0 md:border-l border-slate-800 p-4 overflow-y-auto h-auto md:h-full md:max-h-[560px]", children: [
1581
+ activeTab === "crop" && /* @__PURE__ */ jsxs7("div", { className: "flex flex-col gap-4 text-xs", children: [
1582
+ /* @__PURE__ */ jsx7("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Aspect Ratio Presets" }),
1583
+ /* @__PURE__ */ jsxs7("div", { className: "grid grid-cols-3 gap-2", children: [
1584
+ /* @__PURE__ */ jsx7(
1288
1585
  "button",
1289
1586
  {
1290
1587
  type: "button",
@@ -1296,7 +1593,7 @@ var ImageEditor = ({
1296
1593
  children: "Freeform"
1297
1594
  }
1298
1595
  ),
1299
- /* @__PURE__ */ jsx5(
1596
+ /* @__PURE__ */ jsx7(
1300
1597
  "button",
1301
1598
  {
1302
1599
  type: "button",
@@ -1308,7 +1605,7 @@ var ImageEditor = ({
1308
1605
  children: "1:1 Square"
1309
1606
  }
1310
1607
  ),
1311
- /* @__PURE__ */ jsx5(
1608
+ /* @__PURE__ */ jsx7(
1312
1609
  "button",
1313
1610
  {
1314
1611
  type: "button",
@@ -1320,7 +1617,7 @@ var ImageEditor = ({
1320
1617
  children: "4:3 Standard"
1321
1618
  }
1322
1619
  ),
1323
- /* @__PURE__ */ jsx5(
1620
+ /* @__PURE__ */ jsx7(
1324
1621
  "button",
1325
1622
  {
1326
1623
  type: "button",
@@ -1332,7 +1629,7 @@ var ImageEditor = ({
1332
1629
  children: "16:9 Wide"
1333
1630
  }
1334
1631
  ),
1335
- /* @__PURE__ */ jsx5(
1632
+ /* @__PURE__ */ jsx7(
1336
1633
  "button",
1337
1634
  {
1338
1635
  type: "button",
@@ -1344,7 +1641,7 @@ var ImageEditor = ({
1344
1641
  children: "3:2 Photo"
1345
1642
  }
1346
1643
  ),
1347
- /* @__PURE__ */ jsx5(
1644
+ /* @__PURE__ */ jsx7(
1348
1645
  "button",
1349
1646
  {
1350
1647
  type: "button",
@@ -1357,10 +1654,10 @@ var ImageEditor = ({
1357
1654
  }
1358
1655
  )
1359
1656
  ] }),
1360
- /* @__PURE__ */ jsx5("div", { className: "h-px bg-slate-800 my-1" }),
1361
- /* @__PURE__ */ jsx5("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Orientation & Flips" }),
1362
- /* @__PURE__ */ jsxs5("div", { className: "grid grid-cols-2 gap-2", children: [
1363
- /* @__PURE__ */ jsx5(
1657
+ /* @__PURE__ */ jsx7("div", { className: "h-px bg-slate-800 my-1" }),
1658
+ /* @__PURE__ */ jsx7("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Orientation & Flips" }),
1659
+ /* @__PURE__ */ jsxs7("div", { className: "grid grid-cols-2 gap-2", children: [
1660
+ /* @__PURE__ */ jsx7(
1364
1661
  "button",
1365
1662
  {
1366
1663
  type: "button",
@@ -1369,7 +1666,7 @@ var ImageEditor = ({
1369
1666
  children: "Rotate -90\xB0"
1370
1667
  }
1371
1668
  ),
1372
- /* @__PURE__ */ jsx5(
1669
+ /* @__PURE__ */ jsx7(
1373
1670
  "button",
1374
1671
  {
1375
1672
  type: "button",
@@ -1378,7 +1675,7 @@ var ImageEditor = ({
1378
1675
  children: "Rotate +90\xB0"
1379
1676
  }
1380
1677
  ),
1381
- /* @__PURE__ */ jsx5(
1678
+ /* @__PURE__ */ jsx7(
1382
1679
  "button",
1383
1680
  {
1384
1681
  type: "button",
@@ -1387,7 +1684,7 @@ var ImageEditor = ({
1387
1684
  children: "Flip Horizontal"
1388
1685
  }
1389
1686
  ),
1390
- /* @__PURE__ */ jsx5(
1687
+ /* @__PURE__ */ jsx7(
1391
1688
  "button",
1392
1689
  {
1393
1690
  type: "button",
@@ -1398,10 +1695,10 @@ var ImageEditor = ({
1398
1695
  )
1399
1696
  ] })
1400
1697
  ] }),
1401
- activeTab === "adjust" && /* @__PURE__ */ jsxs5("div", { className: "flex flex-col gap-3 text-xs", children: [
1402
- /* @__PURE__ */ jsxs5("div", { className: "flex items-center justify-between", children: [
1403
- /* @__PURE__ */ jsx5("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Color Adjustments" }),
1404
- /* @__PURE__ */ jsx5(
1698
+ activeTab === "adjust" && /* @__PURE__ */ jsxs7("div", { className: "flex flex-col gap-3 text-xs", children: [
1699
+ /* @__PURE__ */ jsxs7("div", { className: "flex items-center justify-between", children: [
1700
+ /* @__PURE__ */ jsx7("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Color Adjustments" }),
1701
+ /* @__PURE__ */ jsx7(
1405
1702
  "button",
1406
1703
  {
1407
1704
  type: "button",
@@ -1411,9 +1708,9 @@ var ImageEditor = ({
1411
1708
  }
1412
1709
  )
1413
1710
  ] }),
1414
- /* @__PURE__ */ jsx5(Histogram, { histogram: editor.histogram }),
1415
- IMAGE_ADJUSTMENT_CONTROLS.map((spec) => /* @__PURE__ */ jsxs5(React4.Fragment, { children: [
1416
- /* @__PURE__ */ jsx5(
1711
+ /* @__PURE__ */ jsx7(Histogram, { histogram: editor.histogram }),
1712
+ IMAGE_ADJUSTMENT_CONTROLS.map((spec) => /* @__PURE__ */ jsxs7(React6.Fragment, { children: [
1713
+ /* @__PURE__ */ jsx7(
1417
1714
  ControlSlider,
1418
1715
  {
1419
1716
  spec,
@@ -1422,14 +1719,14 @@ var ImageEditor = ({
1422
1719
  onChange: (v) => editor.setAdjustments({ [spec.id]: v })
1423
1720
  }
1424
1721
  ),
1425
- spec.id === "tint" && legacyProcess && /* @__PURE__ */ jsxs5(
1722
+ spec.id === "tint" && legacyProcess && /* @__PURE__ */ jsxs7(
1426
1723
  "div",
1427
1724
  {
1428
1725
  className: "flex items-center justify-between gap-2 rounded border border-amber-500/30 bg-amber-500/10 px-2 py-1.5 text-[10px] text-amber-200",
1429
1726
  "data-testid": "image-editor-process-notice",
1430
1727
  children: [
1431
- /* @__PURE__ */ jsx5("span", { children: "Legacy rendering (process 1). Tint needs the current process." }),
1432
- /* @__PURE__ */ jsx5(
1728
+ /* @__PURE__ */ jsx7("span", { children: "Legacy rendering (process 1). Tint needs the current process." }),
1729
+ /* @__PURE__ */ jsx7(
1433
1730
  "button",
1434
1731
  {
1435
1732
  type: "button",
@@ -1442,7 +1739,7 @@ var ImageEditor = ({
1442
1739
  }
1443
1740
  )
1444
1741
  ] }, spec.id)),
1445
- /* @__PURE__ */ jsx5("div", { className: "border-t border-slate-700/60 pt-3", children: /* @__PURE__ */ jsx5(
1742
+ /* @__PURE__ */ jsx7("div", { className: "border-t border-slate-700/60 pt-3", children: /* @__PURE__ */ jsx7(
1446
1743
  AdjustmentLayersPanel,
1447
1744
  {
1448
1745
  controller,
@@ -1451,9 +1748,9 @@ var ImageEditor = ({
1451
1748
  }
1452
1749
  ) })
1453
1750
  ] }),
1454
- activeTab === "annotate" && /* @__PURE__ */ jsxs5("div", { className: "flex flex-col gap-3 text-xs", children: [
1455
- /* @__PURE__ */ jsx5("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Draw & Annotate" }),
1456
- /* @__PURE__ */ jsx5("div", { className: "grid grid-cols-3 gap-1.5", children: ["pen", "rect", "circle", "arrow", "line"].map((t) => /* @__PURE__ */ jsx5(
1751
+ activeTab === "annotate" && /* @__PURE__ */ jsxs7("div", { className: "flex flex-col gap-3 text-xs", children: [
1752
+ /* @__PURE__ */ jsx7("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Draw & Annotate" }),
1753
+ /* @__PURE__ */ jsx7("div", { className: "grid grid-cols-3 gap-1.5", children: ["pen", "rect", "circle", "arrow", "line"].map((t) => /* @__PURE__ */ jsx7(
1457
1754
  "button",
1458
1755
  {
1459
1756
  type: "button",
@@ -1463,9 +1760,9 @@ var ImageEditor = ({
1463
1760
  },
1464
1761
  t
1465
1762
  )) }),
1466
- /* @__PURE__ */ jsxs5("div", { className: "flex items-center gap-2 mt-2", children: [
1467
- /* @__PURE__ */ jsx5("label", { className: "text-slate-400", children: "Color:" }),
1468
- /* @__PURE__ */ jsx5(
1763
+ /* @__PURE__ */ jsxs7("div", { className: "flex items-center gap-2 mt-2", children: [
1764
+ /* @__PURE__ */ jsx7("label", { className: "text-slate-400", children: "Color:" }),
1765
+ /* @__PURE__ */ jsx7(
1469
1766
  "input",
1470
1767
  {
1471
1768
  type: "color",
@@ -1474,15 +1771,15 @@ var ImageEditor = ({
1474
1771
  className: "w-8 h-8 rounded border border-slate-700 cursor-pointer bg-transparent"
1475
1772
  }
1476
1773
  ),
1477
- /* @__PURE__ */ jsxs5("div", { className: "flex-1 ml-2", children: [
1478
- /* @__PURE__ */ jsxs5("div", { className: "flex justify-between text-slate-400 mb-0.5", children: [
1479
- /* @__PURE__ */ jsx5("span", { children: "Width:" }),
1480
- /* @__PURE__ */ jsxs5("span", { className: "font-mono", children: [
1774
+ /* @__PURE__ */ jsxs7("div", { className: "flex-1 ml-2", children: [
1775
+ /* @__PURE__ */ jsxs7("div", { className: "flex justify-between text-slate-400 mb-0.5", children: [
1776
+ /* @__PURE__ */ jsx7("span", { children: "Width:" }),
1777
+ /* @__PURE__ */ jsxs7("span", { className: "font-mono", children: [
1481
1778
  strokeWidth,
1482
1779
  "px"
1483
1780
  ] })
1484
1781
  ] }),
1485
- /* @__PURE__ */ jsx5(
1782
+ /* @__PURE__ */ jsx7(
1486
1783
  "input",
1487
1784
  {
1488
1785
  type: "range",
@@ -1495,10 +1792,10 @@ var ImageEditor = ({
1495
1792
  )
1496
1793
  ] })
1497
1794
  ] }),
1498
- /* @__PURE__ */ jsx5("div", { className: "h-px bg-slate-800 my-1" }),
1499
- /* @__PURE__ */ jsx5("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Add Text" }),
1500
- /* @__PURE__ */ jsxs5("div", { className: "flex gap-2", children: [
1501
- /* @__PURE__ */ jsx5(
1795
+ /* @__PURE__ */ jsx7("div", { className: "h-px bg-slate-800 my-1" }),
1796
+ /* @__PURE__ */ jsx7("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Add Text" }),
1797
+ /* @__PURE__ */ jsxs7("div", { className: "flex gap-2", children: [
1798
+ /* @__PURE__ */ jsx7(
1502
1799
  "input",
1503
1800
  {
1504
1801
  type: "text",
@@ -1509,7 +1806,7 @@ var ImageEditor = ({
1509
1806
  className: "flex-1 bg-slate-950 border border-slate-700 rounded-lg px-2.5 py-1.5 text-xs text-slate-100 placeholder-slate-500 focus:outline-none focus:border-indigo-500"
1510
1807
  }
1511
1808
  ),
1512
- /* @__PURE__ */ jsx5(
1809
+ /* @__PURE__ */ jsx7(
1513
1810
  "button",
1514
1811
  {
1515
1812
  type: "button",
@@ -1519,14 +1816,14 @@ var ImageEditor = ({
1519
1816
  }
1520
1817
  )
1521
1818
  ] }),
1522
- /* @__PURE__ */ jsxs5("div", { className: "flex items-center justify-between text-slate-400", children: [
1523
- /* @__PURE__ */ jsx5("span", { children: "Font Size:" }),
1524
- /* @__PURE__ */ jsxs5("span", { className: "font-mono", children: [
1819
+ /* @__PURE__ */ jsxs7("div", { className: "flex items-center justify-between text-slate-400", children: [
1820
+ /* @__PURE__ */ jsx7("span", { children: "Font Size:" }),
1821
+ /* @__PURE__ */ jsxs7("span", { className: "font-mono", children: [
1525
1822
  fontSize,
1526
1823
  "px"
1527
1824
  ] })
1528
1825
  ] }),
1529
- /* @__PURE__ */ jsx5(
1826
+ /* @__PURE__ */ jsx7(
1530
1827
  "input",
1531
1828
  {
1532
1829
  type: "range",
@@ -1537,14 +1834,14 @@ var ImageEditor = ({
1537
1834
  className: "w-full accent-indigo-500"
1538
1835
  }
1539
1836
  ),
1540
- /* @__PURE__ */ jsx5("div", { className: "h-px bg-slate-800 my-1" }),
1541
- /* @__PURE__ */ jsxs5("div", { className: "flex items-center justify-between", children: [
1542
- /* @__PURE__ */ jsxs5("span", { className: "text-slate-400", children: [
1837
+ /* @__PURE__ */ jsx7("div", { className: "h-px bg-slate-800 my-1" }),
1838
+ /* @__PURE__ */ jsxs7("div", { className: "flex items-center justify-between", children: [
1839
+ /* @__PURE__ */ jsxs7("span", { className: "text-slate-400", children: [
1543
1840
  "Layers (",
1544
1841
  state.annotations.length,
1545
1842
  ")"
1546
1843
  ] }),
1547
- state.selectedAnnotationId && /* @__PURE__ */ jsx5(
1844
+ state.selectedAnnotationId && /* @__PURE__ */ jsx7(
1548
1845
  "button",
1549
1846
  {
1550
1847
  type: "button",
@@ -1553,7 +1850,7 @@ var ImageEditor = ({
1553
1850
  children: "Delete Selected"
1554
1851
  }
1555
1852
  ),
1556
- state.annotations.length > 0 && /* @__PURE__ */ jsx5(
1853
+ state.annotations.length > 0 && /* @__PURE__ */ jsx7(
1557
1854
  "button",
1558
1855
  {
1559
1856
  type: "button",
@@ -1564,10 +1861,10 @@ var ImageEditor = ({
1564
1861
  )
1565
1862
  ] })
1566
1863
  ] }),
1567
- activeTab === "depth" && /* @__PURE__ */ jsxs5("div", { className: "flex flex-col gap-3 text-xs", children: [
1568
- /* @__PURE__ */ jsxs5("div", { className: "flex items-center justify-between", children: [
1569
- /* @__PURE__ */ jsx5("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Depth Masking" }),
1570
- /* @__PURE__ */ jsx5(
1864
+ activeTab === "depth" && /* @__PURE__ */ jsxs7("div", { className: "flex flex-col gap-3 text-xs", children: [
1865
+ /* @__PURE__ */ jsxs7("div", { className: "flex items-center justify-between", children: [
1866
+ /* @__PURE__ */ jsx7("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Depth Masking" }),
1867
+ /* @__PURE__ */ jsx7(
1571
1868
  "button",
1572
1869
  {
1573
1870
  type: "button",
@@ -1577,8 +1874,8 @@ var ImageEditor = ({
1577
1874
  }
1578
1875
  )
1579
1876
  ] }),
1580
- /* @__PURE__ */ jsxs5("label", { className: "flex items-center gap-2 cursor-pointer text-slate-300", children: [
1581
- /* @__PURE__ */ jsx5(
1877
+ /* @__PURE__ */ jsxs7("label", { className: "flex items-center gap-2 cursor-pointer text-slate-300", children: [
1878
+ /* @__PURE__ */ jsx7(
1582
1879
  "input",
1583
1880
  {
1584
1881
  type: "checkbox",
@@ -1587,12 +1884,12 @@ var ImageEditor = ({
1587
1884
  className: "rounded accent-indigo-500"
1588
1885
  }
1589
1886
  ),
1590
- /* @__PURE__ */ jsx5("span", { children: "Enable Depth / Alpha Mask" })
1887
+ /* @__PURE__ */ jsx7("span", { children: "Enable Depth / Alpha Mask" })
1591
1888
  ] }),
1592
- state.depthMask.enabled && /* @__PURE__ */ jsxs5(Fragment, { children: [
1593
- /* @__PURE__ */ jsxs5("div", { children: [
1594
- /* @__PURE__ */ jsx5("label", { className: "text-slate-400 block mb-1", children: "Mask Image URL:" }),
1595
- /* @__PURE__ */ jsx5(
1889
+ state.depthMask.enabled && /* @__PURE__ */ jsxs7(Fragment2, { children: [
1890
+ /* @__PURE__ */ jsxs7("div", { children: [
1891
+ /* @__PURE__ */ jsx7("label", { className: "text-slate-400 block mb-1", children: "Mask Image URL:" }),
1892
+ /* @__PURE__ */ jsx7(
1596
1893
  "input",
1597
1894
  {
1598
1895
  type: "text",
@@ -1603,8 +1900,8 @@ var ImageEditor = ({
1603
1900
  }
1604
1901
  )
1605
1902
  ] }),
1606
- /* @__PURE__ */ jsxs5("div", { className: "flex gap-2", children: [
1607
- /* @__PURE__ */ jsx5(
1903
+ /* @__PURE__ */ jsxs7("div", { className: "flex gap-2", children: [
1904
+ /* @__PURE__ */ jsx7(
1608
1905
  "button",
1609
1906
  {
1610
1907
  type: "button",
@@ -1613,7 +1910,7 @@ var ImageEditor = ({
1613
1910
  children: "Threshold Mode"
1614
1911
  }
1615
1912
  ),
1616
- /* @__PURE__ */ jsx5(
1913
+ /* @__PURE__ */ jsx7(
1617
1914
  "button",
1618
1915
  {
1619
1916
  type: "button",
@@ -1623,12 +1920,12 @@ var ImageEditor = ({
1623
1920
  }
1624
1921
  )
1625
1922
  ] }),
1626
- /* @__PURE__ */ jsxs5("div", { children: [
1627
- /* @__PURE__ */ jsxs5("div", { className: "flex justify-between text-slate-400 mb-1", children: [
1628
- /* @__PURE__ */ jsx5("span", { children: "Depth Start (Lower):" }),
1629
- /* @__PURE__ */ jsx5("span", { className: "font-mono", children: state.depthMask.depthRange[0] })
1923
+ /* @__PURE__ */ jsxs7("div", { children: [
1924
+ /* @__PURE__ */ jsxs7("div", { className: "flex justify-between text-slate-400 mb-1", children: [
1925
+ /* @__PURE__ */ jsx7("span", { children: "Depth Start (Lower):" }),
1926
+ /* @__PURE__ */ jsx7("span", { className: "font-mono", children: state.depthMask.depthRange[0] })
1630
1927
  ] }),
1631
- /* @__PURE__ */ jsx5(
1928
+ /* @__PURE__ */ jsx7(
1632
1929
  "input",
1633
1930
  {
1634
1931
  type: "range",
@@ -1642,12 +1939,12 @@ var ImageEditor = ({
1642
1939
  }
1643
1940
  )
1644
1941
  ] }),
1645
- /* @__PURE__ */ jsxs5("div", { children: [
1646
- /* @__PURE__ */ jsxs5("div", { className: "flex justify-between text-slate-400 mb-1", children: [
1647
- /* @__PURE__ */ jsx5("span", { children: "Depth Stop (Upper):" }),
1648
- /* @__PURE__ */ jsx5("span", { className: "font-mono", children: state.depthMask.depthRange[1] })
1942
+ /* @__PURE__ */ jsxs7("div", { children: [
1943
+ /* @__PURE__ */ jsxs7("div", { className: "flex justify-between text-slate-400 mb-1", children: [
1944
+ /* @__PURE__ */ jsx7("span", { children: "Depth Stop (Upper):" }),
1945
+ /* @__PURE__ */ jsx7("span", { className: "font-mono", children: state.depthMask.depthRange[1] })
1649
1946
  ] }),
1650
- /* @__PURE__ */ jsx5(
1947
+ /* @__PURE__ */ jsx7(
1651
1948
  "input",
1652
1949
  {
1653
1950
  type: "range",
@@ -1661,12 +1958,12 @@ var ImageEditor = ({
1661
1958
  }
1662
1959
  )
1663
1960
  ] }),
1664
- /* @__PURE__ */ jsxs5("div", { children: [
1665
- /* @__PURE__ */ jsxs5("div", { className: "flex justify-between text-slate-400 mb-1", children: [
1666
- /* @__PURE__ */ jsx5("span", { children: "Softness:" }),
1667
- /* @__PURE__ */ jsx5("span", { className: "font-mono", children: state.depthMask.softness })
1961
+ /* @__PURE__ */ jsxs7("div", { children: [
1962
+ /* @__PURE__ */ jsxs7("div", { className: "flex justify-between text-slate-400 mb-1", children: [
1963
+ /* @__PURE__ */ jsx7("span", { children: "Softness:" }),
1964
+ /* @__PURE__ */ jsx7("span", { className: "font-mono", children: state.depthMask.softness })
1668
1965
  ] }),
1669
- /* @__PURE__ */ jsx5(
1966
+ /* @__PURE__ */ jsx7(
1670
1967
  "input",
1671
1968
  {
1672
1969
  type: "range",
@@ -1678,8 +1975,8 @@ var ImageEditor = ({
1678
1975
  }
1679
1976
  )
1680
1977
  ] }),
1681
- /* @__PURE__ */ jsxs5("label", { className: "flex items-center gap-2 cursor-pointer text-slate-300 mt-1", children: [
1682
- /* @__PURE__ */ jsx5(
1978
+ /* @__PURE__ */ jsxs7("label", { className: "flex items-center gap-2 cursor-pointer text-slate-300 mt-1", children: [
1979
+ /* @__PURE__ */ jsx7(
1683
1980
  "input",
1684
1981
  {
1685
1982
  type: "checkbox",
@@ -1688,52 +1985,66 @@ var ImageEditor = ({
1688
1985
  className: "rounded accent-indigo-500"
1689
1986
  }
1690
1987
  ),
1691
- /* @__PURE__ */ jsx5("span", { children: "Invert Mask" })
1988
+ /* @__PURE__ */ jsx7("span", { children: "Invert Mask" })
1692
1989
  ] })
1693
1990
  ] })
1694
1991
  ] }),
1695
- activeTab === "ai" && /* @__PURE__ */ jsxs5("div", { className: "flex flex-col gap-4 text-xs", children: [
1696
- /* @__PURE__ */ jsxs5("div", { className: "p-3 rounded-lg bg-slate-950/60 border border-slate-800 flex flex-col gap-2.5", children: [
1697
- /* @__PURE__ */ jsxs5("div", { className: "flex items-center justify-between", children: [
1698
- /* @__PURE__ */ jsxs5("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px] flex items-center gap-1.5", children: [
1699
- /* @__PURE__ */ jsx5("svg", { className: "w-3.5 h-3.5 text-indigo-400", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: /* @__PURE__ */ jsx5("path", { d: "M6 3v12M18 9a3 3 0 1 0 0-6 3 3 0 0 0 0 6zM6 21a3 3 0 1 0 0-6 3 3 0 0 0 0 6z" }) }),
1992
+ activeTab === "select" && /* @__PURE__ */ jsxs7("div", { className: "flex flex-col gap-4 text-xs", children: [
1993
+ /* @__PURE__ */ jsx7(
1994
+ SelectionOptionsBar,
1995
+ {
1996
+ controller,
1997
+ options: selectionOptions,
1998
+ onOptionsChange: setSelectionOptions,
1999
+ selection: state.selection ?? null,
2000
+ quickMask: Boolean(state.quickMask)
2001
+ }
2002
+ ),
2003
+ selectionError && /* @__PURE__ */ jsx7("p", { role: "alert", className: "text-rose-400", children: selectionError }),
2004
+ /* @__PURE__ */ jsx7(RefineEdgePanel, { controller, selection: state.selection ?? null, layers: state.adjustments.layers })
2005
+ ] }),
2006
+ activeTab === "ai" && /* @__PURE__ */ jsxs7("div", { className: "flex flex-col gap-4 text-xs", children: [
2007
+ /* @__PURE__ */ jsxs7("div", { className: "p-3 rounded-lg bg-slate-950/60 border border-slate-800 flex flex-col gap-2.5", children: [
2008
+ /* @__PURE__ */ jsxs7("div", { className: "flex items-center justify-between", children: [
2009
+ /* @__PURE__ */ jsxs7("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px] flex items-center gap-1.5", children: [
2010
+ /* @__PURE__ */ jsx7("svg", { className: "w-3.5 h-3.5 text-indigo-400", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: /* @__PURE__ */ jsx7("path", { d: "M6 3v12M18 9a3 3 0 1 0 0-6 3 3 0 0 0 0 6zM6 21a3 3 0 1 0 0-6 3 3 0 0 0 0 6z" }) }),
1700
2011
  "Background Removal"
1701
2012
  ] }),
1702
- isRemovingBg && /* @__PURE__ */ jsx5("span", { className: "inline-flex items-center px-1.5 py-0.5 rounded text-[10px] font-medium bg-indigo-900/60 text-indigo-300 animate-pulse", children: "Removing..." })
2013
+ isRemovingBg && /* @__PURE__ */ jsx7("span", { className: "inline-flex items-center px-1.5 py-0.5 rounded text-[10px] font-medium bg-indigo-900/60 text-indigo-300 animate-pulse", children: "Removing..." })
1703
2014
  ] }),
1704
- /* @__PURE__ */ jsx5("p", { className: "text-slate-400 text-[11px] leading-relaxed", children: "Isolate foreground subject with AI alpha transparency segmentation." }),
1705
- /* @__PURE__ */ jsx5(
2015
+ /* @__PURE__ */ jsx7("p", { className: "text-slate-400 text-[11px] leading-relaxed", children: "Isolate foreground subject with AI alpha transparency segmentation." }),
2016
+ /* @__PURE__ */ jsx7(
1706
2017
  "button",
1707
2018
  {
1708
2019
  type: "button",
1709
2020
  onClick: handleRemoveBackground,
1710
2021
  disabled: isRemovingBg || isInpainting,
1711
2022
  className: "mt-1 px-3 py-2 rounded-lg bg-indigo-600 hover:bg-indigo-500 disabled:opacity-50 text-white font-medium shadow transition-colors flex items-center justify-center gap-2",
1712
- children: isRemovingBg ? /* @__PURE__ */ jsxs5(Fragment, { children: [
1713
- /* @__PURE__ */ jsx5("div", { className: "w-3.5 h-3.5 border-2 border-white/30 border-t-white rounded-full animate-spin" }),
2023
+ children: isRemovingBg ? /* @__PURE__ */ jsxs7(Fragment2, { children: [
2024
+ /* @__PURE__ */ jsx7("div", { className: "w-3.5 h-3.5 border-2 border-white/30 border-t-white rounded-full animate-spin" }),
1714
2025
  "Removing Background..."
1715
- ] }) : /* @__PURE__ */ jsxs5(Fragment, { children: [
1716
- /* @__PURE__ */ jsx5("svg", { className: "w-3.5 h-3.5", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: /* @__PURE__ */ jsx5("path", { d: "M12 2v4M12 18v4M4.93 4.93l2.83 2.83M16.24 16.24l2.83 2.83M2 12h4M18 12h4M4.93 19.07l2.83-2.83M16.24 7.76l2.83-2.83" }) }),
2026
+ ] }) : /* @__PURE__ */ jsxs7(Fragment2, { children: [
2027
+ /* @__PURE__ */ jsx7("svg", { className: "w-3.5 h-3.5", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: /* @__PURE__ */ jsx7("path", { d: "M12 2v4M12 18v4M4.93 4.93l2.83 2.83M16.24 16.24l2.83 2.83M2 12h4M18 12h4M4.93 19.07l2.83-2.83M16.24 7.76l2.83-2.83" }) }),
1717
2028
  "Remove Background"
1718
2029
  ] })
1719
2030
  }
1720
2031
  )
1721
2032
  ] }),
1722
- /* @__PURE__ */ jsxs5("div", { className: "p-3 rounded-lg bg-slate-950/60 border border-slate-800 flex flex-col gap-2.5", children: [
1723
- /* @__PURE__ */ jsxs5("div", { className: "flex items-center justify-between", children: [
1724
- /* @__PURE__ */ jsxs5("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px] flex items-center gap-1.5", children: [
1725
- /* @__PURE__ */ jsxs5("svg", { className: "w-3.5 h-3.5 text-purple-400", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: [
1726
- /* @__PURE__ */ jsx5("path", { d: "m21.64 3.64-1.28-1.28a1.2 1.2 0 0 0-1.7 0l-9.72 9.72-1.94 4.86 4.86-1.94 9.72-9.72a1.2 1.2 0 0 0 .06-1.64z" }),
1727
- /* @__PURE__ */ jsx5("path", { d: "m14 7 3 3" })
2033
+ /* @__PURE__ */ jsxs7("div", { className: "p-3 rounded-lg bg-slate-950/60 border border-slate-800 flex flex-col gap-2.5", children: [
2034
+ /* @__PURE__ */ jsxs7("div", { className: "flex items-center justify-between", children: [
2035
+ /* @__PURE__ */ jsxs7("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px] flex items-center gap-1.5", children: [
2036
+ /* @__PURE__ */ jsxs7("svg", { className: "w-3.5 h-3.5 text-purple-400", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: [
2037
+ /* @__PURE__ */ jsx7("path", { d: "m21.64 3.64-1.28-1.28a1.2 1.2 0 0 0-1.7 0l-9.72 9.72-1.94 4.86 4.86-1.94 9.72-9.72a1.2 1.2 0 0 0 .06-1.64z" }),
2038
+ /* @__PURE__ */ jsx7("path", { d: "m14 7 3 3" })
1728
2039
  ] }),
1729
2040
  "Generative Inpainting"
1730
2041
  ] }),
1731
- isInpainting && /* @__PURE__ */ jsx5("span", { className: "inline-flex items-center px-1.5 py-0.5 rounded text-[10px] font-medium bg-purple-900/60 text-purple-300 animate-pulse", children: "Inpainting..." })
2042
+ isInpainting && /* @__PURE__ */ jsx7("span", { className: "inline-flex items-center px-1.5 py-0.5 rounded text-[10px] font-medium bg-purple-900/60 text-purple-300 animate-pulse", children: "Inpainting..." })
1732
2043
  ] }),
1733
- /* @__PURE__ */ jsx5("p", { className: "text-slate-400 text-[11px] leading-relaxed", children: "Replace, modify, or fill selected regions using prompt-guided generative inpainting." }),
1734
- /* @__PURE__ */ jsxs5("div", { className: "flex flex-col gap-1", children: [
1735
- /* @__PURE__ */ jsx5("label", { htmlFor: "ai-inpaint-prompt-react", className: "text-slate-300 text-[11px] font-medium", children: "Prompt" }),
1736
- /* @__PURE__ */ jsx5(
2044
+ /* @__PURE__ */ jsx7("p", { className: "text-slate-400 text-[11px] leading-relaxed", children: "Replace, modify, or fill selected regions using prompt-guided generative inpainting." }),
2045
+ /* @__PURE__ */ jsxs7("div", { className: "flex flex-col gap-1", children: [
2046
+ /* @__PURE__ */ jsx7("label", { htmlFor: "ai-inpaint-prompt-react", className: "text-slate-300 text-[11px] font-medium", children: "Prompt" }),
2047
+ /* @__PURE__ */ jsx7(
1737
2048
  "textarea",
1738
2049
  {
1739
2050
  id: "ai-inpaint-prompt-react",
@@ -1745,10 +2056,10 @@ var ImageEditor = ({
1745
2056
  }
1746
2057
  )
1747
2058
  ] }),
1748
- /* @__PURE__ */ jsxs5("div", { className: "flex flex-col gap-1", children: [
1749
- /* @__PURE__ */ jsx5("span", { className: "text-slate-300 text-[11px] font-medium", children: "Target Mask Region" }),
1750
- /* @__PURE__ */ jsxs5("div", { className: "grid grid-cols-2 gap-1.5", children: [
1751
- /* @__PURE__ */ jsxs5(
2059
+ /* @__PURE__ */ jsxs7("div", { className: "flex flex-col gap-1", children: [
2060
+ /* @__PURE__ */ jsx7("span", { className: "text-slate-300 text-[11px] font-medium", children: "Target Mask Region" }),
2061
+ /* @__PURE__ */ jsxs7("div", { className: "grid grid-cols-2 gap-1.5", children: [
2062
+ /* @__PURE__ */ jsxs7(
1752
2063
  "button",
1753
2064
  {
1754
2065
  type: "button",
@@ -1761,7 +2072,7 @@ var ImageEditor = ({
1761
2072
  ]
1762
2073
  }
1763
2074
  ),
1764
- /* @__PURE__ */ jsxs5(
2075
+ /* @__PURE__ */ jsxs7(
1765
2076
  "button",
1766
2077
  {
1767
2078
  type: "button",
@@ -1776,25 +2087,25 @@ var ImageEditor = ({
1776
2087
  )
1777
2088
  ] })
1778
2089
  ] }),
1779
- /* @__PURE__ */ jsx5(
2090
+ /* @__PURE__ */ jsx7(
1780
2091
  "button",
1781
2092
  {
1782
2093
  type: "button",
1783
2094
  onClick: handleInpaint,
1784
2095
  disabled: isInpainting || isRemovingBg || !inpaintPrompt.trim(),
1785
2096
  className: "mt-1 px-3 py-2 rounded-lg bg-purple-600 hover:bg-purple-500 disabled:opacity-50 text-white font-medium shadow transition-colors flex items-center justify-center gap-2",
1786
- children: isInpainting ? /* @__PURE__ */ jsxs5(Fragment, { children: [
1787
- /* @__PURE__ */ jsx5("div", { className: "w-3.5 h-3.5 border-2 border-white/30 border-t-white rounded-full animate-spin" }),
2097
+ children: isInpainting ? /* @__PURE__ */ jsxs7(Fragment2, { children: [
2098
+ /* @__PURE__ */ jsx7("div", { className: "w-3.5 h-3.5 border-2 border-white/30 border-t-white rounded-full animate-spin" }),
1788
2099
  "Generating Inpaint..."
1789
- ] }) : /* @__PURE__ */ jsxs5(Fragment, { children: [
1790
- /* @__PURE__ */ jsx5("svg", { className: "w-3.5 h-3.5", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: /* @__PURE__ */ jsx5("path", { d: "M12 2v4M12 18v4M4.93 4.93l2.83 2.83M16.24 16.24l2.83 2.83M2 12h4M18 12h4M4.93 19.07l2.83-2.83M16.24 7.76l2.83-2.83" }) }),
2100
+ ] }) : /* @__PURE__ */ jsxs7(Fragment2, { children: [
2101
+ /* @__PURE__ */ jsx7("svg", { className: "w-3.5 h-3.5", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: /* @__PURE__ */ jsx7("path", { d: "M12 2v4M12 18v4M4.93 4.93l2.83 2.83M16.24 16.24l2.83 2.83M2 12h4M18 12h4M4.93 19.07l2.83-2.83M16.24 7.76l2.83-2.83" }) }),
1791
2102
  "Apply Inpainting"
1792
2103
  ] })
1793
2104
  }
1794
2105
  )
1795
2106
  ] }),
1796
- aiError && /* @__PURE__ */ jsx5("div", { className: "p-2.5 rounded-lg bg-rose-950/60 border border-rose-800 text-rose-300 text-[11px]", children: aiError }),
1797
- aiSuccess && /* @__PURE__ */ jsx5("div", { className: "p-2.5 rounded-lg bg-emerald-950/60 border border-emerald-800 text-emerald-300 text-[11px]", children: aiSuccess })
2107
+ aiError && /* @__PURE__ */ jsx7("div", { className: "p-2.5 rounded-lg bg-rose-950/60 border border-rose-800 text-rose-300 text-[11px]", children: aiError }),
2108
+ aiSuccess && /* @__PURE__ */ jsx7("div", { className: "p-2.5 rounded-lg bg-emerald-950/60 border border-emerald-800 text-emerald-300 text-[11px]", children: aiSuccess })
1798
2109
  ] })
1799
2110
  ] })
1800
2111
  ] })
@@ -1810,6 +2121,8 @@ export {
1810
2121
  useImageHistogram,
1811
2122
  CurvesEditor,
1812
2123
  AdjustmentLayersPanel,
2124
+ SelectionOptionsBar,
2125
+ RefineEdgePanel,
1813
2126
  ImageEditor
1814
2127
  };
1815
- //# sourceMappingURL=chunk-XTFR3IMK.js.map
2128
+ //# sourceMappingURL=chunk-ZU54BMDC.js.map