@pixerate/editor-react 0.71.0 → 0.73.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/{chunk-63FQB5BT.js → chunk-VNZKHFEM.js} +525 -382
- package/dist/chunk-VNZKHFEM.js.map +1 -0
- package/dist/image-editor/index.cjs +575 -444
- package/dist/image-editor/index.cjs.map +1 -1
- package/dist/image-editor/index.d.cts +15 -1
- package/dist/image-editor/index.d.ts +15 -1
- package/dist/image-editor/index.js +3 -1
- package/dist/index.cjs +1004 -873
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +3 -1
- package/dist/index.js.map +1 -1
- package/dist/vector/index.cjs +910 -175
- package/dist/vector/index.cjs.map +1 -1
- package/dist/vector/index.d.cts +67 -3
- package/dist/vector/index.d.ts +67 -3
- package/dist/vector/index.js +915 -164
- package/dist/vector/index.js.map +1 -1
- package/package.json +3 -3
- package/dist/chunk-63FQB5BT.js.map +0 -1
|
@@ -159,7 +159,7 @@ function useImageEditor(options = {}) {
|
|
|
159
159
|
}
|
|
160
160
|
|
|
161
161
|
// src/image-editor/ImageEditor.tsx
|
|
162
|
-
import
|
|
162
|
+
import React13, { useRef as useRef5, useEffect as useEffect11, useState as useState14, useCallback as useCallback2 } from "react";
|
|
163
163
|
import {
|
|
164
164
|
canvasToImagePoint,
|
|
165
165
|
hitTestCrop,
|
|
@@ -823,6 +823,7 @@ var LayerEffectsPanel = ({ controller, layerId, className }) => {
|
|
|
823
823
|
|
|
824
824
|
// src/image-editor/LayersPanel.tsx
|
|
825
825
|
import {
|
|
826
|
+
BIT_DEPTH_OPTIONS,
|
|
826
827
|
BLEND_MODES as BLEND_MODES2,
|
|
827
828
|
PSD_FILE_ACCEPT,
|
|
828
829
|
downloadPsd,
|
|
@@ -949,6 +950,17 @@ var LayersPanel = ({ controller, thumbnailSize = 32, psd = true, psdFileName = "
|
|
|
949
950
|
children: "\u22EF"
|
|
950
951
|
}
|
|
951
952
|
),
|
|
953
|
+
/* @__PURE__ */ jsx6(
|
|
954
|
+
"select",
|
|
955
|
+
{
|
|
956
|
+
"aria-label": "Bits per channel",
|
|
957
|
+
title: "Image \u203A Mode: bits per channel",
|
|
958
|
+
className: "rounded bg-slate-800 px-1 py-0.5 text-[11px] text-slate-200",
|
|
959
|
+
value: controller.bitDepth,
|
|
960
|
+
onChange: (e) => attempt(() => controller.setBitDepth(Number(e.target.value))),
|
|
961
|
+
children: BIT_DEPTH_OPTIONS.map((o) => /* @__PURE__ */ jsx6("option", { value: o.depth, title: o.title, children: o.label }, o.depth))
|
|
962
|
+
}
|
|
963
|
+
),
|
|
952
964
|
psd && /* @__PURE__ */ jsxs6(Fragment, { children: [
|
|
953
965
|
/* @__PURE__ */ jsx6("button", { type: "button", className: iconButton, onClick: () => fileInput.current?.click(), children: "Open PSD\u2026" }),
|
|
954
966
|
/* @__PURE__ */ jsx6("button", { type: "button", className: iconButton, onClick: () => psdTask(async () => (await downloadPsd(controller, psdFileName)).warnings), children: "Export PSD" }),
|
|
@@ -1254,7 +1266,19 @@ var LayersPanel = ({ controller, thumbnailSize = 32, psd = true, psdFileName = "
|
|
|
1254
1266
|
|
|
1255
1267
|
// src/image-editor/BrushOptionsBar.tsx
|
|
1256
1268
|
import { useEffect as useEffect6, useState as useState7 } from "react";
|
|
1257
|
-
import {
|
|
1269
|
+
import {
|
|
1270
|
+
BRUSH_OPTION_CONTROLS,
|
|
1271
|
+
MIXER_MIXING_OPTIONS,
|
|
1272
|
+
MIXER_OPTION_CONTROLS,
|
|
1273
|
+
PAINT_TOOLS,
|
|
1274
|
+
RETOUCH_CHOICES,
|
|
1275
|
+
RETOUCH_OPTION_CONTROLS,
|
|
1276
|
+
RETOUCH_TOGGLES,
|
|
1277
|
+
cloneSourceLabel,
|
|
1278
|
+
isRetouchPaintTool,
|
|
1279
|
+
rgbUnitToHex,
|
|
1280
|
+
setRetouchChoice
|
|
1281
|
+
} from "@pixerate/editor/image-editor";
|
|
1258
1282
|
import { jsx as jsx7, jsxs as jsxs7 } from "react/jsx-runtime";
|
|
1259
1283
|
var chip = (on) => `px-2 py-1 rounded text-[11px] ${on ? "bg-indigo-600 text-white" : "bg-slate-800 text-slate-300 hover:text-white"}`;
|
|
1260
1284
|
var BrushOptionsBar = ({ controller, className }) => {
|
|
@@ -1262,7 +1286,8 @@ var BrushOptionsBar = ({ controller, className }) => {
|
|
|
1262
1286
|
useEffect6(() => controller.subscribe(() => setTick((n) => n + 1)), [controller]);
|
|
1263
1287
|
const [error, setError] = useState7(null);
|
|
1264
1288
|
const state = controller.getState();
|
|
1265
|
-
const { brush, foreground, background, mixer, mixerLoad } = state.paint;
|
|
1289
|
+
const { brush, foreground, background, mixer, mixerLoad, retouch, cloneSource } = state.paint;
|
|
1290
|
+
const tool = state.activeTool;
|
|
1266
1291
|
const attempt = (fn) => {
|
|
1267
1292
|
try {
|
|
1268
1293
|
setError(null);
|
|
@@ -1272,12 +1297,12 @@ var BrushOptionsBar = ({ controller, className }) => {
|
|
|
1272
1297
|
}
|
|
1273
1298
|
};
|
|
1274
1299
|
return /* @__PURE__ */ jsxs7("div", { className: `flex flex-col gap-2 text-xs text-slate-200 ${className ?? ""}`, "data-testid": "brush-options", children: [
|
|
1275
|
-
/* @__PURE__ */ jsx7("div", { className: "flex gap-1", role: "toolbar", "aria-label": "Paint tools", children: PAINT_TOOLS.map((t) => /* @__PURE__ */ jsx7(
|
|
1300
|
+
/* @__PURE__ */ jsx7("div", { className: "flex flex-wrap gap-1", role: "toolbar", "aria-label": "Paint tools", children: PAINT_TOOLS.map((t) => /* @__PURE__ */ jsx7(
|
|
1276
1301
|
"button",
|
|
1277
1302
|
{
|
|
1278
1303
|
type: "button",
|
|
1279
1304
|
"aria-pressed": state.activeTool === t.id,
|
|
1280
|
-
title: `${t.label} (${t.shortcut})
|
|
1305
|
+
title: t.shortcut ? `${t.label} (${t.shortcut})` : t.label,
|
|
1281
1306
|
className: chip(state.activeTool === t.id),
|
|
1282
1307
|
onClick: () => controller.setTool(t.id),
|
|
1283
1308
|
children: t.label
|
|
@@ -1379,6 +1404,41 @@ var BrushOptionsBar = ({ controller, className }) => {
|
|
|
1379
1404
|
] })
|
|
1380
1405
|
] })
|
|
1381
1406
|
] }),
|
|
1407
|
+
isRetouchPaintTool(tool) && /* @__PURE__ */ jsxs7("div", { className: "flex flex-col gap-2 border-t border-slate-800 pt-2", role: "group", "aria-label": "Retouch options", "data-testid": "retouch-options", children: [
|
|
1408
|
+
(tool === "clone" || tool === "heal") && /* @__PURE__ */ jsxs7("div", { className: "flex items-center gap-2", children: [
|
|
1409
|
+
/* @__PURE__ */ jsx7("span", { className: "text-slate-400", "data-testid": "clone-source", children: cloneSourceLabel(controller) }),
|
|
1410
|
+
cloneSource && /* @__PURE__ */ jsx7("button", { type: "button", title: "Forget the source point", className: chip(false), onClick: () => controller.setCloneSource(null), children: "Clear source" })
|
|
1411
|
+
] }),
|
|
1412
|
+
RETOUCH_CHOICES.filter((c) => c.tools.includes(tool)).map((choice) => /* @__PURE__ */ jsxs7("div", { className: "flex flex-wrap items-center gap-1", role: "group", "aria-label": choice.label, children: [
|
|
1413
|
+
/* @__PURE__ */ jsx7("span", { className: "text-slate-400", children: choice.label }),
|
|
1414
|
+
choice.options.map((o) => /* @__PURE__ */ jsx7(
|
|
1415
|
+
"button",
|
|
1416
|
+
{
|
|
1417
|
+
type: "button",
|
|
1418
|
+
"aria-pressed": retouch[choice.id] === o.id,
|
|
1419
|
+
title: o.title,
|
|
1420
|
+
className: chip(retouch[choice.id] === o.id),
|
|
1421
|
+
onClick: () => setRetouchChoice(controller, choice.id, o.id),
|
|
1422
|
+
children: o.label
|
|
1423
|
+
},
|
|
1424
|
+
o.id
|
|
1425
|
+
))
|
|
1426
|
+
] }, choice.id)),
|
|
1427
|
+
RETOUCH_OPTION_CONTROLS.filter((c) => c.tools.includes(tool)).map((spec) => /* @__PURE__ */ jsx7(ControlSlider, { spec, value: retouch[spec.id], onChange: (v) => controller.setPaintOptions({ retouch: { [spec.id]: v } }) }, spec.id)),
|
|
1428
|
+
/* @__PURE__ */ jsx7("div", { className: "flex flex-wrap gap-3 text-slate-300", children: RETOUCH_TOGGLES.filter((t) => t.tools.includes(tool)).map((t) => /* @__PURE__ */ jsxs7("label", { className: "flex items-center gap-1.5", children: [
|
|
1429
|
+
/* @__PURE__ */ jsx7(
|
|
1430
|
+
"input",
|
|
1431
|
+
{
|
|
1432
|
+
type: "checkbox",
|
|
1433
|
+
"aria-label": t.label,
|
|
1434
|
+
checked: retouch[t.id],
|
|
1435
|
+
onChange: (e) => controller.setPaintOptions({ retouch: { [t.id]: e.target.checked } }),
|
|
1436
|
+
className: "accent-indigo-500"
|
|
1437
|
+
}
|
|
1438
|
+
),
|
|
1439
|
+
t.label
|
|
1440
|
+
] }, t.id)) })
|
|
1441
|
+
] }),
|
|
1382
1442
|
/* @__PURE__ */ jsxs7("div", { className: "flex flex-wrap gap-3 text-slate-300", role: "group", "aria-label": "Pressure", children: [
|
|
1383
1443
|
/* @__PURE__ */ jsxs7("label", { className: "flex items-center gap-1.5", children: [
|
|
1384
1444
|
/* @__PURE__ */ jsx7(
|
|
@@ -1415,15 +1475,95 @@ var BrushOptionsBar = ({ controller, className }) => {
|
|
|
1415
1475
|
] });
|
|
1416
1476
|
};
|
|
1417
1477
|
|
|
1478
|
+
// src/image-editor/ColorProfilePanel.tsx
|
|
1479
|
+
import { useEffect as useEffect7, useState as useState8 } from "react";
|
|
1480
|
+
import { INTENT_OPTIONS, PROOF_PROFILE_OPTIONS, WORKING_SPACE_OPTIONS, colorPanelView } from "@pixerate/editor/image-editor";
|
|
1481
|
+
import { Fragment as Fragment2, jsx as jsx8, jsxs as jsxs8 } from "react/jsx-runtime";
|
|
1482
|
+
var chip2 = "px-2 py-1 rounded text-[11px] bg-slate-800 text-slate-300 hover:text-white";
|
|
1483
|
+
var select = "rounded bg-slate-800 px-1 py-0.5 text-[11px] text-slate-200";
|
|
1484
|
+
var ColorProfilePanel = ({ controller, className }) => {
|
|
1485
|
+
const [, setTick] = useState8(0);
|
|
1486
|
+
useEffect7(() => controller.subscribe(() => setTick((n) => n + 1)), [controller]);
|
|
1487
|
+
const [target, setTarget] = useState8("display-p3");
|
|
1488
|
+
const [intent, setIntent] = useState8("relative");
|
|
1489
|
+
const [bpc, setBpc] = useState8(true);
|
|
1490
|
+
const [error, setError] = useState8(null);
|
|
1491
|
+
const view = colorPanelView(controller);
|
|
1492
|
+
const attempt = (fn) => {
|
|
1493
|
+
try {
|
|
1494
|
+
setError(null);
|
|
1495
|
+
fn();
|
|
1496
|
+
} catch (err) {
|
|
1497
|
+
setError(err instanceof Error ? err.message : String(err));
|
|
1498
|
+
}
|
|
1499
|
+
};
|
|
1500
|
+
const proofWith = (patch) => {
|
|
1501
|
+
const cur = view.proof;
|
|
1502
|
+
const id = patch.id ?? cur?.id ?? "coated-cmyk";
|
|
1503
|
+
attempt(
|
|
1504
|
+
() => controller.setProofSetup({
|
|
1505
|
+
profile: id,
|
|
1506
|
+
intent: patch.intent ?? cur?.intent ?? "relative",
|
|
1507
|
+
simulatePaper: patch.simulatePaper ?? cur?.simulatePaper ?? false,
|
|
1508
|
+
gamutWarning: patch.gamutWarning ?? cur?.gamutWarning ?? false
|
|
1509
|
+
})
|
|
1510
|
+
);
|
|
1511
|
+
};
|
|
1512
|
+
return /* @__PURE__ */ jsxs8("div", { className: `flex flex-col gap-2 text-xs text-slate-200 ${className ?? ""}`, "data-testid": "color-profile-panel", children: [
|
|
1513
|
+
/* @__PURE__ */ jsxs8("div", { className: "flex items-center gap-2", children: [
|
|
1514
|
+
/* @__PURE__ */ jsx8("span", { className: "text-slate-400", children: "Profile" }),
|
|
1515
|
+
/* @__PURE__ */ jsx8("span", { "data-testid": "color-profile-name", children: view.profileName })
|
|
1516
|
+
] }),
|
|
1517
|
+
/* @__PURE__ */ jsxs8("div", { className: "flex flex-wrap items-center gap-1", role: "group", "aria-label": "Assign or convert", children: [
|
|
1518
|
+
/* @__PURE__ */ jsx8("select", { "aria-label": "Target profile", className: select, value: target, onChange: (e) => setTarget(e.target.value), children: WORKING_SPACE_OPTIONS.map((o) => /* @__PURE__ */ jsx8("option", { value: o.id, children: o.label }, o.id)) }),
|
|
1519
|
+
/* @__PURE__ */ jsx8("select", { "aria-label": "Rendering intent", className: select, value: intent, onChange: (e) => setIntent(e.target.value), children: INTENT_OPTIONS.map((o) => /* @__PURE__ */ jsx8("option", { value: o.id, title: o.title, children: o.label }, o.id)) }),
|
|
1520
|
+
/* @__PURE__ */ jsxs8("label", { className: "flex items-center gap-1", children: [
|
|
1521
|
+
/* @__PURE__ */ jsx8("input", { type: "checkbox", "aria-label": "Black point compensation", checked: bpc, onChange: (e) => setBpc(e.target.checked), className: "accent-indigo-500" }),
|
|
1522
|
+
"BPC"
|
|
1523
|
+
] }),
|
|
1524
|
+
/* @__PURE__ */ jsx8("button", { type: "button", className: chip2, title: "Edit \u203A Assign Profile: keep the numbers", onClick: () => attempt(() => controller.assignProfile(target)), children: "Assign" }),
|
|
1525
|
+
/* @__PURE__ */ jsx8("button", { type: "button", className: chip2, title: "Edit \u203A Convert to Profile: keep the look", onClick: () => attempt(() => controller.convertToProfile(target, { intent, bpc })), children: "Convert" })
|
|
1526
|
+
] }),
|
|
1527
|
+
/* @__PURE__ */ jsxs8("div", { className: "flex flex-wrap items-center gap-1", role: "group", "aria-label": "Proof setup", children: [
|
|
1528
|
+
/* @__PURE__ */ jsx8("span", { className: "text-slate-400", children: "Proof" }),
|
|
1529
|
+
/* @__PURE__ */ jsxs8(
|
|
1530
|
+
"select",
|
|
1531
|
+
{
|
|
1532
|
+
"aria-label": "Proof profile",
|
|
1533
|
+
className: select,
|
|
1534
|
+
value: view.proof?.id ?? "",
|
|
1535
|
+
onChange: (e) => e.target.value ? proofWith({ id: e.target.value }) : attempt(() => controller.setProofSetup(null)),
|
|
1536
|
+
children: [
|
|
1537
|
+
/* @__PURE__ */ jsx8("option", { value: "", children: "Off" }),
|
|
1538
|
+
PROOF_PROFILE_OPTIONS.map((o) => /* @__PURE__ */ jsx8("option", { value: o.id, children: o.label }, o.id))
|
|
1539
|
+
]
|
|
1540
|
+
}
|
|
1541
|
+
),
|
|
1542
|
+
view.proof && /* @__PURE__ */ jsxs8(Fragment2, { children: [
|
|
1543
|
+
/* @__PURE__ */ jsx8("select", { "aria-label": "Proof intent", className: select, value: view.proof.intent, onChange: (e) => proofWith({ intent: e.target.value }), children: INTENT_OPTIONS.map((o) => /* @__PURE__ */ jsx8("option", { value: o.id, children: o.label }, o.id)) }),
|
|
1544
|
+
/* @__PURE__ */ jsxs8("label", { className: "flex items-center gap-1", children: [
|
|
1545
|
+
/* @__PURE__ */ jsx8("input", { type: "checkbox", "aria-label": "Simulate paper colour", checked: view.proof.simulatePaper, onChange: (e) => proofWith({ simulatePaper: e.target.checked }), className: "accent-indigo-500" }),
|
|
1546
|
+
"Paper"
|
|
1547
|
+
] }),
|
|
1548
|
+
/* @__PURE__ */ jsxs8("label", { className: "flex items-center gap-1", children: [
|
|
1549
|
+
/* @__PURE__ */ jsx8("input", { type: "checkbox", "aria-label": "Gamut warning", checked: view.proof.gamutWarning, onChange: (e) => proofWith({ gamutWarning: e.target.checked }), className: "accent-indigo-500" }),
|
|
1550
|
+
"Gamut warning"
|
|
1551
|
+
] })
|
|
1552
|
+
] })
|
|
1553
|
+
] }),
|
|
1554
|
+
error && /* @__PURE__ */ jsx8("p", { role: "alert", className: "text-rose-400", children: error })
|
|
1555
|
+
] });
|
|
1556
|
+
};
|
|
1557
|
+
|
|
1418
1558
|
// src/image-editor/SelectionOptionsBar.tsx
|
|
1419
|
-
import { useState as
|
|
1559
|
+
import { useState as useState9 } from "react";
|
|
1420
1560
|
import {
|
|
1421
1561
|
SELECTION_MODES,
|
|
1422
1562
|
SELECTION_MODE_LABELS,
|
|
1423
1563
|
SELECTION_TOOLS,
|
|
1424
1564
|
describeSelection
|
|
1425
1565
|
} from "@pixerate/editor/image-editor";
|
|
1426
|
-
import { jsx as
|
|
1566
|
+
import { jsx as jsx9, jsxs as jsxs9 } from "react/jsx-runtime";
|
|
1427
1567
|
var MODIFY_OPS = [
|
|
1428
1568
|
{ op: "grow", label: "Grow" },
|
|
1429
1569
|
{ op: "shrink", label: "Shrink" },
|
|
@@ -1440,20 +1580,20 @@ var SelectionOptionsBar = ({
|
|
|
1440
1580
|
quickMask,
|
|
1441
1581
|
className = ""
|
|
1442
1582
|
}) => {
|
|
1443
|
-
const [radius, setRadius] =
|
|
1583
|
+
const [radius, setRadius] = useState9(2);
|
|
1444
1584
|
const set = (patch) => onOptionsChange({ ...options, ...patch });
|
|
1445
1585
|
const sel = selection === void 0 ? controller.getSelection() : selection;
|
|
1446
1586
|
const qm = quickMask ?? Boolean(controller.getState().quickMask);
|
|
1447
|
-
return /* @__PURE__ */
|
|
1448
|
-
/* @__PURE__ */
|
|
1449
|
-
/* @__PURE__ */
|
|
1450
|
-
options.tool === "wand" && /* @__PURE__ */
|
|
1451
|
-
/* @__PURE__ */
|
|
1452
|
-
/* @__PURE__ */
|
|
1453
|
-
/* @__PURE__ */
|
|
1454
|
-
/* @__PURE__ */
|
|
1587
|
+
return /* @__PURE__ */ jsxs9("div", { "data-testid": "selection-options-bar", className: `flex flex-col gap-3 text-xs ${className}`, children: [
|
|
1588
|
+
/* @__PURE__ */ jsx9("div", { role: "group", "aria-label": "Selection tool", className: "flex flex-wrap gap-1", children: SELECTION_TOOLS.map((t) => /* @__PURE__ */ jsx9("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)) }),
|
|
1589
|
+
/* @__PURE__ */ jsx9("div", { role: "group", "aria-label": "Selection mode", className: "flex flex-wrap gap-1", children: SELECTION_MODES.map((m) => /* @__PURE__ */ jsx9("button", { type: "button", "aria-pressed": options.mode === m, className: btn(options.mode === m), onClick: () => set({ mode: m }), children: SELECTION_MODE_LABELS[m] }, m)) }),
|
|
1590
|
+
options.tool === "wand" && /* @__PURE__ */ jsxs9("div", { className: "flex flex-col gap-2", children: [
|
|
1591
|
+
/* @__PURE__ */ jsxs9("label", { className: "flex flex-col gap-1", children: [
|
|
1592
|
+
/* @__PURE__ */ jsxs9("span", { className: "flex justify-between text-slate-400", children: [
|
|
1593
|
+
/* @__PURE__ */ jsx9("span", { children: "Tolerance" }),
|
|
1594
|
+
/* @__PURE__ */ jsx9("span", { className: "font-mono", children: options.tolerance })
|
|
1455
1595
|
] }),
|
|
1456
|
-
/* @__PURE__ */
|
|
1596
|
+
/* @__PURE__ */ jsx9(
|
|
1457
1597
|
"input",
|
|
1458
1598
|
{
|
|
1459
1599
|
type: "range",
|
|
@@ -1467,17 +1607,17 @@ var SelectionOptionsBar = ({
|
|
|
1467
1607
|
}
|
|
1468
1608
|
)
|
|
1469
1609
|
] }),
|
|
1470
|
-
/* @__PURE__ */
|
|
1471
|
-
/* @__PURE__ */
|
|
1610
|
+
/* @__PURE__ */ jsxs9("label", { className: "flex items-center gap-2 text-slate-300", children: [
|
|
1611
|
+
/* @__PURE__ */ jsx9("input", { type: "checkbox", checked: options.contiguous, onChange: (e) => set({ contiguous: e.target.checked }) }),
|
|
1472
1612
|
"Contiguous"
|
|
1473
1613
|
] }),
|
|
1474
|
-
/* @__PURE__ */
|
|
1475
|
-
/* @__PURE__ */
|
|
1614
|
+
/* @__PURE__ */ jsxs9("label", { className: "flex items-center gap-2 text-slate-300", children: [
|
|
1615
|
+
/* @__PURE__ */ jsx9("input", { type: "checkbox", checked: options.sampleMerged, onChange: (e) => set({ sampleMerged: e.target.checked }) }),
|
|
1476
1616
|
"Sample adjusted image"
|
|
1477
1617
|
] }),
|
|
1478
|
-
/* @__PURE__ */
|
|
1618
|
+
/* @__PURE__ */ jsxs9("label", { className: "flex items-center gap-2 text-slate-300", children: [
|
|
1479
1619
|
"Sample",
|
|
1480
|
-
/* @__PURE__ */
|
|
1620
|
+
/* @__PURE__ */ jsxs9(
|
|
1481
1621
|
"select",
|
|
1482
1622
|
{
|
|
1483
1623
|
"aria-label": "Sample from",
|
|
@@ -1485,27 +1625,27 @@ var SelectionOptionsBar = ({
|
|
|
1485
1625
|
onChange: (e) => set({ sample: e.target.value }),
|
|
1486
1626
|
className: "bg-slate-800 border border-slate-700 rounded px-1 py-0.5",
|
|
1487
1627
|
children: [
|
|
1488
|
-
/* @__PURE__ */
|
|
1489
|
-
/* @__PURE__ */
|
|
1628
|
+
/* @__PURE__ */ jsx9("option", { value: "composite", children: "All layers" }),
|
|
1629
|
+
/* @__PURE__ */ jsx9("option", { value: "active-layer", children: "Active layer" })
|
|
1490
1630
|
]
|
|
1491
1631
|
}
|
|
1492
1632
|
)
|
|
1493
1633
|
] })
|
|
1494
1634
|
] }),
|
|
1495
|
-
/* @__PURE__ */
|
|
1496
|
-
/* @__PURE__ */
|
|
1635
|
+
/* @__PURE__ */ jsxs9("label", { className: "flex items-center gap-2 text-slate-300", children: [
|
|
1636
|
+
/* @__PURE__ */ jsx9("input", { type: "checkbox", checked: options.antiAlias, onChange: (e) => set({ antiAlias: e.target.checked }) }),
|
|
1497
1637
|
"Anti-alias"
|
|
1498
1638
|
] }),
|
|
1499
|
-
/* @__PURE__ */
|
|
1500
|
-
/* @__PURE__ */
|
|
1501
|
-
/* @__PURE__ */
|
|
1502
|
-
/* @__PURE__ */
|
|
1503
|
-
/* @__PURE__ */
|
|
1639
|
+
/* @__PURE__ */ jsxs9("div", { className: "flex flex-wrap gap-1", children: [
|
|
1640
|
+
/* @__PURE__ */ jsx9("button", { type: "button", className: btn(false), onClick: () => controller.selectAll(), children: "Select All" }),
|
|
1641
|
+
/* @__PURE__ */ jsx9("button", { type: "button", className: btn(false), disabled: !sel, onClick: () => controller.deselect(), children: "Deselect" }),
|
|
1642
|
+
/* @__PURE__ */ jsx9("button", { type: "button", className: btn(false), onClick: () => controller.invertSelection(), children: "Inverse" }),
|
|
1643
|
+
/* @__PURE__ */ jsx9("button", { type: "button", "aria-pressed": qm, className: btn(qm), onClick: () => controller.setQuickMask(!qm), children: "Quick Mask" })
|
|
1504
1644
|
] }),
|
|
1505
|
-
/* @__PURE__ */
|
|
1506
|
-
/* @__PURE__ */
|
|
1645
|
+
/* @__PURE__ */ jsxs9("div", { className: "flex flex-wrap items-center gap-1", children: [
|
|
1646
|
+
/* @__PURE__ */ jsxs9("label", { className: "flex items-center gap-1 text-slate-400", children: [
|
|
1507
1647
|
"Radius",
|
|
1508
|
-
/* @__PURE__ */
|
|
1648
|
+
/* @__PURE__ */ jsx9(
|
|
1509
1649
|
"input",
|
|
1510
1650
|
{
|
|
1511
1651
|
type: "number",
|
|
@@ -1519,29 +1659,29 @@ var SelectionOptionsBar = ({
|
|
|
1519
1659
|
}
|
|
1520
1660
|
)
|
|
1521
1661
|
] }),
|
|
1522
|
-
MODIFY_OPS.map(({ op, label }) => /* @__PURE__ */
|
|
1662
|
+
MODIFY_OPS.map(({ op, label }) => /* @__PURE__ */ jsx9("button", { type: "button", className: btn(false), disabled: !sel, onClick: () => controller.modifySelection(op, radius), children: label }, op))
|
|
1523
1663
|
] }),
|
|
1524
|
-
/* @__PURE__ */
|
|
1664
|
+
/* @__PURE__ */ jsx9("p", { "data-testid": "selection-status", className: "text-slate-400", children: describeSelection(sel) })
|
|
1525
1665
|
] });
|
|
1526
1666
|
};
|
|
1527
1667
|
|
|
1528
1668
|
// src/image-editor/RefineEdgePanel.tsx
|
|
1529
|
-
import { useState as
|
|
1669
|
+
import { useState as useState10 } from "react";
|
|
1530
1670
|
import {
|
|
1531
1671
|
ADJUSTMENT_KINDS as ADJUSTMENT_KINDS2,
|
|
1532
1672
|
REFINE_EDGE_CONTROLS,
|
|
1533
1673
|
adjustmentKindLabel as adjustmentKindLabel2,
|
|
1534
1674
|
layerMaskFromSelection
|
|
1535
1675
|
} from "@pixerate/editor/image-editor";
|
|
1536
|
-
import { Fragment as
|
|
1676
|
+
import { Fragment as Fragment3, jsx as jsx10, jsxs as jsxs10 } from "react/jsx-runtime";
|
|
1537
1677
|
var DEFAULT_PARAMS = { radius: 8, smartRadius: false, smooth: 0, feather: 0, contrast: 0, shiftEdge: 0 };
|
|
1538
1678
|
var button2 = "px-2 py-1 rounded-md border border-slate-800 bg-slate-950 text-[11px] text-slate-200 hover:text-white disabled:opacity-40";
|
|
1539
1679
|
var RefineEdgePanel = ({ controller, selection, layers, className = "" }) => {
|
|
1540
|
-
const [params, setParams] =
|
|
1541
|
-
const [busy, setBusy] =
|
|
1542
|
-
const [error, setError] =
|
|
1543
|
-
const [layerId, setLayerId] =
|
|
1544
|
-
const [newKind, setNewKind] =
|
|
1680
|
+
const [params, setParams] = useState10(DEFAULT_PARAMS);
|
|
1681
|
+
const [busy, setBusy] = useState10(false);
|
|
1682
|
+
const [error, setError] = useState10(null);
|
|
1683
|
+
const [layerId, setLayerId] = useState10("");
|
|
1684
|
+
const [newKind, setNewKind] = useState10("hueSaturation");
|
|
1545
1685
|
const sel = selection === void 0 ? controller.getSelection() : selection;
|
|
1546
1686
|
const list = layers ?? controller.getAdjustmentLayers();
|
|
1547
1687
|
const target = list.find((l) => l.id === layerId) ?? list[list.length - 1];
|
|
@@ -1556,17 +1696,17 @@ var RefineEdgePanel = ({ controller, selection, layers, className = "" }) => {
|
|
|
1556
1696
|
setBusy(false);
|
|
1557
1697
|
}
|
|
1558
1698
|
};
|
|
1559
|
-
return /* @__PURE__ */
|
|
1560
|
-
/* @__PURE__ */
|
|
1561
|
-
REFINE_EDGE_CONTROLS.map((c) => /* @__PURE__ */
|
|
1562
|
-
/* @__PURE__ */
|
|
1563
|
-
/* @__PURE__ */
|
|
1564
|
-
/* @__PURE__ */
|
|
1699
|
+
return /* @__PURE__ */ jsxs10("div", { "data-testid": "refine-edge-panel", className: `flex flex-col gap-3 text-xs ${className}`, children: [
|
|
1700
|
+
/* @__PURE__ */ jsx10("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Refine Edge" }),
|
|
1701
|
+
REFINE_EDGE_CONTROLS.map((c) => /* @__PURE__ */ jsxs10("label", { className: "flex flex-col gap-1", children: [
|
|
1702
|
+
/* @__PURE__ */ jsxs10("span", { className: "flex justify-between text-slate-400", children: [
|
|
1703
|
+
/* @__PURE__ */ jsx10("span", { children: c.label }),
|
|
1704
|
+
/* @__PURE__ */ jsxs10("span", { className: "font-mono", children: [
|
|
1565
1705
|
params[c.id],
|
|
1566
1706
|
c.unit
|
|
1567
1707
|
] })
|
|
1568
1708
|
] }),
|
|
1569
|
-
/* @__PURE__ */
|
|
1709
|
+
/* @__PURE__ */ jsx10(
|
|
1570
1710
|
"input",
|
|
1571
1711
|
{
|
|
1572
1712
|
type: "range",
|
|
@@ -1580,28 +1720,28 @@ var RefineEdgePanel = ({ controller, selection, layers, className = "" }) => {
|
|
|
1580
1720
|
}
|
|
1581
1721
|
)
|
|
1582
1722
|
] }, c.id)),
|
|
1583
|
-
/* @__PURE__ */
|
|
1584
|
-
/* @__PURE__ */
|
|
1723
|
+
/* @__PURE__ */ jsxs10("label", { className: "flex items-center gap-2 text-slate-300", children: [
|
|
1724
|
+
/* @__PURE__ */ jsx10("input", { type: "checkbox", checked: params.smartRadius, onChange: (e) => setParams({ ...params, smartRadius: e.target.checked }) }),
|
|
1585
1725
|
"Smart Radius"
|
|
1586
1726
|
] }),
|
|
1587
|
-
/* @__PURE__ */
|
|
1588
|
-
/* @__PURE__ */
|
|
1589
|
-
/* @__PURE__ */
|
|
1727
|
+
/* @__PURE__ */ jsxs10("div", { className: "flex gap-1", children: [
|
|
1728
|
+
/* @__PURE__ */ jsx10("button", { type: "button", className: button2, disabled: !sel || busy, onClick: refine, children: "Refine Edge" }),
|
|
1729
|
+
/* @__PURE__ */ jsx10("button", { type: "button", className: button2, onClick: () => setParams(DEFAULT_PARAMS), children: "Reset" })
|
|
1590
1730
|
] }),
|
|
1591
|
-
error && /* @__PURE__ */
|
|
1592
|
-
/* @__PURE__ */
|
|
1593
|
-
/* @__PURE__ */
|
|
1594
|
-
/* @__PURE__ */
|
|
1731
|
+
error && /* @__PURE__ */ jsx10("p", { role: "alert", className: "text-rose-400", children: error }),
|
|
1732
|
+
/* @__PURE__ */ jsx10("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px] mt-2", children: "Layer Mask" }),
|
|
1733
|
+
/* @__PURE__ */ jsxs10("div", { className: "flex gap-1 items-center", children: [
|
|
1734
|
+
/* @__PURE__ */ jsx10(
|
|
1595
1735
|
"select",
|
|
1596
1736
|
{
|
|
1597
1737
|
"aria-label": "New masked layer kind",
|
|
1598
1738
|
value: newKind,
|
|
1599
1739
|
onChange: (e) => setNewKind(e.target.value),
|
|
1600
1740
|
className: "flex-1 bg-slate-950 border border-slate-800 rounded px-1 py-1 text-slate-200",
|
|
1601
|
-
children: ADJUSTMENT_KINDS2.map((k) => /* @__PURE__ */
|
|
1741
|
+
children: ADJUSTMENT_KINDS2.map((k) => /* @__PURE__ */ jsx10("option", { value: k.kind, children: k.label }, k.kind))
|
|
1602
1742
|
}
|
|
1603
1743
|
),
|
|
1604
|
-
/* @__PURE__ */
|
|
1744
|
+
/* @__PURE__ */ jsx10(
|
|
1605
1745
|
"button",
|
|
1606
1746
|
{
|
|
1607
1747
|
type: "button",
|
|
@@ -1612,35 +1752,35 @@ var RefineEdgePanel = ({ controller, selection, layers, className = "" }) => {
|
|
|
1612
1752
|
}
|
|
1613
1753
|
)
|
|
1614
1754
|
] }),
|
|
1615
|
-
list.length > 0 && target && /* @__PURE__ */
|
|
1616
|
-
/* @__PURE__ */
|
|
1755
|
+
list.length > 0 && target && /* @__PURE__ */ jsxs10("div", { className: "flex flex-col gap-2", children: [
|
|
1756
|
+
/* @__PURE__ */ jsx10(
|
|
1617
1757
|
"select",
|
|
1618
1758
|
{
|
|
1619
1759
|
"aria-label": "Mask layer",
|
|
1620
1760
|
value: target.id,
|
|
1621
1761
|
onChange: (e) => setLayerId(e.target.value),
|
|
1622
1762
|
className: "bg-slate-950 border border-slate-800 rounded px-1 py-1 text-slate-200",
|
|
1623
|
-
children: list.map((l) => /* @__PURE__ */
|
|
1763
|
+
children: list.map((l) => /* @__PURE__ */ jsxs10("option", { value: l.id, children: [
|
|
1624
1764
|
l.name || adjustmentKindLabel2(l.kind),
|
|
1625
1765
|
l.mask ? " (masked)" : ""
|
|
1626
1766
|
] }, l.id))
|
|
1627
1767
|
}
|
|
1628
1768
|
),
|
|
1629
|
-
/* @__PURE__ */
|
|
1630
|
-
/* @__PURE__ */
|
|
1631
|
-
/* @__PURE__ */
|
|
1632
|
-
/* @__PURE__ */
|
|
1769
|
+
/* @__PURE__ */ jsxs10("div", { className: "flex flex-wrap gap-1", children: [
|
|
1770
|
+
/* @__PURE__ */ jsx10("button", { type: "button", className: button2, disabled: !sel, onClick: () => controller.applySelectionAsLayerMask(target.id), children: "Mask with Selection" }),
|
|
1771
|
+
/* @__PURE__ */ jsx10("button", { type: "button", className: button2, disabled: !target.mask, onClick: () => controller.selectionFromLayerMask(target.id), children: "Load as Selection" }),
|
|
1772
|
+
/* @__PURE__ */ jsx10("button", { type: "button", className: button2, disabled: !target.mask, onClick: () => controller.setAdjustmentLayerMask(target.id, null), children: "Remove Mask" })
|
|
1633
1773
|
] }),
|
|
1634
|
-
target.mask && /* @__PURE__ */
|
|
1635
|
-
/* @__PURE__ */
|
|
1636
|
-
/* @__PURE__ */
|
|
1637
|
-
/* @__PURE__ */
|
|
1638
|
-
/* @__PURE__ */
|
|
1774
|
+
target.mask && /* @__PURE__ */ jsxs10(Fragment3, { children: [
|
|
1775
|
+
/* @__PURE__ */ jsxs10("label", { className: "flex flex-col gap-1", children: [
|
|
1776
|
+
/* @__PURE__ */ jsxs10("span", { className: "flex justify-between text-slate-400", children: [
|
|
1777
|
+
/* @__PURE__ */ jsx10("span", { children: "Density" }),
|
|
1778
|
+
/* @__PURE__ */ jsxs10("span", { className: "font-mono", children: [
|
|
1639
1779
|
Math.round((target.mask.density ?? 1) * 100),
|
|
1640
1780
|
"%"
|
|
1641
1781
|
] })
|
|
1642
1782
|
] }),
|
|
1643
|
-
/* @__PURE__ */
|
|
1783
|
+
/* @__PURE__ */ jsx10(
|
|
1644
1784
|
"input",
|
|
1645
1785
|
{
|
|
1646
1786
|
type: "range",
|
|
@@ -1654,15 +1794,15 @@ var RefineEdgePanel = ({ controller, selection, layers, className = "" }) => {
|
|
|
1654
1794
|
}
|
|
1655
1795
|
)
|
|
1656
1796
|
] }),
|
|
1657
|
-
/* @__PURE__ */
|
|
1658
|
-
/* @__PURE__ */
|
|
1659
|
-
/* @__PURE__ */
|
|
1660
|
-
/* @__PURE__ */
|
|
1797
|
+
/* @__PURE__ */ jsxs10("label", { className: "flex flex-col gap-1", children: [
|
|
1798
|
+
/* @__PURE__ */ jsxs10("span", { className: "flex justify-between text-slate-400", children: [
|
|
1799
|
+
/* @__PURE__ */ jsx10("span", { children: "Mask Feather" }),
|
|
1800
|
+
/* @__PURE__ */ jsxs10("span", { className: "font-mono", children: [
|
|
1661
1801
|
target.mask.feather ?? 0,
|
|
1662
1802
|
"px"
|
|
1663
1803
|
] })
|
|
1664
1804
|
] }),
|
|
1665
|
-
/* @__PURE__ */
|
|
1805
|
+
/* @__PURE__ */ jsx10(
|
|
1666
1806
|
"input",
|
|
1667
1807
|
{
|
|
1668
1808
|
type: "range",
|
|
@@ -1682,14 +1822,14 @@ var RefineEdgePanel = ({ controller, selection, layers, className = "" }) => {
|
|
|
1682
1822
|
};
|
|
1683
1823
|
|
|
1684
1824
|
// src/image-editor/FreeTransformOptionsBar.tsx
|
|
1685
|
-
import { useEffect as
|
|
1825
|
+
import { useEffect as useEffect8, useState as useState11 } from "react";
|
|
1686
1826
|
import { FREE_TRANSFORM_FIELDS, FREE_TRANSFORM_MODE_OPTIONS, INTERPOLATIONS, TRANSFORM_ANCHORS, WARP_GRID_OPTIONS, WARP_STYLE_OPTIONS } from "@pixerate/editor/image-editor";
|
|
1687
|
-
import { jsx as
|
|
1688
|
-
var
|
|
1827
|
+
import { jsx as jsx11, jsxs as jsxs11 } from "react/jsx-runtime";
|
|
1828
|
+
var chip3 = (on) => `px-2 py-1 rounded text-[11px] ${on ? "bg-indigo-600 text-white" : "bg-slate-800 text-slate-300 hover:text-white"}`;
|
|
1689
1829
|
var round = (v, unit) => unit === "px" ? Math.round(v * 10) / 10 : Math.round(v * 100) / 100;
|
|
1690
1830
|
var FreeTransformOptionsBar = ({ tool, className }) => {
|
|
1691
|
-
const [, setTick] =
|
|
1692
|
-
|
|
1831
|
+
const [, setTick] = useState11(0);
|
|
1832
|
+
useEffect8(() => tool.subscribe(() => setTick((n) => n + 1)), [tool]);
|
|
1693
1833
|
const bar = tool.bar();
|
|
1694
1834
|
if (!tool.active || !bar) return null;
|
|
1695
1835
|
const warp = tool.warpBar();
|
|
@@ -1701,17 +1841,17 @@ var FreeTransformOptionsBar = ({ tool, className }) => {
|
|
|
1701
1841
|
const v = Number(raw);
|
|
1702
1842
|
if (raw.trim() !== "" && Number.isFinite(v) && Math.abs(v - bar[field]) > 1e-9) tool.setField(field, v);
|
|
1703
1843
|
};
|
|
1704
|
-
return /* @__PURE__ */
|
|
1705
|
-
/* @__PURE__ */
|
|
1706
|
-
/* @__PURE__ */
|
|
1707
|
-
tool.mode === "warp" && /* @__PURE__ */
|
|
1708
|
-
/* @__PURE__ */
|
|
1709
|
-
/* @__PURE__ */
|
|
1710
|
-
/* @__PURE__ */
|
|
1844
|
+
return /* @__PURE__ */ jsxs11("div", { className: `flex flex-wrap items-center gap-2 text-xs text-slate-200 ${className ?? ""}`, "data-testid": "free-transform-options", role: "toolbar", "aria-label": "Free Transform options", children: [
|
|
1845
|
+
/* @__PURE__ */ jsx11("div", { className: "flex gap-1", role: "group", "aria-label": "Transform mode", children: FREE_TRANSFORM_MODE_OPTIONS.map((m) => /* @__PURE__ */ jsx11("button", { type: "button", title: m.title, "aria-pressed": tool.mode === m.id, className: chip3(tool.mode === m.id), onClick: () => tool.setMode(m.id), children: m.label }, m.id)) }),
|
|
1846
|
+
/* @__PURE__ */ jsx11("div", { className: "grid grid-cols-3 gap-px", role: "group", "aria-label": "Reference point", children: TRANSFORM_ANCHORS.map((a) => /* @__PURE__ */ jsx11("button", { type: "button", "aria-label": `Reference point ${a}`, title: `Reference point: ${a}`, className: "h-2.5 w-2.5 rounded-sm bg-slate-700 hover:bg-indigo-500", onClick: () => tool.setReference(a) }, a)) }),
|
|
1847
|
+
tool.mode === "warp" && /* @__PURE__ */ jsxs11("div", { className: "flex flex-wrap items-center gap-2", role: "group", "aria-label": "Warp options", children: [
|
|
1848
|
+
/* @__PURE__ */ jsxs11("label", { className: "flex items-center gap-1", children: [
|
|
1849
|
+
/* @__PURE__ */ jsx11("span", { className: "text-slate-400", children: "Warp" }),
|
|
1850
|
+
/* @__PURE__ */ jsx11("select", { "aria-label": "Warp style", value: warp.style, onChange: (e) => tool.setWarp({ style: e.target.value }), className: "rounded border border-slate-700 bg-slate-900 px-1 py-0.5", children: WARP_STYLE_OPTIONS.map((o) => /* @__PURE__ */ jsx11("option", { value: o.id, children: o.label }, o.id)) })
|
|
1711
1851
|
] }),
|
|
1712
|
-
["bend", "horizontal", "vertical"].map((k) => /* @__PURE__ */
|
|
1713
|
-
/* @__PURE__ */
|
|
1714
|
-
/* @__PURE__ */
|
|
1852
|
+
["bend", "horizontal", "vertical"].map((k) => /* @__PURE__ */ jsxs11("label", { className: "flex items-center gap-1", children: [
|
|
1853
|
+
/* @__PURE__ */ jsx11("span", { className: "text-slate-400", children: k === "bend" ? "Bend" : k === "horizontal" ? "H" : "V" }),
|
|
1854
|
+
/* @__PURE__ */ jsx11(
|
|
1715
1855
|
"input",
|
|
1716
1856
|
{
|
|
1717
1857
|
type: "number",
|
|
@@ -1732,23 +1872,23 @@ var FreeTransformOptionsBar = ({ tool, className }) => {
|
|
|
1732
1872
|
},
|
|
1733
1873
|
`${k}:${warp[k]}`
|
|
1734
1874
|
),
|
|
1735
|
-
/* @__PURE__ */
|
|
1875
|
+
/* @__PURE__ */ jsx11("span", { className: "text-slate-500", children: "%" })
|
|
1736
1876
|
] }, k)),
|
|
1737
|
-
/* @__PURE__ */
|
|
1877
|
+
/* @__PURE__ */ jsx11(
|
|
1738
1878
|
"button",
|
|
1739
1879
|
{
|
|
1740
1880
|
type: "button",
|
|
1741
1881
|
title: "Bend along the vertical axis",
|
|
1742
1882
|
"aria-pressed": warp.orientation === "vertical",
|
|
1743
1883
|
disabled: warp.style === "custom",
|
|
1744
|
-
className:
|
|
1884
|
+
className: chip3(warp.orientation === "vertical"),
|
|
1745
1885
|
onClick: () => tool.setWarp({ orientation: warp.orientation === "vertical" ? "horizontal" : "vertical" }),
|
|
1746
1886
|
children: "Vertical"
|
|
1747
1887
|
}
|
|
1748
1888
|
),
|
|
1749
|
-
/* @__PURE__ */
|
|
1750
|
-
/* @__PURE__ */
|
|
1751
|
-
/* @__PURE__ */
|
|
1889
|
+
/* @__PURE__ */ jsxs11("label", { className: "flex items-center gap-1", children: [
|
|
1890
|
+
/* @__PURE__ */ jsx11("span", { className: "text-slate-400", children: "Grid" }),
|
|
1891
|
+
/* @__PURE__ */ jsx11(
|
|
1752
1892
|
"select",
|
|
1753
1893
|
{
|
|
1754
1894
|
"aria-label": "Warp grid",
|
|
@@ -1758,14 +1898,14 @@ var FreeTransformOptionsBar = ({ tool, className }) => {
|
|
|
1758
1898
|
tool.setWarp({ columns: g.columns, rows: g.rows });
|
|
1759
1899
|
},
|
|
1760
1900
|
className: "rounded border border-slate-700 bg-slate-900 px-1 py-0.5",
|
|
1761
|
-
children: WARP_GRID_OPTIONS.map((g) => /* @__PURE__ */
|
|
1901
|
+
children: WARP_GRID_OPTIONS.map((g) => /* @__PURE__ */ jsx11("option", { value: g.id, children: g.label }, g.id))
|
|
1762
1902
|
}
|
|
1763
1903
|
)
|
|
1764
1904
|
] })
|
|
1765
1905
|
] }),
|
|
1766
|
-
tool.mode !== "warp" && FREE_TRANSFORM_FIELDS.map((f) => /* @__PURE__ */
|
|
1767
|
-
/* @__PURE__ */
|
|
1768
|
-
/* @__PURE__ */
|
|
1906
|
+
tool.mode !== "warp" && FREE_TRANSFORM_FIELDS.map((f) => /* @__PURE__ */ jsxs11("label", { className: "flex items-center gap-1", title: f.title, children: [
|
|
1907
|
+
/* @__PURE__ */ jsx11("span", { className: "text-slate-400", children: f.label }),
|
|
1908
|
+
/* @__PURE__ */ jsx11(
|
|
1769
1909
|
"input",
|
|
1770
1910
|
{
|
|
1771
1911
|
type: "number",
|
|
@@ -1785,14 +1925,14 @@ var FreeTransformOptionsBar = ({ tool, className }) => {
|
|
|
1785
1925
|
},
|
|
1786
1926
|
`${f.id}:${round(bar[f.id], f.unit)}`
|
|
1787
1927
|
),
|
|
1788
|
-
/* @__PURE__ */
|
|
1789
|
-
f.id === "scaleX" && /* @__PURE__ */
|
|
1928
|
+
/* @__PURE__ */ jsx11("span", { className: "text-slate-500", children: f.unit }),
|
|
1929
|
+
f.id === "scaleX" && /* @__PURE__ */ jsx11(
|
|
1790
1930
|
"button",
|
|
1791
1931
|
{
|
|
1792
1932
|
type: "button",
|
|
1793
1933
|
"aria-label": "Keep width and height proportional",
|
|
1794
1934
|
"aria-pressed": tool.proportional,
|
|
1795
|
-
className:
|
|
1935
|
+
className: chip3(tool.proportional),
|
|
1796
1936
|
onClick: () => {
|
|
1797
1937
|
tool.proportional = !tool.proportional;
|
|
1798
1938
|
setTick((n) => n + 1);
|
|
@@ -1801,34 +1941,34 @@ var FreeTransformOptionsBar = ({ tool, className }) => {
|
|
|
1801
1941
|
}
|
|
1802
1942
|
)
|
|
1803
1943
|
] }, f.id)),
|
|
1804
|
-
/* @__PURE__ */
|
|
1805
|
-
/* @__PURE__ */
|
|
1806
|
-
/* @__PURE__ */
|
|
1944
|
+
/* @__PURE__ */ jsxs11("label", { className: "flex items-center gap-1", children: [
|
|
1945
|
+
/* @__PURE__ */ jsx11("span", { className: "text-slate-400", children: "Interpolation" }),
|
|
1946
|
+
/* @__PURE__ */ jsx11(
|
|
1807
1947
|
"select",
|
|
1808
1948
|
{
|
|
1809
1949
|
"aria-label": "Interpolation",
|
|
1810
1950
|
value: tool.interpolation,
|
|
1811
1951
|
onChange: (e) => tool.setInterpolation(e.target.value),
|
|
1812
1952
|
className: "rounded border border-slate-700 bg-slate-900 px-1 py-0.5",
|
|
1813
|
-
children: INTERPOLATIONS.map((i) => /* @__PURE__ */
|
|
1953
|
+
children: INTERPOLATIONS.map((i) => /* @__PURE__ */ jsx11("option", { value: i, children: i[0].toUpperCase() + i.slice(1) }, i))
|
|
1814
1954
|
}
|
|
1815
1955
|
)
|
|
1816
1956
|
] }),
|
|
1817
|
-
/* @__PURE__ */
|
|
1818
|
-
/* @__PURE__ */
|
|
1819
|
-
tool.error && /* @__PURE__ */
|
|
1957
|
+
/* @__PURE__ */ jsx11("button", { type: "button", title: "Commit (Enter)", className: "px-2 py-1 rounded bg-emerald-600 text-white hover:bg-emerald-500", onClick: () => tool.commit(), children: "Commit" }),
|
|
1958
|
+
/* @__PURE__ */ jsx11("button", { type: "button", title: "Cancel (Esc)", className: chip3(false), onClick: () => tool.cancel(), children: "Cancel" }),
|
|
1959
|
+
tool.error && /* @__PURE__ */ jsx11("span", { role: "alert", className: "text-rose-400", children: tool.error })
|
|
1820
1960
|
] });
|
|
1821
1961
|
};
|
|
1822
1962
|
|
|
1823
1963
|
// src/image-editor/ShapeOptionsBar.tsx
|
|
1824
|
-
import { useEffect as
|
|
1964
|
+
import { useEffect as useEffect9, useState as useState12 } from "react";
|
|
1825
1965
|
import { LIVE_SHAPE_KINDS, SHAPE_KIND_LABELS, applyShapeOptions } from "@pixerate/editor/image-editor";
|
|
1826
|
-
import { Fragment as
|
|
1827
|
-
var
|
|
1966
|
+
import { Fragment as Fragment4, jsx as jsx12, jsxs as jsxs12 } from "react/jsx-runtime";
|
|
1967
|
+
var chip4 = (on) => `px-2 py-1 rounded text-[11px] ${on ? "bg-indigo-600 text-white" : "bg-slate-800 text-slate-300 hover:text-white"}`;
|
|
1828
1968
|
var ShapeOptionsBar = ({ controller, options, onChange, className }) => {
|
|
1829
|
-
const [, setTick] =
|
|
1830
|
-
|
|
1831
|
-
const [error, setError] =
|
|
1969
|
+
const [, setTick] = useState12(0);
|
|
1970
|
+
useEffect9(() => controller.subscribe(() => setTick((n) => n + 1)), [controller]);
|
|
1971
|
+
const [error, setError] = useState12(null);
|
|
1832
1972
|
const active = controller.getActiveLayer();
|
|
1833
1973
|
const shapeId = active?.type === "shape" ? active.id : null;
|
|
1834
1974
|
const set = (change) => {
|
|
@@ -1842,13 +1982,13 @@ var ShapeOptionsBar = ({ controller, options, onChange, className }) => {
|
|
|
1842
1982
|
}
|
|
1843
1983
|
};
|
|
1844
1984
|
const num = (v, min, max) => Math.max(min, Math.min(max, Number(v) || min));
|
|
1845
|
-
return /* @__PURE__ */
|
|
1846
|
-
/* @__PURE__ */
|
|
1847
|
-
/* @__PURE__ */
|
|
1848
|
-
/* @__PURE__ */
|
|
1849
|
-
/* @__PURE__ */
|
|
1985
|
+
return /* @__PURE__ */ jsxs12("div", { className: `flex flex-col gap-2 text-xs text-slate-200 ${className ?? ""}`, "data-testid": "shape-options", children: [
|
|
1986
|
+
/* @__PURE__ */ jsx12("div", { className: "flex flex-wrap gap-1", role: "toolbar", "aria-label": "Shape kind", children: LIVE_SHAPE_KINDS.map((k) => /* @__PURE__ */ jsx12("button", { type: "button", "aria-pressed": options.kind === k, className: chip4(options.kind === k), onClick: () => onChange({ ...options, kind: k }), children: SHAPE_KIND_LABELS[k] }, k)) }),
|
|
1987
|
+
/* @__PURE__ */ jsxs12("div", { className: "flex flex-wrap items-center gap-3", children: [
|
|
1988
|
+
/* @__PURE__ */ jsxs12("label", { className: "flex items-center gap-1", children: [
|
|
1989
|
+
/* @__PURE__ */ jsx12("input", { type: "checkbox", "aria-label": "Fill", checked: options.fill !== null, onChange: (e) => set({ fill: e.target.checked ? "#4f46e5" : null }) }),
|
|
1850
1990
|
"Fill",
|
|
1851
|
-
/* @__PURE__ */
|
|
1991
|
+
/* @__PURE__ */ jsx12(
|
|
1852
1992
|
"input",
|
|
1853
1993
|
{
|
|
1854
1994
|
type: "color",
|
|
@@ -1860,10 +2000,10 @@ var ShapeOptionsBar = ({ controller, options, onChange, className }) => {
|
|
|
1860
2000
|
}
|
|
1861
2001
|
)
|
|
1862
2002
|
] }),
|
|
1863
|
-
/* @__PURE__ */
|
|
1864
|
-
/* @__PURE__ */
|
|
2003
|
+
/* @__PURE__ */ jsxs12("label", { className: "flex items-center gap-1", children: [
|
|
2004
|
+
/* @__PURE__ */ jsx12("input", { type: "checkbox", "aria-label": "Stroke", checked: options.stroke !== null, onChange: (e) => set({ stroke: e.target.checked ? "#000000" : null }) }),
|
|
1865
2005
|
"Stroke",
|
|
1866
|
-
/* @__PURE__ */
|
|
2006
|
+
/* @__PURE__ */ jsx12(
|
|
1867
2007
|
"input",
|
|
1868
2008
|
{
|
|
1869
2009
|
type: "color",
|
|
@@ -1875,9 +2015,9 @@ var ShapeOptionsBar = ({ controller, options, onChange, className }) => {
|
|
|
1875
2015
|
}
|
|
1876
2016
|
)
|
|
1877
2017
|
] }),
|
|
1878
|
-
/* @__PURE__ */
|
|
2018
|
+
/* @__PURE__ */ jsxs12("label", { className: "flex items-center gap-1", children: [
|
|
1879
2019
|
"Width",
|
|
1880
|
-
/* @__PURE__ */
|
|
2020
|
+
/* @__PURE__ */ jsx12(
|
|
1881
2021
|
"input",
|
|
1882
2022
|
{
|
|
1883
2023
|
type: "number",
|
|
@@ -1891,23 +2031,23 @@ var ShapeOptionsBar = ({ controller, options, onChange, className }) => {
|
|
|
1891
2031
|
)
|
|
1892
2032
|
] })
|
|
1893
2033
|
] }),
|
|
1894
|
-
/* @__PURE__ */
|
|
1895
|
-
options.kind === "rect" && /* @__PURE__ */
|
|
2034
|
+
/* @__PURE__ */ jsxs12("div", { className: "flex flex-wrap items-center gap-3", children: [
|
|
2035
|
+
options.kind === "rect" && /* @__PURE__ */ jsxs12("label", { className: "flex items-center gap-1", children: [
|
|
1896
2036
|
"Radius",
|
|
1897
|
-
/* @__PURE__ */
|
|
2037
|
+
/* @__PURE__ */ jsx12("input", { type: "number", "aria-label": "Corner radius", min: 0, max: 1e3, value: options.radius, onChange: (e) => set({ radius: num(e.target.value, 0, 1e3) }), className: "w-14 rounded border border-slate-700 bg-slate-950 px-1 py-0.5" })
|
|
1898
2038
|
] }),
|
|
1899
|
-
options.kind === "polygon" && /* @__PURE__ */
|
|
2039
|
+
options.kind === "polygon" && /* @__PURE__ */ jsxs12("label", { className: "flex items-center gap-1", children: [
|
|
1900
2040
|
"Sides",
|
|
1901
|
-
/* @__PURE__ */
|
|
2041
|
+
/* @__PURE__ */ jsx12("input", { type: "number", "aria-label": "Sides", min: 3, max: 100, value: options.sides, onChange: (e) => set({ sides: num(e.target.value, 3, 100) }), className: "w-14 rounded border border-slate-700 bg-slate-950 px-1 py-0.5" })
|
|
1902
2042
|
] }),
|
|
1903
|
-
options.kind === "star" && /* @__PURE__ */
|
|
1904
|
-
/* @__PURE__ */
|
|
2043
|
+
options.kind === "star" && /* @__PURE__ */ jsxs12(Fragment4, { children: [
|
|
2044
|
+
/* @__PURE__ */ jsxs12("label", { className: "flex items-center gap-1", children: [
|
|
1905
2045
|
"Points",
|
|
1906
|
-
/* @__PURE__ */
|
|
2046
|
+
/* @__PURE__ */ jsx12("input", { type: "number", "aria-label": "Points", min: 3, max: 100, value: options.points, onChange: (e) => set({ points: num(e.target.value, 3, 100) }), className: "w-14 rounded border border-slate-700 bg-slate-950 px-1 py-0.5" })
|
|
1907
2047
|
] }),
|
|
1908
|
-
/* @__PURE__ */
|
|
2048
|
+
/* @__PURE__ */ jsxs12("label", { className: "flex items-center gap-1", children: [
|
|
1909
2049
|
"Inner",
|
|
1910
|
-
/* @__PURE__ */
|
|
2050
|
+
/* @__PURE__ */ jsx12(
|
|
1911
2051
|
"input",
|
|
1912
2052
|
{
|
|
1913
2053
|
type: "range",
|
|
@@ -1922,33 +2062,33 @@ var ShapeOptionsBar = ({ controller, options, onChange, className }) => {
|
|
|
1922
2062
|
)
|
|
1923
2063
|
] })
|
|
1924
2064
|
] }),
|
|
1925
|
-
options.kind === "line" && /* @__PURE__ */
|
|
1926
|
-
/* @__PURE__ */
|
|
2065
|
+
options.kind === "line" && /* @__PURE__ */ jsxs12(Fragment4, { children: [
|
|
2066
|
+
/* @__PURE__ */ jsxs12("label", { className: "flex items-center gap-1", children: [
|
|
1927
2067
|
"Weight",
|
|
1928
|
-
/* @__PURE__ */
|
|
2068
|
+
/* @__PURE__ */ jsx12("input", { type: "number", "aria-label": "Line weight", min: 1, max: 200, value: options.weight, onChange: (e) => set({ weight: num(e.target.value, 1, 200) }), className: "w-14 rounded border border-slate-700 bg-slate-950 px-1 py-0.5" })
|
|
1929
2069
|
] }),
|
|
1930
|
-
/* @__PURE__ */
|
|
1931
|
-
/* @__PURE__ */
|
|
2070
|
+
/* @__PURE__ */ jsxs12("label", { className: "flex items-center gap-1", children: [
|
|
2071
|
+
/* @__PURE__ */ jsx12("input", { type: "checkbox", "aria-label": "Arrowhead", checked: options.arrow, onChange: (e) => set({ arrow: e.target.checked }) }),
|
|
1932
2072
|
"Arrowhead"
|
|
1933
2073
|
] })
|
|
1934
2074
|
] })
|
|
1935
2075
|
] }),
|
|
1936
|
-
/* @__PURE__ */
|
|
1937
|
-
error && /* @__PURE__ */
|
|
2076
|
+
/* @__PURE__ */ jsx12("p", { className: "text-[10px] text-slate-500", children: "Drag on the image to draw. Shift: square, circle or 45\xB0 line. Alt: from the centre." }),
|
|
2077
|
+
error && /* @__PURE__ */ jsx12("p", { role: "alert", className: "text-rose-400", children: error })
|
|
1938
2078
|
] });
|
|
1939
2079
|
};
|
|
1940
2080
|
|
|
1941
2081
|
// src/image-editor/TypeOptionsBar.tsx
|
|
1942
|
-
import { useEffect as
|
|
2082
|
+
import { useEffect as useEffect10, useState as useState13 } from "react";
|
|
1943
2083
|
import { TEXT_ALIGNS } from "@pixerate/editor/image-editor";
|
|
1944
|
-
import { jsx as
|
|
1945
|
-
var
|
|
2084
|
+
import { jsx as jsx13, jsxs as jsxs13 } from "react/jsx-runtime";
|
|
2085
|
+
var chip5 = (on) => `px-2 py-1 rounded text-[11px] ${on ? "bg-indigo-600 text-white" : "bg-slate-800 text-slate-300 hover:text-white"}`;
|
|
1946
2086
|
var ALIGN_LABELS = { left: "Left", center: "Centre", right: "Right", justify: "Justify" };
|
|
1947
2087
|
var TypeOptionsBar = ({ controller, options, onChange, session, className }) => {
|
|
1948
|
-
const [, setTick] =
|
|
1949
|
-
|
|
1950
|
-
|
|
1951
|
-
const [error, setError] =
|
|
2088
|
+
const [, setTick] = useState13(0);
|
|
2089
|
+
useEffect10(() => controller.subscribe(() => setTick((n) => n + 1)), [controller]);
|
|
2090
|
+
useEffect10(() => session?.subscribe(() => setTick((n) => n + 1)), [session]);
|
|
2091
|
+
const [error, setError] = useState13(null);
|
|
1952
2092
|
const active = controller.getActiveLayer();
|
|
1953
2093
|
const typeId = !session && active?.type === "type" ? active.id : null;
|
|
1954
2094
|
const here = session?.alive ? session.styleHere() : {};
|
|
@@ -1980,11 +2120,11 @@ var TypeOptionsBar = ({ controller, options, onChange, session, className }) =>
|
|
|
1980
2120
|
setError(e instanceof Error ? e.message : String(e));
|
|
1981
2121
|
}
|
|
1982
2122
|
};
|
|
1983
|
-
return /* @__PURE__ */
|
|
1984
|
-
/* @__PURE__ */
|
|
1985
|
-
/* @__PURE__ */
|
|
2123
|
+
return /* @__PURE__ */ jsxs13("div", { className: `flex flex-col gap-2 text-xs text-slate-200 ${className ?? ""}`, "data-testid": "type-options", children: [
|
|
2124
|
+
/* @__PURE__ */ jsxs13("div", { className: "flex flex-wrap items-center gap-2", children: [
|
|
2125
|
+
/* @__PURE__ */ jsxs13("label", { className: "flex items-center gap-1", children: [
|
|
1986
2126
|
"Font",
|
|
1987
|
-
/* @__PURE__ */
|
|
2127
|
+
/* @__PURE__ */ jsx13(
|
|
1988
2128
|
"input",
|
|
1989
2129
|
{
|
|
1990
2130
|
list: "pixerate-type-fonts",
|
|
@@ -1994,11 +2134,11 @@ var TypeOptionsBar = ({ controller, options, onChange, session, className }) =>
|
|
|
1994
2134
|
className: "w-32 rounded border border-slate-700 bg-slate-950 px-1 py-0.5"
|
|
1995
2135
|
}
|
|
1996
2136
|
),
|
|
1997
|
-
/* @__PURE__ */
|
|
2137
|
+
/* @__PURE__ */ jsx13("datalist", { id: "pixerate-type-fonts", children: fonts.map((f) => /* @__PURE__ */ jsx13("option", { value: f }, f)) })
|
|
1998
2138
|
] }),
|
|
1999
|
-
/* @__PURE__ */
|
|
2139
|
+
/* @__PURE__ */ jsxs13("label", { className: "flex items-center gap-1", children: [
|
|
2000
2140
|
"Size",
|
|
2001
|
-
/* @__PURE__ */
|
|
2141
|
+
/* @__PURE__ */ jsx13(
|
|
2002
2142
|
"input",
|
|
2003
2143
|
{
|
|
2004
2144
|
type: "number",
|
|
@@ -2011,24 +2151,24 @@ var TypeOptionsBar = ({ controller, options, onChange, session, className }) =>
|
|
|
2011
2151
|
}
|
|
2012
2152
|
)
|
|
2013
2153
|
] }),
|
|
2014
|
-
/* @__PURE__ */
|
|
2015
|
-
/* @__PURE__ */
|
|
2016
|
-
/* @__PURE__ */
|
|
2154
|
+
/* @__PURE__ */ jsx13("button", { type: "button", "aria-pressed": shown.fontWeight >= 600, className: `${chip5(shown.fontWeight >= 600)} font-bold`, onClick: () => style({ fontWeight: shown.fontWeight >= 600 ? 400 : 700 }), children: "B" }),
|
|
2155
|
+
/* @__PURE__ */ jsx13("button", { type: "button", "aria-pressed": shown.italic, className: `${chip5(shown.italic)} italic`, onClick: () => style({ italic: !shown.italic }), children: "I" }),
|
|
2156
|
+
/* @__PURE__ */ jsx13("input", { type: "color", "aria-label": "Text colour", value: shown.color, onChange: (e) => style({ color: e.target.value }), className: "h-6 w-8 rounded border border-slate-700 bg-transparent" })
|
|
2017
2157
|
] }),
|
|
2018
|
-
/* @__PURE__ */
|
|
2019
|
-
/* @__PURE__ */
|
|
2020
|
-
missing.length > 0 && /* @__PURE__ */
|
|
2158
|
+
/* @__PURE__ */ jsx13("div", { className: "flex gap-1", role: "toolbar", "aria-label": "Alignment", children: TEXT_ALIGNS.map((a) => /* @__PURE__ */ jsx13("button", { type: "button", "aria-pressed": options.align === a, className: chip5(options.align === a), onClick: () => style({ align: a }), children: ALIGN_LABELS[a] }, a)) }),
|
|
2159
|
+
/* @__PURE__ */ jsx13("p", { className: "text-[10px] text-slate-500", children: "Click to type point text, drag for a paragraph box, click text to edit it. Esc finishes." }),
|
|
2160
|
+
missing.length > 0 && /* @__PURE__ */ jsxs13("p", { role: "status", className: "text-amber-400", "data-testid": "type-missing-fonts", children: [
|
|
2021
2161
|
"Missing ",
|
|
2022
2162
|
missing.length === 1 ? "font" : "fonts",
|
|
2023
2163
|
": ",
|
|
2024
2164
|
missing.join(", ")
|
|
2025
2165
|
] }),
|
|
2026
|
-
error && /* @__PURE__ */
|
|
2166
|
+
error && /* @__PURE__ */ jsx13("p", { role: "alert", className: "text-rose-400", children: error })
|
|
2027
2167
|
] });
|
|
2028
2168
|
};
|
|
2029
2169
|
|
|
2030
2170
|
// src/image-editor/ImageEditor.tsx
|
|
2031
|
-
import { Fragment as
|
|
2171
|
+
import { Fragment as Fragment5, jsx as jsx14, jsxs as jsxs14 } from "react/jsx-runtime";
|
|
2032
2172
|
var ImageEditor = ({
|
|
2033
2173
|
editor: externalEditor,
|
|
2034
2174
|
src,
|
|
@@ -2046,9 +2186,9 @@ var ImageEditor = ({
|
|
|
2046
2186
|
const legacyProcess = normalizeProcessVersion(state.adjustments.process) < LATEST_PROCESS_VERSION;
|
|
2047
2187
|
const canvasRef = useRef5(null);
|
|
2048
2188
|
const containerRef = useRef5(null);
|
|
2049
|
-
const [activeTab, setActiveTab] =
|
|
2050
|
-
const [activeCropRatio, setActiveCropRatio] =
|
|
2051
|
-
const [selectionOptions, setSelectionOptions] =
|
|
2189
|
+
const [activeTab, setActiveTab] = useState14("crop");
|
|
2190
|
+
const [activeCropRatio, setActiveCropRatio] = useState14(null);
|
|
2191
|
+
const [selectionOptions, setSelectionOptions] = useState14(DEFAULT_SELECTION_TOOL_OPTIONS);
|
|
2052
2192
|
const selectionOptionsRef = useRef5(selectionOptions);
|
|
2053
2193
|
selectionOptionsRef.current = selectionOptions;
|
|
2054
2194
|
const selectionGestureRef = useRef5(null);
|
|
@@ -2056,7 +2196,7 @@ var ImageEditor = ({
|
|
|
2056
2196
|
selectionGestureRef.current = new SelectionGesture(controller, () => selectionOptionsRef.current);
|
|
2057
2197
|
}
|
|
2058
2198
|
const selectionDraftRef = useRef5(null);
|
|
2059
|
-
const [selectionError, setSelectionError] =
|
|
2199
|
+
const [selectionError, setSelectionError] = useState14(null);
|
|
2060
2200
|
const paintGestureRef = useRef5(null);
|
|
2061
2201
|
const paintControllerRef = useRef5(controller);
|
|
2062
2202
|
if (!paintGestureRef.current || paintControllerRef.current !== controller) {
|
|
@@ -2064,7 +2204,7 @@ var ImageEditor = ({
|
|
|
2064
2204
|
paintControllerRef.current = controller;
|
|
2065
2205
|
}
|
|
2066
2206
|
const brushCursorRef = useRef5(null);
|
|
2067
|
-
const [paintError, setPaintError] =
|
|
2207
|
+
const [paintError, setPaintError] = useState14(null);
|
|
2068
2208
|
const transformToolRef = useRef5(null);
|
|
2069
2209
|
const transformControllerRef = useRef5(controller);
|
|
2070
2210
|
if (!transformToolRef.current || transformControllerRef.current !== controller) {
|
|
@@ -2075,12 +2215,12 @@ var ImageEditor = ({
|
|
|
2075
2215
|
transformControllerRef.current = controller;
|
|
2076
2216
|
}
|
|
2077
2217
|
const transformTool = transformToolRef.current;
|
|
2078
|
-
const [, setTransformTick] =
|
|
2079
|
-
const [transformCursor, setTransformCursor] =
|
|
2080
|
-
const [shapeOptions, setShapeOptions] =
|
|
2218
|
+
const [, setTransformTick] = useState14(0);
|
|
2219
|
+
const [transformCursor, setTransformCursor] = useState14("default");
|
|
2220
|
+
const [shapeOptions, setShapeOptions] = useState14(DEFAULT_SHAPE_TOOL_OPTIONS);
|
|
2081
2221
|
const shapeOptionsRef = useRef5(shapeOptions);
|
|
2082
2222
|
shapeOptionsRef.current = shapeOptions;
|
|
2083
|
-
const [typeOptions, setTypeOptions] =
|
|
2223
|
+
const [typeOptions, setTypeOptions] = useState14(DEFAULT_TYPE_TOOL_OPTIONS);
|
|
2084
2224
|
const typeOptionsRef = useRef5(typeOptions);
|
|
2085
2225
|
typeOptionsRef.current = typeOptions;
|
|
2086
2226
|
const shapeGestureRef = useRef5(null);
|
|
@@ -2093,15 +2233,15 @@ var ImageEditor = ({
|
|
|
2093
2233
|
shapeTypeControllerRef.current = controller;
|
|
2094
2234
|
}
|
|
2095
2235
|
const typeInputRef = useRef5(null);
|
|
2096
|
-
const [typeSession, setTypeSession] =
|
|
2097
|
-
const [shapeTypeError, setShapeTypeError] =
|
|
2098
|
-
const [inpaintPrompt, setInpaintPrompt] =
|
|
2099
|
-
const [inpaintMaskMode, setInpaintMaskMode] =
|
|
2100
|
-
const [isRemovingBg, setIsRemovingBg] =
|
|
2101
|
-
const [isInpainting, setIsInpainting] =
|
|
2102
|
-
const [aiError, setAiError] =
|
|
2103
|
-
const [aiSuccess, setAiSuccess] =
|
|
2104
|
-
const [aiTarget, setAiTarget] =
|
|
2236
|
+
const [typeSession, setTypeSession] = useState14(typeToolRef.current.session);
|
|
2237
|
+
const [shapeTypeError, setShapeTypeError] = useState14(null);
|
|
2238
|
+
const [inpaintPrompt, setInpaintPrompt] = useState14("");
|
|
2239
|
+
const [inpaintMaskMode, setInpaintMaskMode] = useState14("annotations");
|
|
2240
|
+
const [isRemovingBg, setIsRemovingBg] = useState14(false);
|
|
2241
|
+
const [isInpainting, setIsInpainting] = useState14(false);
|
|
2242
|
+
const [aiError, setAiError] = useState14(null);
|
|
2243
|
+
const [aiSuccess, setAiSuccess] = useState14(null);
|
|
2244
|
+
const [aiTarget, setAiTarget] = useState14("auto");
|
|
2105
2245
|
const aiOptions = aiTarget === "auto" ? {} : { target: aiTarget };
|
|
2106
2246
|
const effectiveOnInpaint = onInpaint || aiHooks?.onInpaint;
|
|
2107
2247
|
const effectiveOnRemoveBg = onRemoveBackground || aiHooks?.onRemoveBackground;
|
|
@@ -2164,10 +2304,10 @@ var ImageEditor = ({
|
|
|
2164
2304
|
setIsInpainting(false);
|
|
2165
2305
|
}
|
|
2166
2306
|
};
|
|
2167
|
-
const [activeColor, setActiveColor] =
|
|
2168
|
-
const [strokeWidth, setStrokeWidth] =
|
|
2169
|
-
const [fontSize, setFontSize] =
|
|
2170
|
-
const [textInput, setTextInput] =
|
|
2307
|
+
const [activeColor, setActiveColor] = useState14("#ef4444");
|
|
2308
|
+
const [strokeWidth, setStrokeWidth] = useState14(3);
|
|
2309
|
+
const [fontSize, setFontSize] = useState14(24);
|
|
2310
|
+
const [textInput, setTextInput] = useState14("");
|
|
2171
2311
|
const draftAnnotationRef = useRef5(null);
|
|
2172
2312
|
const draftCropRef = useRef5(null);
|
|
2173
2313
|
const cropDragInfoRef = useRef5(null);
|
|
@@ -2198,8 +2338,8 @@ var ImageEditor = ({
|
|
|
2198
2338
|
},
|
|
2199
2339
|
[controller, activeTab, transformTool]
|
|
2200
2340
|
);
|
|
2201
|
-
|
|
2202
|
-
|
|
2341
|
+
useEffect11(() => typeSession?.subscribe(() => void renderCanvas()), [typeSession, renderCanvas]);
|
|
2342
|
+
useEffect11(() => {
|
|
2203
2343
|
if (activeTab === "annotate" && state.activeTool === "type") return;
|
|
2204
2344
|
if (typeToolRef.current?.session) {
|
|
2205
2345
|
typeToolRef.current.finish();
|
|
@@ -2234,7 +2374,7 @@ var ImageEditor = ({
|
|
|
2234
2374
|
el.value = "";
|
|
2235
2375
|
}
|
|
2236
2376
|
};
|
|
2237
|
-
|
|
2377
|
+
useEffect11(() => transformTool.subscribe(() => {
|
|
2238
2378
|
setTransformTick((n) => n + 1);
|
|
2239
2379
|
void renderCanvas();
|
|
2240
2380
|
}), [transformTool, renderCanvas]);
|
|
@@ -2277,7 +2417,7 @@ var ImageEditor = ({
|
|
|
2277
2417
|
transformTool.up();
|
|
2278
2418
|
return true;
|
|
2279
2419
|
};
|
|
2280
|
-
|
|
2420
|
+
useEffect11(() => {
|
|
2281
2421
|
if (typeof window === "undefined") return;
|
|
2282
2422
|
const onKey = (e) => {
|
|
2283
2423
|
if (transformTool.key(e)) e.preventDefault();
|
|
@@ -2285,7 +2425,7 @@ var ImageEditor = ({
|
|
|
2285
2425
|
window.addEventListener("keydown", onKey);
|
|
2286
2426
|
return () => window.removeEventListener("keydown", onKey);
|
|
2287
2427
|
}, [transformTool]);
|
|
2288
|
-
|
|
2428
|
+
useEffect11(() => {
|
|
2289
2429
|
const raf = typeof requestAnimationFrame !== "undefined" ? requestAnimationFrame : (cb) => setTimeout(cb, 0);
|
|
2290
2430
|
const caf = typeof cancelAnimationFrame !== "undefined" ? cancelAnimationFrame : (id) => clearTimeout(id);
|
|
2291
2431
|
const animId = raf(() => {
|
|
@@ -2293,12 +2433,12 @@ var ImageEditor = ({
|
|
|
2293
2433
|
});
|
|
2294
2434
|
return () => caf(animId);
|
|
2295
2435
|
}, [renderCanvas, state]);
|
|
2296
|
-
|
|
2436
|
+
useEffect11(() => {
|
|
2297
2437
|
if (activeTab === "crop" && editor.state.activeTool !== "crop") {
|
|
2298
2438
|
editor.setTool("crop");
|
|
2299
2439
|
}
|
|
2300
2440
|
}, [activeTab, editor]);
|
|
2301
|
-
|
|
2441
|
+
useEffect11(() => {
|
|
2302
2442
|
const container = containerRef.current;
|
|
2303
2443
|
if (!container) return;
|
|
2304
2444
|
if (typeof ResizeObserver !== "undefined") {
|
|
@@ -2347,7 +2487,7 @@ var ImageEditor = ({
|
|
|
2347
2487
|
} catch {
|
|
2348
2488
|
}
|
|
2349
2489
|
const [first] = paintSamples(e);
|
|
2350
|
-
setPaintError(paintGestureRef.current.down(first));
|
|
2490
|
+
setPaintError(paintGestureRef.current.down({ ...first, altKey: e.altKey }));
|
|
2351
2491
|
};
|
|
2352
2492
|
const handlePaintPointerMove = (e) => {
|
|
2353
2493
|
if (handleTransformPointerMove(e)) return;
|
|
@@ -2366,7 +2506,7 @@ var ImageEditor = ({
|
|
|
2366
2506
|
if (g.error) setPaintError(g.error);
|
|
2367
2507
|
}
|
|
2368
2508
|
};
|
|
2369
|
-
|
|
2509
|
+
useEffect11(() => {
|
|
2370
2510
|
if (activeTab !== "paint" || typeof window === "undefined") return;
|
|
2371
2511
|
const onKey = (e) => {
|
|
2372
2512
|
if (handlePaintShortcut(controller, e)) e.preventDefault();
|
|
@@ -2761,15 +2901,15 @@ var ImageEditor = ({
|
|
|
2761
2901
|
link.click();
|
|
2762
2902
|
}
|
|
2763
2903
|
};
|
|
2764
|
-
return /* @__PURE__ */
|
|
2904
|
+
return /* @__PURE__ */ jsxs14(
|
|
2765
2905
|
"div",
|
|
2766
2906
|
{
|
|
2767
2907
|
className: `flex flex-col bg-slate-900 border border-slate-800 rounded-xl overflow-hidden shadow-2xl text-slate-100 ${className}`,
|
|
2768
2908
|
style,
|
|
2769
2909
|
children: [
|
|
2770
|
-
/* @__PURE__ */
|
|
2771
|
-
/* @__PURE__ */
|
|
2772
|
-
/* @__PURE__ */
|
|
2910
|
+
/* @__PURE__ */ jsxs14("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: [
|
|
2911
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex items-center gap-1 bg-slate-900 p-1 rounded-lg border border-slate-800 text-xs", children: [
|
|
2912
|
+
/* @__PURE__ */ jsx14(
|
|
2773
2913
|
"button",
|
|
2774
2914
|
{
|
|
2775
2915
|
type: "button",
|
|
@@ -2781,7 +2921,7 @@ var ImageEditor = ({
|
|
|
2781
2921
|
children: "Transform & Crop"
|
|
2782
2922
|
}
|
|
2783
2923
|
),
|
|
2784
|
-
/* @__PURE__ */
|
|
2924
|
+
/* @__PURE__ */ jsx14(
|
|
2785
2925
|
"button",
|
|
2786
2926
|
{
|
|
2787
2927
|
type: "button",
|
|
@@ -2793,7 +2933,7 @@ var ImageEditor = ({
|
|
|
2793
2933
|
children: "Adjustments"
|
|
2794
2934
|
}
|
|
2795
2935
|
),
|
|
2796
|
-
/* @__PURE__ */
|
|
2936
|
+
/* @__PURE__ */ jsx14(
|
|
2797
2937
|
"button",
|
|
2798
2938
|
{
|
|
2799
2939
|
type: "button",
|
|
@@ -2805,7 +2945,7 @@ var ImageEditor = ({
|
|
|
2805
2945
|
children: "Layers"
|
|
2806
2946
|
}
|
|
2807
2947
|
),
|
|
2808
|
-
/* @__PURE__ */
|
|
2948
|
+
/* @__PURE__ */ jsx14(
|
|
2809
2949
|
"button",
|
|
2810
2950
|
{
|
|
2811
2951
|
type: "button",
|
|
@@ -2817,7 +2957,7 @@ var ImageEditor = ({
|
|
|
2817
2957
|
children: "Paint"
|
|
2818
2958
|
}
|
|
2819
2959
|
),
|
|
2820
|
-
/* @__PURE__ */
|
|
2960
|
+
/* @__PURE__ */ jsx14(
|
|
2821
2961
|
"button",
|
|
2822
2962
|
{
|
|
2823
2963
|
type: "button",
|
|
@@ -2829,7 +2969,7 @@ var ImageEditor = ({
|
|
|
2829
2969
|
children: "Select & Mask"
|
|
2830
2970
|
}
|
|
2831
2971
|
),
|
|
2832
|
-
/* @__PURE__ */
|
|
2972
|
+
/* @__PURE__ */ jsx14(
|
|
2833
2973
|
"button",
|
|
2834
2974
|
{
|
|
2835
2975
|
type: "button",
|
|
@@ -2841,7 +2981,7 @@ var ImageEditor = ({
|
|
|
2841
2981
|
children: "Annotations"
|
|
2842
2982
|
}
|
|
2843
2983
|
),
|
|
2844
|
-
/* @__PURE__ */
|
|
2984
|
+
/* @__PURE__ */ jsx14(
|
|
2845
2985
|
"button",
|
|
2846
2986
|
{
|
|
2847
2987
|
type: "button",
|
|
@@ -2853,7 +2993,7 @@ var ImageEditor = ({
|
|
|
2853
2993
|
children: "Depth Mask"
|
|
2854
2994
|
}
|
|
2855
2995
|
),
|
|
2856
|
-
/* @__PURE__ */
|
|
2996
|
+
/* @__PURE__ */ jsxs14(
|
|
2857
2997
|
"button",
|
|
2858
2998
|
{
|
|
2859
2999
|
type: "button",
|
|
@@ -2863,14 +3003,14 @@ var ImageEditor = ({
|
|
|
2863
3003
|
},
|
|
2864
3004
|
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"}`,
|
|
2865
3005
|
children: [
|
|
2866
|
-
/* @__PURE__ */
|
|
3006
|
+
/* @__PURE__ */ jsx14("svg", { className: "w-3.5 h-3.5", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: /* @__PURE__ */ jsx14("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" }) }),
|
|
2867
3007
|
"AI Tools"
|
|
2868
3008
|
]
|
|
2869
3009
|
}
|
|
2870
3010
|
)
|
|
2871
3011
|
] }),
|
|
2872
|
-
/* @__PURE__ */
|
|
2873
|
-
/* @__PURE__ */
|
|
3012
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex items-center gap-2 text-xs", children: [
|
|
3013
|
+
/* @__PURE__ */ jsx14(
|
|
2874
3014
|
"button",
|
|
2875
3015
|
{
|
|
2876
3016
|
type: "button",
|
|
@@ -2881,7 +3021,7 @@ var ImageEditor = ({
|
|
|
2881
3021
|
children: "\u21A9"
|
|
2882
3022
|
}
|
|
2883
3023
|
),
|
|
2884
|
-
/* @__PURE__ */
|
|
3024
|
+
/* @__PURE__ */ jsx14(
|
|
2885
3025
|
"button",
|
|
2886
3026
|
{
|
|
2887
3027
|
type: "button",
|
|
@@ -2892,7 +3032,7 @@ var ImageEditor = ({
|
|
|
2892
3032
|
children: "\u21AA"
|
|
2893
3033
|
}
|
|
2894
3034
|
),
|
|
2895
|
-
/* @__PURE__ */
|
|
3035
|
+
/* @__PURE__ */ jsx14(
|
|
2896
3036
|
"button",
|
|
2897
3037
|
{
|
|
2898
3038
|
type: "button",
|
|
@@ -2901,8 +3041,8 @@ var ImageEditor = ({
|
|
|
2901
3041
|
children: "Reset"
|
|
2902
3042
|
}
|
|
2903
3043
|
),
|
|
2904
|
-
/* @__PURE__ */
|
|
2905
|
-
/* @__PURE__ */
|
|
3044
|
+
/* @__PURE__ */ jsx14("div", { className: "h-4 w-px bg-slate-800 mx-1" }),
|
|
3045
|
+
/* @__PURE__ */ jsx14(
|
|
2906
3046
|
"button",
|
|
2907
3047
|
{
|
|
2908
3048
|
type: "button",
|
|
@@ -2912,11 +3052,11 @@ var ImageEditor = ({
|
|
|
2912
3052
|
children: "-"
|
|
2913
3053
|
}
|
|
2914
3054
|
),
|
|
2915
|
-
/* @__PURE__ */
|
|
3055
|
+
/* @__PURE__ */ jsxs14("span", { className: "font-mono text-slate-400 w-10 text-center", children: [
|
|
2916
3056
|
Math.round(state.zoom * 100),
|
|
2917
3057
|
"%"
|
|
2918
3058
|
] }),
|
|
2919
|
-
/* @__PURE__ */
|
|
3059
|
+
/* @__PURE__ */ jsx14(
|
|
2920
3060
|
"button",
|
|
2921
3061
|
{
|
|
2922
3062
|
type: "button",
|
|
@@ -2926,8 +3066,8 @@ var ImageEditor = ({
|
|
|
2926
3066
|
children: "+"
|
|
2927
3067
|
}
|
|
2928
3068
|
),
|
|
2929
|
-
/* @__PURE__ */
|
|
2930
|
-
/* @__PURE__ */
|
|
3069
|
+
/* @__PURE__ */ jsx14("div", { className: "h-4 w-px bg-slate-800 mx-1" }),
|
|
3070
|
+
/* @__PURE__ */ jsx14(
|
|
2931
3071
|
"button",
|
|
2932
3072
|
{
|
|
2933
3073
|
type: "button",
|
|
@@ -2938,7 +3078,7 @@ var ImageEditor = ({
|
|
|
2938
3078
|
children: "Hold Compare"
|
|
2939
3079
|
}
|
|
2940
3080
|
),
|
|
2941
|
-
/* @__PURE__ */
|
|
3081
|
+
/* @__PURE__ */ jsx14(
|
|
2942
3082
|
"button",
|
|
2943
3083
|
{
|
|
2944
3084
|
type: "button",
|
|
@@ -2949,16 +3089,16 @@ var ImageEditor = ({
|
|
|
2949
3089
|
)
|
|
2950
3090
|
] })
|
|
2951
3091
|
] }),
|
|
2952
|
-
transformTool.active && /* @__PURE__ */
|
|
2953
|
-
!transformTool.active && transformTool.error && /* @__PURE__ */
|
|
2954
|
-
/* @__PURE__ */
|
|
2955
|
-
/* @__PURE__ */
|
|
3092
|
+
transformTool.active && /* @__PURE__ */ jsx14(FreeTransformOptionsBar, { tool: transformTool, className: "border-b border-slate-800 bg-slate-900/95 px-4 py-2" }),
|
|
3093
|
+
!transformTool.active && transformTool.error && /* @__PURE__ */ jsx14("div", { role: "alert", className: "border-b border-rose-900 bg-rose-950/80 px-4 py-1.5 text-xs text-rose-200", children: transformTool.error }),
|
|
3094
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex flex-col md:flex-row flex-1 min-h-[520px] md:h-[560px]", children: [
|
|
3095
|
+
/* @__PURE__ */ jsxs14(
|
|
2956
3096
|
"div",
|
|
2957
3097
|
{
|
|
2958
3098
|
ref: containerRef,
|
|
2959
3099
|
className: "relative flex-1 h-[360px] md:h-full min-h-[320px] bg-slate-950 overflow-hidden select-none",
|
|
2960
3100
|
children: [
|
|
2961
|
-
/* @__PURE__ */
|
|
3101
|
+
/* @__PURE__ */ jsx14(
|
|
2962
3102
|
"canvas",
|
|
2963
3103
|
{
|
|
2964
3104
|
ref: canvasRef,
|
|
@@ -2975,7 +3115,7 @@ var ImageEditor = ({
|
|
|
2975
3115
|
className: `absolute inset-0 w-full h-full block ${transformTool.active ? "touch-none" : activeTab === "paint" ? "touch-none cursor-crosshair" : activeTab === "annotate" && state.activeTool === "type" ? "cursor-text" : activeTab === "annotate" && state.activeTool === "shape" ? "cursor-crosshair" : ""}`
|
|
2976
3116
|
}
|
|
2977
3117
|
),
|
|
2978
|
-
typeSession && /* @__PURE__ */
|
|
3118
|
+
typeSession && /* @__PURE__ */ jsx14(
|
|
2979
3119
|
"textarea",
|
|
2980
3120
|
{
|
|
2981
3121
|
ref: typeInputRef,
|
|
@@ -2997,11 +3137,11 @@ var ImageEditor = ({
|
|
|
2997
3137
|
]
|
|
2998
3138
|
}
|
|
2999
3139
|
),
|
|
3000
|
-
/* @__PURE__ */
|
|
3001
|
-
activeTab === "crop" && /* @__PURE__ */
|
|
3002
|
-
/* @__PURE__ */
|
|
3003
|
-
/* @__PURE__ */
|
|
3004
|
-
/* @__PURE__ */
|
|
3140
|
+
/* @__PURE__ */ jsxs14("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: [
|
|
3141
|
+
activeTab === "crop" && /* @__PURE__ */ jsxs14("div", { className: "flex flex-col gap-4 text-xs", children: [
|
|
3142
|
+
/* @__PURE__ */ jsx14("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Aspect Ratio Presets" }),
|
|
3143
|
+
/* @__PURE__ */ jsxs14("div", { className: "grid grid-cols-3 gap-2", children: [
|
|
3144
|
+
/* @__PURE__ */ jsx14(
|
|
3005
3145
|
"button",
|
|
3006
3146
|
{
|
|
3007
3147
|
type: "button",
|
|
@@ -3013,7 +3153,7 @@ var ImageEditor = ({
|
|
|
3013
3153
|
children: "Freeform"
|
|
3014
3154
|
}
|
|
3015
3155
|
),
|
|
3016
|
-
/* @__PURE__ */
|
|
3156
|
+
/* @__PURE__ */ jsx14(
|
|
3017
3157
|
"button",
|
|
3018
3158
|
{
|
|
3019
3159
|
type: "button",
|
|
@@ -3025,7 +3165,7 @@ var ImageEditor = ({
|
|
|
3025
3165
|
children: "1:1 Square"
|
|
3026
3166
|
}
|
|
3027
3167
|
),
|
|
3028
|
-
/* @__PURE__ */
|
|
3168
|
+
/* @__PURE__ */ jsx14(
|
|
3029
3169
|
"button",
|
|
3030
3170
|
{
|
|
3031
3171
|
type: "button",
|
|
@@ -3037,7 +3177,7 @@ var ImageEditor = ({
|
|
|
3037
3177
|
children: "4:3 Standard"
|
|
3038
3178
|
}
|
|
3039
3179
|
),
|
|
3040
|
-
/* @__PURE__ */
|
|
3180
|
+
/* @__PURE__ */ jsx14(
|
|
3041
3181
|
"button",
|
|
3042
3182
|
{
|
|
3043
3183
|
type: "button",
|
|
@@ -3049,7 +3189,7 @@ var ImageEditor = ({
|
|
|
3049
3189
|
children: "16:9 Wide"
|
|
3050
3190
|
}
|
|
3051
3191
|
),
|
|
3052
|
-
/* @__PURE__ */
|
|
3192
|
+
/* @__PURE__ */ jsx14(
|
|
3053
3193
|
"button",
|
|
3054
3194
|
{
|
|
3055
3195
|
type: "button",
|
|
@@ -3061,7 +3201,7 @@ var ImageEditor = ({
|
|
|
3061
3201
|
children: "3:2 Photo"
|
|
3062
3202
|
}
|
|
3063
3203
|
),
|
|
3064
|
-
/* @__PURE__ */
|
|
3204
|
+
/* @__PURE__ */ jsx14(
|
|
3065
3205
|
"button",
|
|
3066
3206
|
{
|
|
3067
3207
|
type: "button",
|
|
@@ -3074,10 +3214,10 @@ var ImageEditor = ({
|
|
|
3074
3214
|
}
|
|
3075
3215
|
)
|
|
3076
3216
|
] }),
|
|
3077
|
-
/* @__PURE__ */
|
|
3078
|
-
/* @__PURE__ */
|
|
3079
|
-
/* @__PURE__ */
|
|
3080
|
-
/* @__PURE__ */
|
|
3217
|
+
/* @__PURE__ */ jsx14("div", { className: "h-px bg-slate-800 my-1" }),
|
|
3218
|
+
/* @__PURE__ */ jsx14("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Orientation & Flips" }),
|
|
3219
|
+
/* @__PURE__ */ jsxs14("div", { className: "grid grid-cols-2 gap-2", children: [
|
|
3220
|
+
/* @__PURE__ */ jsx14(
|
|
3081
3221
|
"button",
|
|
3082
3222
|
{
|
|
3083
3223
|
type: "button",
|
|
@@ -3086,7 +3226,7 @@ var ImageEditor = ({
|
|
|
3086
3226
|
children: "Rotate -90\xB0"
|
|
3087
3227
|
}
|
|
3088
3228
|
),
|
|
3089
|
-
/* @__PURE__ */
|
|
3229
|
+
/* @__PURE__ */ jsx14(
|
|
3090
3230
|
"button",
|
|
3091
3231
|
{
|
|
3092
3232
|
type: "button",
|
|
@@ -3095,7 +3235,7 @@ var ImageEditor = ({
|
|
|
3095
3235
|
children: "Rotate +90\xB0"
|
|
3096
3236
|
}
|
|
3097
3237
|
),
|
|
3098
|
-
/* @__PURE__ */
|
|
3238
|
+
/* @__PURE__ */ jsx14(
|
|
3099
3239
|
"button",
|
|
3100
3240
|
{
|
|
3101
3241
|
type: "button",
|
|
@@ -3104,7 +3244,7 @@ var ImageEditor = ({
|
|
|
3104
3244
|
children: "Flip Horizontal"
|
|
3105
3245
|
}
|
|
3106
3246
|
),
|
|
3107
|
-
/* @__PURE__ */
|
|
3247
|
+
/* @__PURE__ */ jsx14(
|
|
3108
3248
|
"button",
|
|
3109
3249
|
{
|
|
3110
3250
|
type: "button",
|
|
@@ -3115,10 +3255,10 @@ var ImageEditor = ({
|
|
|
3115
3255
|
)
|
|
3116
3256
|
] })
|
|
3117
3257
|
] }),
|
|
3118
|
-
activeTab === "adjust" && /* @__PURE__ */
|
|
3119
|
-
/* @__PURE__ */
|
|
3120
|
-
/* @__PURE__ */
|
|
3121
|
-
/* @__PURE__ */
|
|
3258
|
+
activeTab === "adjust" && /* @__PURE__ */ jsxs14("div", { className: "flex flex-col gap-3 text-xs", children: [
|
|
3259
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex items-center justify-between", children: [
|
|
3260
|
+
/* @__PURE__ */ jsx14("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Color Adjustments" }),
|
|
3261
|
+
/* @__PURE__ */ jsx14(
|
|
3122
3262
|
"button",
|
|
3123
3263
|
{
|
|
3124
3264
|
type: "button",
|
|
@@ -3128,9 +3268,9 @@ var ImageEditor = ({
|
|
|
3128
3268
|
}
|
|
3129
3269
|
)
|
|
3130
3270
|
] }),
|
|
3131
|
-
/* @__PURE__ */
|
|
3132
|
-
IMAGE_ADJUSTMENT_CONTROLS.map((spec) => /* @__PURE__ */
|
|
3133
|
-
/* @__PURE__ */
|
|
3271
|
+
/* @__PURE__ */ jsx14(Histogram, { histogram: editor.histogram }),
|
|
3272
|
+
IMAGE_ADJUSTMENT_CONTROLS.map((spec) => /* @__PURE__ */ jsxs14(React13.Fragment, { children: [
|
|
3273
|
+
/* @__PURE__ */ jsx14(
|
|
3134
3274
|
ControlSlider,
|
|
3135
3275
|
{
|
|
3136
3276
|
spec,
|
|
@@ -3139,14 +3279,14 @@ var ImageEditor = ({
|
|
|
3139
3279
|
onChange: (v) => editor.setAdjustments({ [spec.id]: v })
|
|
3140
3280
|
}
|
|
3141
3281
|
),
|
|
3142
|
-
spec.id === "tint" && legacyProcess && /* @__PURE__ */
|
|
3282
|
+
spec.id === "tint" && legacyProcess && /* @__PURE__ */ jsxs14(
|
|
3143
3283
|
"div",
|
|
3144
3284
|
{
|
|
3145
3285
|
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",
|
|
3146
3286
|
"data-testid": "image-editor-process-notice",
|
|
3147
3287
|
children: [
|
|
3148
|
-
/* @__PURE__ */
|
|
3149
|
-
/* @__PURE__ */
|
|
3288
|
+
/* @__PURE__ */ jsx14("span", { children: "Legacy rendering (process 1). Tint needs the current process." }),
|
|
3289
|
+
/* @__PURE__ */ jsx14(
|
|
3150
3290
|
"button",
|
|
3151
3291
|
{
|
|
3152
3292
|
type: "button",
|
|
@@ -3159,7 +3299,7 @@ var ImageEditor = ({
|
|
|
3159
3299
|
}
|
|
3160
3300
|
)
|
|
3161
3301
|
] }, spec.id)),
|
|
3162
|
-
/* @__PURE__ */
|
|
3302
|
+
/* @__PURE__ */ jsx14("div", { className: "border-t border-slate-700/60 pt-3", children: /* @__PURE__ */ jsx14(
|
|
3163
3303
|
AdjustmentLayersPanel,
|
|
3164
3304
|
{
|
|
3165
3305
|
controller,
|
|
@@ -3168,9 +3308,9 @@ var ImageEditor = ({
|
|
|
3168
3308
|
}
|
|
3169
3309
|
) })
|
|
3170
3310
|
] }),
|
|
3171
|
-
activeTab === "layers" && /* @__PURE__ */
|
|
3172
|
-
/* @__PURE__ */
|
|
3173
|
-
/* @__PURE__ */
|
|
3311
|
+
activeTab === "layers" && /* @__PURE__ */ jsxs14("div", { className: "flex flex-col gap-3 text-xs", children: [
|
|
3312
|
+
/* @__PURE__ */ jsx14("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Layers" }),
|
|
3313
|
+
/* @__PURE__ */ jsx14(
|
|
3174
3314
|
"button",
|
|
3175
3315
|
{
|
|
3176
3316
|
type: "button",
|
|
@@ -3181,12 +3321,14 @@ var ImageEditor = ({
|
|
|
3181
3321
|
children: "Free Transform"
|
|
3182
3322
|
}
|
|
3183
3323
|
),
|
|
3184
|
-
/* @__PURE__ */
|
|
3324
|
+
/* @__PURE__ */ jsx14(LayersPanel, { controller }),
|
|
3325
|
+
/* @__PURE__ */ jsx14("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Colour" }),
|
|
3326
|
+
/* @__PURE__ */ jsx14(ColorProfilePanel, { controller })
|
|
3185
3327
|
] }),
|
|
3186
|
-
activeTab === "paint" && /* @__PURE__ */
|
|
3187
|
-
/* @__PURE__ */
|
|
3188
|
-
/* @__PURE__ */
|
|
3189
|
-
/* @__PURE__ */
|
|
3328
|
+
activeTab === "paint" && /* @__PURE__ */ jsxs14("div", { className: "flex flex-col gap-3 text-xs", children: [
|
|
3329
|
+
/* @__PURE__ */ jsx14("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Paint" }),
|
|
3330
|
+
/* @__PURE__ */ jsx14(BrushOptionsBar, { controller }),
|
|
3331
|
+
/* @__PURE__ */ jsx14(
|
|
3190
3332
|
"button",
|
|
3191
3333
|
{
|
|
3192
3334
|
type: "button",
|
|
@@ -3197,12 +3339,12 @@ var ImageEditor = ({
|
|
|
3197
3339
|
children: "Free Transform"
|
|
3198
3340
|
}
|
|
3199
3341
|
),
|
|
3200
|
-
paintError && /* @__PURE__ */
|
|
3201
|
-
/* @__PURE__ */
|
|
3342
|
+
paintError && /* @__PURE__ */ jsx14("p", { role: "alert", className: "text-rose-400", "data-testid": "paint-error", children: paintError }),
|
|
3343
|
+
/* @__PURE__ */ jsx14("div", { className: "border-t border-slate-700/60 pt-3", children: /* @__PURE__ */ jsx14(LayersPanel, { controller }) })
|
|
3202
3344
|
] }),
|
|
3203
|
-
activeTab === "annotate" && /* @__PURE__ */
|
|
3204
|
-
/* @__PURE__ */
|
|
3205
|
-
/* @__PURE__ */
|
|
3345
|
+
activeTab === "annotate" && /* @__PURE__ */ jsxs14("div", { className: "flex flex-col gap-3 text-xs", children: [
|
|
3346
|
+
/* @__PURE__ */ jsx14("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Shape & Type Layers" }),
|
|
3347
|
+
/* @__PURE__ */ jsx14("div", { className: "grid grid-cols-2 gap-1.5", children: ["shape", "type"].map((t) => /* @__PURE__ */ jsx14(
|
|
3206
3348
|
"button",
|
|
3207
3349
|
{
|
|
3208
3350
|
type: "button",
|
|
@@ -3213,13 +3355,13 @@ var ImageEditor = ({
|
|
|
3213
3355
|
},
|
|
3214
3356
|
t
|
|
3215
3357
|
)) }),
|
|
3216
|
-
state.activeTool === "shape" && /* @__PURE__ */
|
|
3217
|
-
state.activeTool === "type" && /* @__PURE__ */
|
|
3218
|
-
state.activeTool === "type" && typeSession && /* @__PURE__ */
|
|
3219
|
-
shapeTypeError && /* @__PURE__ */
|
|
3220
|
-
/* @__PURE__ */
|
|
3221
|
-
/* @__PURE__ */
|
|
3222
|
-
/* @__PURE__ */
|
|
3358
|
+
state.activeTool === "shape" && /* @__PURE__ */ jsx14(ShapeOptionsBar, { controller, options: shapeOptions, onChange: setShapeOptions }),
|
|
3359
|
+
state.activeTool === "type" && /* @__PURE__ */ jsx14(TypeOptionsBar, { controller, options: typeOptions, onChange: setTypeOptions, session: typeSession }),
|
|
3360
|
+
state.activeTool === "type" && typeSession && /* @__PURE__ */ jsx14("button", { type: "button", onClick: finishTyping, className: "self-start rounded bg-slate-800 px-2 py-1 text-[11px] text-slate-200 hover:bg-slate-700", children: "Done editing text" }),
|
|
3361
|
+
shapeTypeError && /* @__PURE__ */ jsx14("p", { role: "alert", className: "text-rose-400", "data-testid": "shape-type-error", children: shapeTypeError }),
|
|
3362
|
+
/* @__PURE__ */ jsx14("div", { className: "h-px bg-slate-800 my-1" }),
|
|
3363
|
+
/* @__PURE__ */ jsx14("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Draw & Annotate" }),
|
|
3364
|
+
/* @__PURE__ */ jsx14("div", { className: "grid grid-cols-3 gap-1.5", children: ["pen", "rect", "circle", "arrow", "line"].map((t) => /* @__PURE__ */ jsx14(
|
|
3223
3365
|
"button",
|
|
3224
3366
|
{
|
|
3225
3367
|
type: "button",
|
|
@@ -3229,9 +3371,9 @@ var ImageEditor = ({
|
|
|
3229
3371
|
},
|
|
3230
3372
|
t
|
|
3231
3373
|
)) }),
|
|
3232
|
-
/* @__PURE__ */
|
|
3233
|
-
/* @__PURE__ */
|
|
3234
|
-
/* @__PURE__ */
|
|
3374
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex items-center gap-2 mt-2", children: [
|
|
3375
|
+
/* @__PURE__ */ jsx14("label", { className: "text-slate-400", children: "Color:" }),
|
|
3376
|
+
/* @__PURE__ */ jsx14(
|
|
3235
3377
|
"input",
|
|
3236
3378
|
{
|
|
3237
3379
|
type: "color",
|
|
@@ -3240,15 +3382,15 @@ var ImageEditor = ({
|
|
|
3240
3382
|
className: "w-8 h-8 rounded border border-slate-700 cursor-pointer bg-transparent"
|
|
3241
3383
|
}
|
|
3242
3384
|
),
|
|
3243
|
-
/* @__PURE__ */
|
|
3244
|
-
/* @__PURE__ */
|
|
3245
|
-
/* @__PURE__ */
|
|
3246
|
-
/* @__PURE__ */
|
|
3385
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex-1 ml-2", children: [
|
|
3386
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex justify-between text-slate-400 mb-0.5", children: [
|
|
3387
|
+
/* @__PURE__ */ jsx14("span", { children: "Width:" }),
|
|
3388
|
+
/* @__PURE__ */ jsxs14("span", { className: "font-mono", children: [
|
|
3247
3389
|
strokeWidth,
|
|
3248
3390
|
"px"
|
|
3249
3391
|
] })
|
|
3250
3392
|
] }),
|
|
3251
|
-
/* @__PURE__ */
|
|
3393
|
+
/* @__PURE__ */ jsx14(
|
|
3252
3394
|
"input",
|
|
3253
3395
|
{
|
|
3254
3396
|
type: "range",
|
|
@@ -3261,10 +3403,10 @@ var ImageEditor = ({
|
|
|
3261
3403
|
)
|
|
3262
3404
|
] })
|
|
3263
3405
|
] }),
|
|
3264
|
-
/* @__PURE__ */
|
|
3265
|
-
/* @__PURE__ */
|
|
3266
|
-
/* @__PURE__ */
|
|
3267
|
-
/* @__PURE__ */
|
|
3406
|
+
/* @__PURE__ */ jsx14("div", { className: "h-px bg-slate-800 my-1" }),
|
|
3407
|
+
/* @__PURE__ */ jsx14("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Add Text" }),
|
|
3408
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex gap-2", children: [
|
|
3409
|
+
/* @__PURE__ */ jsx14(
|
|
3268
3410
|
"input",
|
|
3269
3411
|
{
|
|
3270
3412
|
type: "text",
|
|
@@ -3275,7 +3417,7 @@ var ImageEditor = ({
|
|
|
3275
3417
|
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"
|
|
3276
3418
|
}
|
|
3277
3419
|
),
|
|
3278
|
-
/* @__PURE__ */
|
|
3420
|
+
/* @__PURE__ */ jsx14(
|
|
3279
3421
|
"button",
|
|
3280
3422
|
{
|
|
3281
3423
|
type: "button",
|
|
@@ -3285,14 +3427,14 @@ var ImageEditor = ({
|
|
|
3285
3427
|
}
|
|
3286
3428
|
)
|
|
3287
3429
|
] }),
|
|
3288
|
-
/* @__PURE__ */
|
|
3289
|
-
/* @__PURE__ */
|
|
3290
|
-
/* @__PURE__ */
|
|
3430
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex items-center justify-between text-slate-400", children: [
|
|
3431
|
+
/* @__PURE__ */ jsx14("span", { children: "Font Size:" }),
|
|
3432
|
+
/* @__PURE__ */ jsxs14("span", { className: "font-mono", children: [
|
|
3291
3433
|
fontSize,
|
|
3292
3434
|
"px"
|
|
3293
3435
|
] })
|
|
3294
3436
|
] }),
|
|
3295
|
-
/* @__PURE__ */
|
|
3437
|
+
/* @__PURE__ */ jsx14(
|
|
3296
3438
|
"input",
|
|
3297
3439
|
{
|
|
3298
3440
|
type: "range",
|
|
@@ -3303,14 +3445,14 @@ var ImageEditor = ({
|
|
|
3303
3445
|
className: "w-full accent-indigo-500"
|
|
3304
3446
|
}
|
|
3305
3447
|
),
|
|
3306
|
-
/* @__PURE__ */
|
|
3307
|
-
/* @__PURE__ */
|
|
3308
|
-
/* @__PURE__ */
|
|
3448
|
+
/* @__PURE__ */ jsx14("div", { className: "h-px bg-slate-800 my-1" }),
|
|
3449
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex items-center justify-between", children: [
|
|
3450
|
+
/* @__PURE__ */ jsxs14("span", { className: "text-slate-400", children: [
|
|
3309
3451
|
"Layers (",
|
|
3310
3452
|
state.annotations.length,
|
|
3311
3453
|
")"
|
|
3312
3454
|
] }),
|
|
3313
|
-
state.selectedAnnotationId && /* @__PURE__ */
|
|
3455
|
+
state.selectedAnnotationId && /* @__PURE__ */ jsx14(
|
|
3314
3456
|
"button",
|
|
3315
3457
|
{
|
|
3316
3458
|
type: "button",
|
|
@@ -3319,7 +3461,7 @@ var ImageEditor = ({
|
|
|
3319
3461
|
children: "Delete Selected"
|
|
3320
3462
|
}
|
|
3321
3463
|
),
|
|
3322
|
-
state.annotations.length > 0 && /* @__PURE__ */
|
|
3464
|
+
state.annotations.length > 0 && /* @__PURE__ */ jsx14(
|
|
3323
3465
|
"button",
|
|
3324
3466
|
{
|
|
3325
3467
|
type: "button",
|
|
@@ -3330,10 +3472,10 @@ var ImageEditor = ({
|
|
|
3330
3472
|
)
|
|
3331
3473
|
] })
|
|
3332
3474
|
] }),
|
|
3333
|
-
activeTab === "depth" && /* @__PURE__ */
|
|
3334
|
-
/* @__PURE__ */
|
|
3335
|
-
/* @__PURE__ */
|
|
3336
|
-
/* @__PURE__ */
|
|
3475
|
+
activeTab === "depth" && /* @__PURE__ */ jsxs14("div", { className: "flex flex-col gap-3 text-xs", children: [
|
|
3476
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex items-center justify-between", children: [
|
|
3477
|
+
/* @__PURE__ */ jsx14("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px]", children: "Depth Masking" }),
|
|
3478
|
+
/* @__PURE__ */ jsx14(
|
|
3337
3479
|
"button",
|
|
3338
3480
|
{
|
|
3339
3481
|
type: "button",
|
|
@@ -3343,8 +3485,8 @@ var ImageEditor = ({
|
|
|
3343
3485
|
}
|
|
3344
3486
|
)
|
|
3345
3487
|
] }),
|
|
3346
|
-
/* @__PURE__ */
|
|
3347
|
-
/* @__PURE__ */
|
|
3488
|
+
/* @__PURE__ */ jsxs14("label", { className: "flex items-center gap-2 cursor-pointer text-slate-300", children: [
|
|
3489
|
+
/* @__PURE__ */ jsx14(
|
|
3348
3490
|
"input",
|
|
3349
3491
|
{
|
|
3350
3492
|
type: "checkbox",
|
|
@@ -3353,12 +3495,12 @@ var ImageEditor = ({
|
|
|
3353
3495
|
className: "rounded accent-indigo-500"
|
|
3354
3496
|
}
|
|
3355
3497
|
),
|
|
3356
|
-
/* @__PURE__ */
|
|
3498
|
+
/* @__PURE__ */ jsx14("span", { children: "Enable Depth / Alpha Mask" })
|
|
3357
3499
|
] }),
|
|
3358
|
-
state.depthMask.enabled && /* @__PURE__ */
|
|
3359
|
-
/* @__PURE__ */
|
|
3360
|
-
/* @__PURE__ */
|
|
3361
|
-
/* @__PURE__ */
|
|
3500
|
+
state.depthMask.enabled && /* @__PURE__ */ jsxs14(Fragment5, { children: [
|
|
3501
|
+
/* @__PURE__ */ jsxs14("div", { children: [
|
|
3502
|
+
/* @__PURE__ */ jsx14("label", { className: "text-slate-400 block mb-1", children: "Mask Image URL:" }),
|
|
3503
|
+
/* @__PURE__ */ jsx14(
|
|
3362
3504
|
"input",
|
|
3363
3505
|
{
|
|
3364
3506
|
type: "text",
|
|
@@ -3369,8 +3511,8 @@ var ImageEditor = ({
|
|
|
3369
3511
|
}
|
|
3370
3512
|
)
|
|
3371
3513
|
] }),
|
|
3372
|
-
/* @__PURE__ */
|
|
3373
|
-
/* @__PURE__ */
|
|
3514
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex gap-2", children: [
|
|
3515
|
+
/* @__PURE__ */ jsx14(
|
|
3374
3516
|
"button",
|
|
3375
3517
|
{
|
|
3376
3518
|
type: "button",
|
|
@@ -3379,7 +3521,7 @@ var ImageEditor = ({
|
|
|
3379
3521
|
children: "Threshold Mode"
|
|
3380
3522
|
}
|
|
3381
3523
|
),
|
|
3382
|
-
/* @__PURE__ */
|
|
3524
|
+
/* @__PURE__ */ jsx14(
|
|
3383
3525
|
"button",
|
|
3384
3526
|
{
|
|
3385
3527
|
type: "button",
|
|
@@ -3389,12 +3531,12 @@ var ImageEditor = ({
|
|
|
3389
3531
|
}
|
|
3390
3532
|
)
|
|
3391
3533
|
] }),
|
|
3392
|
-
/* @__PURE__ */
|
|
3393
|
-
/* @__PURE__ */
|
|
3394
|
-
/* @__PURE__ */
|
|
3395
|
-
/* @__PURE__ */
|
|
3534
|
+
/* @__PURE__ */ jsxs14("div", { children: [
|
|
3535
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex justify-between text-slate-400 mb-1", children: [
|
|
3536
|
+
/* @__PURE__ */ jsx14("span", { children: "Depth Start (Lower):" }),
|
|
3537
|
+
/* @__PURE__ */ jsx14("span", { className: "font-mono", children: state.depthMask.depthRange[0] })
|
|
3396
3538
|
] }),
|
|
3397
|
-
/* @__PURE__ */
|
|
3539
|
+
/* @__PURE__ */ jsx14(
|
|
3398
3540
|
"input",
|
|
3399
3541
|
{
|
|
3400
3542
|
type: "range",
|
|
@@ -3408,12 +3550,12 @@ var ImageEditor = ({
|
|
|
3408
3550
|
}
|
|
3409
3551
|
)
|
|
3410
3552
|
] }),
|
|
3411
|
-
/* @__PURE__ */
|
|
3412
|
-
/* @__PURE__ */
|
|
3413
|
-
/* @__PURE__ */
|
|
3414
|
-
/* @__PURE__ */
|
|
3553
|
+
/* @__PURE__ */ jsxs14("div", { children: [
|
|
3554
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex justify-between text-slate-400 mb-1", children: [
|
|
3555
|
+
/* @__PURE__ */ jsx14("span", { children: "Depth Stop (Upper):" }),
|
|
3556
|
+
/* @__PURE__ */ jsx14("span", { className: "font-mono", children: state.depthMask.depthRange[1] })
|
|
3415
3557
|
] }),
|
|
3416
|
-
/* @__PURE__ */
|
|
3558
|
+
/* @__PURE__ */ jsx14(
|
|
3417
3559
|
"input",
|
|
3418
3560
|
{
|
|
3419
3561
|
type: "range",
|
|
@@ -3427,12 +3569,12 @@ var ImageEditor = ({
|
|
|
3427
3569
|
}
|
|
3428
3570
|
)
|
|
3429
3571
|
] }),
|
|
3430
|
-
/* @__PURE__ */
|
|
3431
|
-
/* @__PURE__ */
|
|
3432
|
-
/* @__PURE__ */
|
|
3433
|
-
/* @__PURE__ */
|
|
3572
|
+
/* @__PURE__ */ jsxs14("div", { children: [
|
|
3573
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex justify-between text-slate-400 mb-1", children: [
|
|
3574
|
+
/* @__PURE__ */ jsx14("span", { children: "Softness:" }),
|
|
3575
|
+
/* @__PURE__ */ jsx14("span", { className: "font-mono", children: state.depthMask.softness })
|
|
3434
3576
|
] }),
|
|
3435
|
-
/* @__PURE__ */
|
|
3577
|
+
/* @__PURE__ */ jsx14(
|
|
3436
3578
|
"input",
|
|
3437
3579
|
{
|
|
3438
3580
|
type: "range",
|
|
@@ -3444,8 +3586,8 @@ var ImageEditor = ({
|
|
|
3444
3586
|
}
|
|
3445
3587
|
)
|
|
3446
3588
|
] }),
|
|
3447
|
-
/* @__PURE__ */
|
|
3448
|
-
/* @__PURE__ */
|
|
3589
|
+
/* @__PURE__ */ jsxs14("label", { className: "flex items-center gap-2 cursor-pointer text-slate-300 mt-1", children: [
|
|
3590
|
+
/* @__PURE__ */ jsx14(
|
|
3449
3591
|
"input",
|
|
3450
3592
|
{
|
|
3451
3593
|
type: "checkbox",
|
|
@@ -3454,12 +3596,12 @@ var ImageEditor = ({
|
|
|
3454
3596
|
className: "rounded accent-indigo-500"
|
|
3455
3597
|
}
|
|
3456
3598
|
),
|
|
3457
|
-
/* @__PURE__ */
|
|
3599
|
+
/* @__PURE__ */ jsx14("span", { children: "Invert Mask" })
|
|
3458
3600
|
] })
|
|
3459
3601
|
] })
|
|
3460
3602
|
] }),
|
|
3461
|
-
activeTab === "select" && /* @__PURE__ */
|
|
3462
|
-
/* @__PURE__ */
|
|
3603
|
+
activeTab === "select" && /* @__PURE__ */ jsxs14("div", { className: "flex flex-col gap-4 text-xs", children: [
|
|
3604
|
+
/* @__PURE__ */ jsx14(
|
|
3463
3605
|
SelectionOptionsBar,
|
|
3464
3606
|
{
|
|
3465
3607
|
controller,
|
|
@@ -3469,9 +3611,9 @@ var ImageEditor = ({
|
|
|
3469
3611
|
quickMask: Boolean(state.quickMask)
|
|
3470
3612
|
}
|
|
3471
3613
|
),
|
|
3472
|
-
selectionError && /* @__PURE__ */
|
|
3473
|
-
/* @__PURE__ */
|
|
3474
|
-
/* @__PURE__ */
|
|
3614
|
+
selectionError && /* @__PURE__ */ jsx14("p", { role: "alert", className: "text-rose-400", children: selectionError }),
|
|
3615
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex gap-1", children: [
|
|
3616
|
+
/* @__PURE__ */ jsx14(
|
|
3475
3617
|
"button",
|
|
3476
3618
|
{
|
|
3477
3619
|
type: "button",
|
|
@@ -3482,7 +3624,7 @@ var ImageEditor = ({
|
|
|
3482
3624
|
children: "Transform Selection"
|
|
3483
3625
|
}
|
|
3484
3626
|
),
|
|
3485
|
-
/* @__PURE__ */
|
|
3627
|
+
/* @__PURE__ */ jsx14(
|
|
3486
3628
|
"button",
|
|
3487
3629
|
{
|
|
3488
3630
|
type: "button",
|
|
@@ -3494,12 +3636,12 @@ var ImageEditor = ({
|
|
|
3494
3636
|
}
|
|
3495
3637
|
)
|
|
3496
3638
|
] }),
|
|
3497
|
-
/* @__PURE__ */
|
|
3639
|
+
/* @__PURE__ */ jsx14(RefineEdgePanel, { controller, selection: state.selection ?? null, layers: state.adjustments.layers })
|
|
3498
3640
|
] }),
|
|
3499
|
-
activeTab === "ai" && /* @__PURE__ */
|
|
3500
|
-
/* @__PURE__ */
|
|
3501
|
-
/* @__PURE__ */
|
|
3502
|
-
/* @__PURE__ */
|
|
3641
|
+
activeTab === "ai" && /* @__PURE__ */ jsxs14("div", { className: "flex flex-col gap-4 text-xs", children: [
|
|
3642
|
+
/* @__PURE__ */ jsxs14("label", { className: "flex items-center justify-between gap-2 text-slate-300", children: [
|
|
3643
|
+
/* @__PURE__ */ jsx14("span", { children: "Results go to" }),
|
|
3644
|
+
/* @__PURE__ */ jsxs14(
|
|
3503
3645
|
"select",
|
|
3504
3646
|
{
|
|
3505
3647
|
"aria-label": "AI result target",
|
|
@@ -3507,54 +3649,54 @@ var ImageEditor = ({
|
|
|
3507
3649
|
onChange: (e) => setAiTarget(e.target.value),
|
|
3508
3650
|
className: "bg-slate-800 border border-slate-700 rounded px-1.5 py-1",
|
|
3509
3651
|
children: [
|
|
3510
|
-
/* @__PURE__ */
|
|
3511
|
-
/* @__PURE__ */
|
|
3512
|
-
/* @__PURE__ */
|
|
3652
|
+
/* @__PURE__ */ jsx14("option", { value: "auto", children: controller.isMultiLayer ? "Auto (new layer)" : "Auto (replace image)" }),
|
|
3653
|
+
/* @__PURE__ */ jsx14("option", { value: "new-layer", children: "New layer / mask" }),
|
|
3654
|
+
/* @__PURE__ */ jsx14("option", { value: "replace", children: "Replace image" })
|
|
3513
3655
|
]
|
|
3514
3656
|
}
|
|
3515
3657
|
)
|
|
3516
3658
|
] }),
|
|
3517
|
-
/* @__PURE__ */
|
|
3518
|
-
/* @__PURE__ */
|
|
3519
|
-
/* @__PURE__ */
|
|
3520
|
-
/* @__PURE__ */
|
|
3659
|
+
/* @__PURE__ */ jsxs14("div", { className: "p-3 rounded-lg bg-slate-950/60 border border-slate-800 flex flex-col gap-2.5", children: [
|
|
3660
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex items-center justify-between", children: [
|
|
3661
|
+
/* @__PURE__ */ jsxs14("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px] flex items-center gap-1.5", children: [
|
|
3662
|
+
/* @__PURE__ */ jsx14("svg", { className: "w-3.5 h-3.5 text-indigo-400", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: /* @__PURE__ */ jsx14("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" }) }),
|
|
3521
3663
|
"Background Removal"
|
|
3522
3664
|
] }),
|
|
3523
|
-
isRemovingBg && /* @__PURE__ */
|
|
3665
|
+
isRemovingBg && /* @__PURE__ */ jsx14("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..." })
|
|
3524
3666
|
] }),
|
|
3525
|
-
/* @__PURE__ */
|
|
3526
|
-
/* @__PURE__ */
|
|
3667
|
+
/* @__PURE__ */ jsx14("p", { className: "text-slate-400 text-[11px] leading-relaxed", children: "Isolate foreground subject with AI alpha transparency segmentation." }),
|
|
3668
|
+
/* @__PURE__ */ jsx14(
|
|
3527
3669
|
"button",
|
|
3528
3670
|
{
|
|
3529
3671
|
type: "button",
|
|
3530
3672
|
onClick: handleRemoveBackground,
|
|
3531
3673
|
disabled: isRemovingBg || isInpainting,
|
|
3532
3674
|
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",
|
|
3533
|
-
children: isRemovingBg ? /* @__PURE__ */
|
|
3534
|
-
/* @__PURE__ */
|
|
3675
|
+
children: isRemovingBg ? /* @__PURE__ */ jsxs14(Fragment5, { children: [
|
|
3676
|
+
/* @__PURE__ */ jsx14("div", { className: "w-3.5 h-3.5 border-2 border-white/30 border-t-white rounded-full animate-spin" }),
|
|
3535
3677
|
"Removing Background..."
|
|
3536
|
-
] }) : /* @__PURE__ */
|
|
3537
|
-
/* @__PURE__ */
|
|
3678
|
+
] }) : /* @__PURE__ */ jsxs14(Fragment5, { children: [
|
|
3679
|
+
/* @__PURE__ */ jsx14("svg", { className: "w-3.5 h-3.5", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: /* @__PURE__ */ jsx14("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" }) }),
|
|
3538
3680
|
"Remove Background"
|
|
3539
3681
|
] })
|
|
3540
3682
|
}
|
|
3541
3683
|
)
|
|
3542
3684
|
] }),
|
|
3543
|
-
/* @__PURE__ */
|
|
3544
|
-
/* @__PURE__ */
|
|
3545
|
-
/* @__PURE__ */
|
|
3546
|
-
/* @__PURE__ */
|
|
3547
|
-
/* @__PURE__ */
|
|
3548
|
-
/* @__PURE__ */
|
|
3685
|
+
/* @__PURE__ */ jsxs14("div", { className: "p-3 rounded-lg bg-slate-950/60 border border-slate-800 flex flex-col gap-2.5", children: [
|
|
3686
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex items-center justify-between", children: [
|
|
3687
|
+
/* @__PURE__ */ jsxs14("span", { className: "font-semibold text-slate-200 uppercase tracking-wider text-[11px] flex items-center gap-1.5", children: [
|
|
3688
|
+
/* @__PURE__ */ jsxs14("svg", { className: "w-3.5 h-3.5 text-purple-400", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: [
|
|
3689
|
+
/* @__PURE__ */ jsx14("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" }),
|
|
3690
|
+
/* @__PURE__ */ jsx14("path", { d: "m14 7 3 3" })
|
|
3549
3691
|
] }),
|
|
3550
3692
|
"Generative Inpainting"
|
|
3551
3693
|
] }),
|
|
3552
|
-
isInpainting && /* @__PURE__ */
|
|
3694
|
+
isInpainting && /* @__PURE__ */ jsx14("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..." })
|
|
3553
3695
|
] }),
|
|
3554
|
-
/* @__PURE__ */
|
|
3555
|
-
/* @__PURE__ */
|
|
3556
|
-
/* @__PURE__ */
|
|
3557
|
-
/* @__PURE__ */
|
|
3696
|
+
/* @__PURE__ */ jsx14("p", { className: "text-slate-400 text-[11px] leading-relaxed", children: "Replace, modify, or fill selected regions using prompt-guided generative inpainting." }),
|
|
3697
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex flex-col gap-1", children: [
|
|
3698
|
+
/* @__PURE__ */ jsx14("label", { htmlFor: "ai-inpaint-prompt-react", className: "text-slate-300 text-[11px] font-medium", children: "Prompt" }),
|
|
3699
|
+
/* @__PURE__ */ jsx14(
|
|
3558
3700
|
"textarea",
|
|
3559
3701
|
{
|
|
3560
3702
|
id: "ai-inpaint-prompt-react",
|
|
@@ -3566,10 +3708,10 @@ var ImageEditor = ({
|
|
|
3566
3708
|
}
|
|
3567
3709
|
)
|
|
3568
3710
|
] }),
|
|
3569
|
-
/* @__PURE__ */
|
|
3570
|
-
/* @__PURE__ */
|
|
3571
|
-
/* @__PURE__ */
|
|
3572
|
-
/* @__PURE__ */
|
|
3711
|
+
/* @__PURE__ */ jsxs14("div", { className: "flex flex-col gap-1", children: [
|
|
3712
|
+
/* @__PURE__ */ jsx14("span", { className: "text-slate-300 text-[11px] font-medium", children: "Target Mask Region" }),
|
|
3713
|
+
/* @__PURE__ */ jsxs14("div", { className: "grid grid-cols-2 gap-1.5", children: [
|
|
3714
|
+
/* @__PURE__ */ jsxs14(
|
|
3573
3715
|
"button",
|
|
3574
3716
|
{
|
|
3575
3717
|
type: "button",
|
|
@@ -3582,7 +3724,7 @@ var ImageEditor = ({
|
|
|
3582
3724
|
]
|
|
3583
3725
|
}
|
|
3584
3726
|
),
|
|
3585
|
-
/* @__PURE__ */
|
|
3727
|
+
/* @__PURE__ */ jsxs14(
|
|
3586
3728
|
"button",
|
|
3587
3729
|
{
|
|
3588
3730
|
type: "button",
|
|
@@ -3597,25 +3739,25 @@ var ImageEditor = ({
|
|
|
3597
3739
|
)
|
|
3598
3740
|
] })
|
|
3599
3741
|
] }),
|
|
3600
|
-
/* @__PURE__ */
|
|
3742
|
+
/* @__PURE__ */ jsx14(
|
|
3601
3743
|
"button",
|
|
3602
3744
|
{
|
|
3603
3745
|
type: "button",
|
|
3604
3746
|
onClick: handleInpaint,
|
|
3605
3747
|
disabled: isInpainting || isRemovingBg || !inpaintPrompt.trim(),
|
|
3606
3748
|
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",
|
|
3607
|
-
children: isInpainting ? /* @__PURE__ */
|
|
3608
|
-
/* @__PURE__ */
|
|
3749
|
+
children: isInpainting ? /* @__PURE__ */ jsxs14(Fragment5, { children: [
|
|
3750
|
+
/* @__PURE__ */ jsx14("div", { className: "w-3.5 h-3.5 border-2 border-white/30 border-t-white rounded-full animate-spin" }),
|
|
3609
3751
|
"Generating Inpaint..."
|
|
3610
|
-
] }) : /* @__PURE__ */
|
|
3611
|
-
/* @__PURE__ */
|
|
3752
|
+
] }) : /* @__PURE__ */ jsxs14(Fragment5, { children: [
|
|
3753
|
+
/* @__PURE__ */ jsx14("svg", { className: "w-3.5 h-3.5", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", children: /* @__PURE__ */ jsx14("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" }) }),
|
|
3612
3754
|
"Apply Inpainting"
|
|
3613
3755
|
] })
|
|
3614
3756
|
}
|
|
3615
3757
|
)
|
|
3616
3758
|
] }),
|
|
3617
|
-
aiError && /* @__PURE__ */
|
|
3618
|
-
aiSuccess && /* @__PURE__ */
|
|
3759
|
+
aiError && /* @__PURE__ */ jsx14("div", { className: "p-2.5 rounded-lg bg-rose-950/60 border border-rose-800 text-rose-300 text-[11px]", children: aiError }),
|
|
3760
|
+
aiSuccess && /* @__PURE__ */ jsx14("div", { className: "p-2.5 rounded-lg bg-emerald-950/60 border border-emerald-800 text-emerald-300 text-[11px]", children: aiSuccess })
|
|
3619
3761
|
] })
|
|
3620
3762
|
] })
|
|
3621
3763
|
] })
|
|
@@ -3634,6 +3776,7 @@ export {
|
|
|
3634
3776
|
LayerEffectsPanel,
|
|
3635
3777
|
LayersPanel,
|
|
3636
3778
|
BrushOptionsBar,
|
|
3779
|
+
ColorProfilePanel,
|
|
3637
3780
|
SelectionOptionsBar,
|
|
3638
3781
|
RefineEdgePanel,
|
|
3639
3782
|
FreeTransformOptionsBar,
|
|
@@ -3641,4 +3784,4 @@ export {
|
|
|
3641
3784
|
TypeOptionsBar,
|
|
3642
3785
|
ImageEditor
|
|
3643
3786
|
};
|
|
3644
|
-
//# sourceMappingURL=chunk-
|
|
3787
|
+
//# sourceMappingURL=chunk-VNZKHFEM.js.map
|