@twick/studio 0.15.12 → 0.15.14
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/components/panel/text-panel.d.ts +1 -1
- package/dist/hooks/use-text-panel.d.ts +6 -0
- package/dist/index.js +200 -58
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +200 -58
- package/dist/index.mjs.map +1 -1
- package/dist/studio.css +4 -0
- package/package.json +12 -12
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import { TextPanelState, TextPanelActions } from '../../hooks/use-text-panel';
|
|
2
2
|
|
|
3
3
|
export type TextPanelProps = TextPanelState & TextPanelActions;
|
|
4
|
-
export declare function TextPanel({ textContent, fontSize, selectedFont, isBold, isItalic, textColor, strokeColor, applyShadow, shadowColor, strokeWidth, fonts, operation, setTextContent, setFontSize, setSelectedFont, setIsBold, setIsItalic, setTextColor, setStrokeColor, setApplyShadow, setShadowColor, setStrokeWidth, handleApplyChanges, }: TextPanelProps): import("react/jsx-runtime").JSX.Element;
|
|
4
|
+
export declare function TextPanel({ textContent, fontSize, selectedFont, isBold, isItalic, textColor, strokeColor, applyShadow, shadowColor, strokeWidth, applyBackground, backgroundColor, backgroundOpacity, fonts, operation, setTextContent, setFontSize, setSelectedFont, setIsBold, setIsItalic, setTextColor, setStrokeColor, setApplyShadow, setShadowColor, setStrokeWidth, setApplyBackground, setBackgroundColor, setBackgroundOpacity, handleApplyChanges, }: TextPanelProps): import("react/jsx-runtime").JSX.Element;
|
|
@@ -27,6 +27,9 @@ export interface TextPanelState {
|
|
|
27
27
|
applyShadow: boolean;
|
|
28
28
|
shadowColor: string;
|
|
29
29
|
strokeWidth: number;
|
|
30
|
+
applyBackground: boolean;
|
|
31
|
+
backgroundColor: string;
|
|
32
|
+
backgroundOpacity: number;
|
|
30
33
|
fonts: string[];
|
|
31
34
|
operation: string;
|
|
32
35
|
}
|
|
@@ -41,6 +44,9 @@ export interface TextPanelActions {
|
|
|
41
44
|
setApplyShadow: (shadow: boolean) => void;
|
|
42
45
|
setShadowColor: (color: string) => void;
|
|
43
46
|
setStrokeWidth: (width: number) => void;
|
|
47
|
+
setApplyBackground: (apply: boolean) => void;
|
|
48
|
+
setBackgroundColor: (color: string) => void;
|
|
49
|
+
setBackgroundOpacity: (opacity: number) => void;
|
|
44
50
|
handleApplyChanges: () => void;
|
|
45
51
|
}
|
|
46
52
|
export declare const useTextPanel: ({ selectedElement, addElement, updateElement, }: {
|
package/dist/index.js
CHANGED
|
@@ -113,49 +113,49 @@ const createLucideIcon = (iconName, iconNode) => {
|
|
|
113
113
|
* This source code is licensed under the ISC license.
|
|
114
114
|
* See the LICENSE file in the root directory of this source tree.
|
|
115
115
|
*/
|
|
116
|
-
const __iconNode$
|
|
116
|
+
const __iconNode$u = [
|
|
117
117
|
["rect", { width: "18", height: "14", x: "3", y: "5", rx: "2", ry: "2", key: "12ruh7" }],
|
|
118
118
|
["path", { d: "M7 15h4M15 15h2M7 11h2M13 11h4", key: "1ueiar" }]
|
|
119
119
|
];
|
|
120
|
-
const Captions = createLucideIcon("captions", __iconNode$
|
|
120
|
+
const Captions = createLucideIcon("captions", __iconNode$u);
|
|
121
121
|
/**
|
|
122
122
|
* @license lucide-react v0.511.0 - ISC
|
|
123
123
|
*
|
|
124
124
|
* This source code is licensed under the ISC license.
|
|
125
125
|
* See the LICENSE file in the root directory of this source tree.
|
|
126
126
|
*/
|
|
127
|
-
const __iconNode$
|
|
127
|
+
const __iconNode$t = [
|
|
128
128
|
["circle", { cx: "12", cy: "12", r: "10", key: "1mglay" }],
|
|
129
129
|
["path", { d: "m9 12 2 2 4-4", key: "dzmm74" }]
|
|
130
130
|
];
|
|
131
|
-
const CircleCheck = createLucideIcon("circle-check", __iconNode$
|
|
131
|
+
const CircleCheck = createLucideIcon("circle-check", __iconNode$t);
|
|
132
132
|
/**
|
|
133
133
|
* @license lucide-react v0.511.0 - ISC
|
|
134
134
|
*
|
|
135
135
|
* This source code is licensed under the ISC license.
|
|
136
136
|
* See the LICENSE file in the root directory of this source tree.
|
|
137
137
|
*/
|
|
138
|
-
const __iconNode$
|
|
138
|
+
const __iconNode$s = [
|
|
139
139
|
["circle", { cx: "12", cy: "12", r: "10", key: "1mglay" }],
|
|
140
140
|
["path", { d: "m15 9-6 6", key: "1uzhvr" }],
|
|
141
141
|
["path", { d: "m9 9 6 6", key: "z0biqf" }]
|
|
142
142
|
];
|
|
143
|
-
const CircleX = createLucideIcon("circle-x", __iconNode$
|
|
143
|
+
const CircleX = createLucideIcon("circle-x", __iconNode$s);
|
|
144
144
|
/**
|
|
145
145
|
* @license lucide-react v0.511.0 - ISC
|
|
146
146
|
*
|
|
147
147
|
* This source code is licensed under the ISC license.
|
|
148
148
|
* See the LICENSE file in the root directory of this source tree.
|
|
149
149
|
*/
|
|
150
|
-
const __iconNode$
|
|
151
|
-
const Circle = createLucideIcon("circle", __iconNode$
|
|
150
|
+
const __iconNode$r = [["circle", { cx: "12", cy: "12", r: "10", key: "1mglay" }]];
|
|
151
|
+
const Circle = createLucideIcon("circle", __iconNode$r);
|
|
152
152
|
/**
|
|
153
153
|
* @license lucide-react v0.511.0 - ISC
|
|
154
154
|
*
|
|
155
155
|
* This source code is licensed under the ISC license.
|
|
156
156
|
* See the LICENSE file in the root directory of this source tree.
|
|
157
157
|
*/
|
|
158
|
-
const __iconNode$
|
|
158
|
+
const __iconNode$q = [
|
|
159
159
|
[
|
|
160
160
|
"path",
|
|
161
161
|
{ d: "M20.2 6 3 11l-.9-2.4c-.3-1.1.3-2.2 1.3-2.5l13.5-4c1.1-.3 2.2.3 2.5 1.3Z", key: "1tn4o7" }
|
|
@@ -164,112 +164,132 @@ const __iconNode$o = [
|
|
|
164
164
|
["path", { d: "m12.4 3.4 3.1 4", key: "6hsd6n" }],
|
|
165
165
|
["path", { d: "M3 11h18v8a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2Z", key: "ltgou9" }]
|
|
166
166
|
];
|
|
167
|
-
const Clapperboard = createLucideIcon("clapperboard", __iconNode$
|
|
167
|
+
const Clapperboard = createLucideIcon("clapperboard", __iconNode$q);
|
|
168
168
|
/**
|
|
169
169
|
* @license lucide-react v0.511.0 - ISC
|
|
170
170
|
*
|
|
171
171
|
* This source code is licensed under the ISC license.
|
|
172
172
|
* See the LICENSE file in the root directory of this source tree.
|
|
173
173
|
*/
|
|
174
|
-
const __iconNode$
|
|
174
|
+
const __iconNode$p = [
|
|
175
175
|
["path", { d: "M12 15V3", key: "m9g1x1" }],
|
|
176
176
|
["path", { d: "M21 15v4a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2v-4", key: "ih7n3h" }],
|
|
177
177
|
["path", { d: "m7 10 5 5 5-5", key: "brsn70" }]
|
|
178
178
|
];
|
|
179
|
-
const Download = createLucideIcon("download", __iconNode$
|
|
179
|
+
const Download = createLucideIcon("download", __iconNode$p);
|
|
180
180
|
/**
|
|
181
181
|
* @license lucide-react v0.511.0 - ISC
|
|
182
182
|
*
|
|
183
183
|
* This source code is licensed under the ISC license.
|
|
184
184
|
* See the LICENSE file in the root directory of this source tree.
|
|
185
185
|
*/
|
|
186
|
-
const __iconNode$
|
|
186
|
+
const __iconNode$o = [
|
|
187
187
|
["path", { d: "M15 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V7Z", key: "1rqfz7" }],
|
|
188
188
|
["path", { d: "M14 2v4a2 2 0 0 0 2 2h4", key: "tnqrlb" }]
|
|
189
189
|
];
|
|
190
|
-
const File = createLucideIcon("file", __iconNode$
|
|
190
|
+
const File = createLucideIcon("file", __iconNode$o);
|
|
191
191
|
/**
|
|
192
192
|
* @license lucide-react v0.511.0 - ISC
|
|
193
193
|
*
|
|
194
194
|
* This source code is licensed under the ISC license.
|
|
195
195
|
* See the LICENSE file in the root directory of this source tree.
|
|
196
196
|
*/
|
|
197
|
-
const __iconNode$
|
|
197
|
+
const __iconNode$n = [
|
|
198
198
|
["rect", { width: "18", height: "18", x: "3", y: "3", rx: "2", ry: "2", key: "1m3agn" }],
|
|
199
199
|
["circle", { cx: "9", cy: "9", r: "2", key: "af1f0g" }],
|
|
200
200
|
["path", { d: "m21 15-3.086-3.086a2 2 0 0 0-2.828 0L6 21", key: "1xmnt7" }]
|
|
201
201
|
];
|
|
202
|
-
const Image = createLucideIcon("image", __iconNode$
|
|
202
|
+
const Image = createLucideIcon("image", __iconNode$n);
|
|
203
203
|
/**
|
|
204
204
|
* @license lucide-react v0.511.0 - ISC
|
|
205
205
|
*
|
|
206
206
|
* This source code is licensed under the ISC license.
|
|
207
207
|
* See the LICENSE file in the root directory of this source tree.
|
|
208
208
|
*/
|
|
209
|
-
const __iconNode$
|
|
209
|
+
const __iconNode$m = [
|
|
210
210
|
["path", { d: "M6 16c5 0 7-8 12-8a4 4 0 0 1 0 8c-5 0-7-8-12-8a4 4 0 1 0 0 8", key: "18ogeb" }]
|
|
211
211
|
];
|
|
212
|
-
const Infinity = createLucideIcon("infinity", __iconNode$
|
|
212
|
+
const Infinity = createLucideIcon("infinity", __iconNode$m);
|
|
213
213
|
/**
|
|
214
214
|
* @license lucide-react v0.511.0 - ISC
|
|
215
215
|
*
|
|
216
216
|
* This source code is licensed under the ISC license.
|
|
217
217
|
* See the LICENSE file in the root directory of this source tree.
|
|
218
218
|
*/
|
|
219
|
-
const __iconNode$
|
|
220
|
-
const LoaderCircle = createLucideIcon("loader-circle", __iconNode$
|
|
219
|
+
const __iconNode$l = [["path", { d: "M21 12a9 9 0 1 1-6.219-8.56", key: "13zald" }]];
|
|
220
|
+
const LoaderCircle = createLucideIcon("loader-circle", __iconNode$l);
|
|
221
221
|
/**
|
|
222
222
|
* @license lucide-react v0.511.0 - ISC
|
|
223
223
|
*
|
|
224
224
|
* This source code is licensed under the ISC license.
|
|
225
225
|
* See the LICENSE file in the root directory of this source tree.
|
|
226
226
|
*/
|
|
227
|
-
const __iconNode$
|
|
227
|
+
const __iconNode$k = [
|
|
228
228
|
["path", { d: "M21 15a2 2 0 0 1-2 2H7l-4 4V5a2 2 0 0 1 2-2h14a2 2 0 0 1 2 2z", key: "1lielz" }]
|
|
229
229
|
];
|
|
230
|
-
const MessageSquare = createLucideIcon("message-square", __iconNode$
|
|
230
|
+
const MessageSquare = createLucideIcon("message-square", __iconNode$k);
|
|
231
231
|
/**
|
|
232
232
|
* @license lucide-react v0.511.0 - ISC
|
|
233
233
|
*
|
|
234
234
|
* This source code is licensed under the ISC license.
|
|
235
235
|
* See the LICENSE file in the root directory of this source tree.
|
|
236
236
|
*/
|
|
237
|
-
const __iconNode$
|
|
237
|
+
const __iconNode$j = [
|
|
238
238
|
["path", { d: "M9 18V5l12-2v13", key: "1jmyc2" }],
|
|
239
239
|
["circle", { cx: "6", cy: "18", r: "3", key: "fqmcym" }],
|
|
240
240
|
["circle", { cx: "18", cy: "16", r: "3", key: "1hluhg" }]
|
|
241
241
|
];
|
|
242
|
-
const Music = createLucideIcon("music", __iconNode$
|
|
242
|
+
const Music = createLucideIcon("music", __iconNode$j);
|
|
243
243
|
/**
|
|
244
244
|
* @license lucide-react v0.511.0 - ISC
|
|
245
245
|
*
|
|
246
246
|
* This source code is licensed under the ISC license.
|
|
247
247
|
* See the LICENSE file in the root directory of this source tree.
|
|
248
248
|
*/
|
|
249
|
-
const __iconNode$
|
|
249
|
+
const __iconNode$i = [
|
|
250
250
|
["rect", { x: "14", y: "4", width: "4", height: "16", rx: "1", key: "zuxfzm" }],
|
|
251
251
|
["rect", { x: "6", y: "4", width: "4", height: "16", rx: "1", key: "1okwgv" }]
|
|
252
252
|
];
|
|
253
|
-
const Pause = createLucideIcon("pause", __iconNode$
|
|
253
|
+
const Pause = createLucideIcon("pause", __iconNode$i);
|
|
254
254
|
/**
|
|
255
255
|
* @license lucide-react v0.511.0 - ISC
|
|
256
256
|
*
|
|
257
257
|
* This source code is licensed under the ISC license.
|
|
258
258
|
* See the LICENSE file in the root directory of this source tree.
|
|
259
259
|
*/
|
|
260
|
-
const __iconNode$
|
|
261
|
-
const Play = createLucideIcon("play", __iconNode$
|
|
260
|
+
const __iconNode$h = [["polygon", { points: "6 3 20 12 6 21 6 3", key: "1oa8hb" }]];
|
|
261
|
+
const Play = createLucideIcon("play", __iconNode$h);
|
|
262
262
|
/**
|
|
263
263
|
* @license lucide-react v0.511.0 - ISC
|
|
264
264
|
*
|
|
265
265
|
* This source code is licensed under the ISC license.
|
|
266
266
|
* See the LICENSE file in the root directory of this source tree.
|
|
267
267
|
*/
|
|
268
|
-
const __iconNode$
|
|
268
|
+
const __iconNode$g = [
|
|
269
269
|
["path", { d: "M5 12h14", key: "1ays0h" }],
|
|
270
270
|
["path", { d: "M12 5v14", key: "s699le" }]
|
|
271
271
|
];
|
|
272
|
-
const Plus = createLucideIcon("plus", __iconNode$
|
|
272
|
+
const Plus = createLucideIcon("plus", __iconNode$g);
|
|
273
|
+
/**
|
|
274
|
+
* @license lucide-react v0.511.0 - ISC
|
|
275
|
+
*
|
|
276
|
+
* This source code is licensed under the ISC license.
|
|
277
|
+
* See the LICENSE file in the root directory of this source tree.
|
|
278
|
+
*/
|
|
279
|
+
const __iconNode$f = [
|
|
280
|
+
["rect", { width: "20", height: "12", x: "2", y: "6", rx: "2", key: "9lu3g6" }]
|
|
281
|
+
];
|
|
282
|
+
const RectangleHorizontal = createLucideIcon("rectangle-horizontal", __iconNode$f);
|
|
283
|
+
/**
|
|
284
|
+
* @license lucide-react v0.511.0 - ISC
|
|
285
|
+
*
|
|
286
|
+
* This source code is licensed under the ISC license.
|
|
287
|
+
* See the LICENSE file in the root directory of this source tree.
|
|
288
|
+
*/
|
|
289
|
+
const __iconNode$e = [
|
|
290
|
+
["rect", { width: "12", height: "20", x: "6", y: "2", rx: "2", key: "1oxtiu" }]
|
|
291
|
+
];
|
|
292
|
+
const RectangleVertical = createLucideIcon("rectangle-vertical", __iconNode$e);
|
|
273
293
|
/**
|
|
274
294
|
* @license lucide-react v0.511.0 - ISC
|
|
275
295
|
*
|
|
@@ -566,6 +586,15 @@ const StudioHeader = ({
|
|
|
566
586
|
setOrientation(orientation2);
|
|
567
587
|
}
|
|
568
588
|
}, []);
|
|
589
|
+
const handleOrientationChange = (nextOrientation) => {
|
|
590
|
+
if (nextOrientation === orientation) return;
|
|
591
|
+
const confirmMessage = "Changing orientation will create a new project with the new resolution. Do you want to continue?";
|
|
592
|
+
if (!window.confirm(confirmMessage)) {
|
|
593
|
+
return;
|
|
594
|
+
}
|
|
595
|
+
onNewProject();
|
|
596
|
+
setOrientation(nextOrientation);
|
|
597
|
+
};
|
|
569
598
|
react.useEffect(() => {
|
|
570
599
|
if (orientation === "horizontal") {
|
|
571
600
|
localStorage.setItem("orientation", "horizontal");
|
|
@@ -576,10 +605,31 @@ const StudioHeader = ({
|
|
|
576
605
|
}
|
|
577
606
|
}, [orientation]);
|
|
578
607
|
return /* @__PURE__ */ jsxRuntime.jsxs("header", { className: "header", children: [
|
|
579
|
-
/* @__PURE__ */ jsxRuntime.
|
|
608
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex-container", children: [
|
|
580
609
|
/* @__PURE__ */ jsxRuntime.jsx(Clapperboard, { className: "icon-lg accent-purple" }),
|
|
581
610
|
/* @__PURE__ */ jsxRuntime.jsx("h1", { className: "text-gradient", children: "Twick Studio" })
|
|
582
|
-
] })
|
|
611
|
+
] }),
|
|
612
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex-container", style: { gap: "0.5rem" }, children: [
|
|
613
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-sm opacity-80", children: "Orientation" }),
|
|
614
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
615
|
+
"button",
|
|
616
|
+
{
|
|
617
|
+
className: `btn-ghost ${orientation === "vertical" ? "btn-primary" : ""}`,
|
|
618
|
+
title: "Portrait (720×1280)",
|
|
619
|
+
onClick: () => handleOrientationChange("vertical"),
|
|
620
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(RectangleVertical, { className: "icon-sm" })
|
|
621
|
+
}
|
|
622
|
+
),
|
|
623
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
624
|
+
"button",
|
|
625
|
+
{
|
|
626
|
+
className: `btn-ghost ${orientation === "horizontal" ? "btn-primary" : ""}`,
|
|
627
|
+
title: "Landscape (1280×720)",
|
|
628
|
+
onClick: () => handleOrientationChange("horizontal"),
|
|
629
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(RectangleHorizontal, { className: "icon-sm" })
|
|
630
|
+
}
|
|
631
|
+
)
|
|
632
|
+
] }),
|
|
583
633
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex-container", children: [
|
|
584
634
|
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
585
635
|
"button",
|
|
@@ -1476,6 +1526,9 @@ function TextPanel({
|
|
|
1476
1526
|
applyShadow,
|
|
1477
1527
|
shadowColor,
|
|
1478
1528
|
strokeWidth,
|
|
1529
|
+
applyBackground,
|
|
1530
|
+
backgroundColor,
|
|
1531
|
+
backgroundOpacity,
|
|
1479
1532
|
fonts,
|
|
1480
1533
|
operation,
|
|
1481
1534
|
setTextContent,
|
|
@@ -1488,6 +1541,9 @@ function TextPanel({
|
|
|
1488
1541
|
setApplyShadow,
|
|
1489
1542
|
setShadowColor,
|
|
1490
1543
|
setStrokeWidth,
|
|
1544
|
+
setApplyBackground,
|
|
1545
|
+
setBackgroundColor,
|
|
1546
|
+
setBackgroundOpacity,
|
|
1491
1547
|
handleApplyChanges
|
|
1492
1548
|
}) {
|
|
1493
1549
|
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "panel-container", children: [
|
|
@@ -1656,6 +1712,69 @@ function TextPanel({
|
|
|
1656
1712
|
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "slider-value", children: strokeWidth })
|
|
1657
1713
|
] })
|
|
1658
1714
|
] }),
|
|
1715
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "panel-section", children: [
|
|
1716
|
+
/* @__PURE__ */ jsxRuntime.jsx("label", { className: "label-dark", children: "Background" }),
|
|
1717
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "color-section", children: [
|
|
1718
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "checkbox-control", children: /* @__PURE__ */ jsxRuntime.jsxs("label", { className: "checkbox-label", children: [
|
|
1719
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
1720
|
+
"input",
|
|
1721
|
+
{
|
|
1722
|
+
type: "checkbox",
|
|
1723
|
+
checked: applyBackground,
|
|
1724
|
+
onChange: (e) => setApplyBackground(e.target.checked),
|
|
1725
|
+
className: "checkbox-purple"
|
|
1726
|
+
}
|
|
1727
|
+
),
|
|
1728
|
+
"Apply Background"
|
|
1729
|
+
] }) }),
|
|
1730
|
+
applyBackground && /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
1731
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "color-control", children: [
|
|
1732
|
+
/* @__PURE__ */ jsxRuntime.jsx("label", { className: "label-small", children: "Background Color" }),
|
|
1733
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "color-inputs", children: [
|
|
1734
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
1735
|
+
"input",
|
|
1736
|
+
{
|
|
1737
|
+
type: "color",
|
|
1738
|
+
value: backgroundColor,
|
|
1739
|
+
onChange: (e) => setBackgroundColor(e.target.value),
|
|
1740
|
+
className: "color-picker"
|
|
1741
|
+
}
|
|
1742
|
+
),
|
|
1743
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
1744
|
+
"input",
|
|
1745
|
+
{
|
|
1746
|
+
type: "text",
|
|
1747
|
+
value: backgroundColor,
|
|
1748
|
+
onChange: (e) => setBackgroundColor(e.target.value),
|
|
1749
|
+
className: "color-text"
|
|
1750
|
+
}
|
|
1751
|
+
)
|
|
1752
|
+
] })
|
|
1753
|
+
] }),
|
|
1754
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "panel-section", children: [
|
|
1755
|
+
/* @__PURE__ */ jsxRuntime.jsx("label", { className: "label-small", children: "Background Opacity" }),
|
|
1756
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "slider-container", children: [
|
|
1757
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
1758
|
+
"input",
|
|
1759
|
+
{
|
|
1760
|
+
type: "range",
|
|
1761
|
+
min: "0",
|
|
1762
|
+
max: "1",
|
|
1763
|
+
step: 0.1,
|
|
1764
|
+
value: backgroundOpacity,
|
|
1765
|
+
onChange: (e) => setBackgroundOpacity(Number(e.target.value)),
|
|
1766
|
+
className: "slider-purple"
|
|
1767
|
+
}
|
|
1768
|
+
),
|
|
1769
|
+
/* @__PURE__ */ jsxRuntime.jsxs("span", { className: "slider-value", children: [
|
|
1770
|
+
Math.round(backgroundOpacity * 100),
|
|
1771
|
+
"%"
|
|
1772
|
+
] })
|
|
1773
|
+
] })
|
|
1774
|
+
] })
|
|
1775
|
+
] })
|
|
1776
|
+
] })
|
|
1777
|
+
] }),
|
|
1659
1778
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex panel-section", children: /* @__PURE__ */ jsxRuntime.jsx("button", { onClick: handleApplyChanges, className: "btn-primary w-full", children: operation }) })
|
|
1660
1779
|
] });
|
|
1661
1780
|
}
|
|
@@ -1690,6 +1809,9 @@ const useTextPanel = ({
|
|
|
1690
1809
|
const [applyShadow, setApplyShadow] = react.useState(DEFAULT_TEXT_PROPS.applyShadow);
|
|
1691
1810
|
const [shadowColor, setShadowColor] = react.useState(DEFAULT_TEXT_PROPS.shadowColor);
|
|
1692
1811
|
const [strokeWidth, setStrokeWidth] = react.useState(DEFAULT_TEXT_PROPS.strokeWidth);
|
|
1812
|
+
const [applyBackground, setApplyBackground] = react.useState(false);
|
|
1813
|
+
const [backgroundColor, setBackgroundColor] = react.useState("#FACC15");
|
|
1814
|
+
const [backgroundOpacity, setBackgroundOpacity] = react.useState(1);
|
|
1693
1815
|
const fonts = Object.values(VideoEditor.AVAILABLE_TEXT_FONTS);
|
|
1694
1816
|
const handleApplyChanges = async () => {
|
|
1695
1817
|
let textElement;
|
|
@@ -1704,35 +1826,41 @@ const useTextPanel = ({
|
|
|
1704
1826
|
textElement.setStrokeColor(strokeColor);
|
|
1705
1827
|
textElement.setLineWidth(strokeWidth);
|
|
1706
1828
|
textElement.setTextAlign(DEFAULT_TEXT_PROPS.textAlign);
|
|
1829
|
+
const nextProps = { ...textElement.getProps() };
|
|
1707
1830
|
if (applyShadow) {
|
|
1708
|
-
|
|
1709
|
-
|
|
1710
|
-
|
|
1711
|
-
|
|
1712
|
-
shadowBlur: DEFAULT_TEXT_PROPS.shadowBlur,
|
|
1713
|
-
shadowOpacity: DEFAULT_TEXT_PROPS.shadowOpacity
|
|
1714
|
-
});
|
|
1831
|
+
nextProps.shadowColor = shadowColor;
|
|
1832
|
+
nextProps.shadowOffset = DEFAULT_TEXT_PROPS.shadowOffset;
|
|
1833
|
+
nextProps.shadowBlur = DEFAULT_TEXT_PROPS.shadowBlur;
|
|
1834
|
+
nextProps.shadowOpacity = DEFAULT_TEXT_PROPS.shadowOpacity;
|
|
1715
1835
|
} else {
|
|
1716
|
-
|
|
1717
|
-
|
|
1718
|
-
|
|
1719
|
-
|
|
1720
|
-
|
|
1721
|
-
|
|
1722
|
-
|
|
1836
|
+
nextProps.shadowColor = void 0;
|
|
1837
|
+
nextProps.shadowOffset = void 0;
|
|
1838
|
+
nextProps.shadowBlur = void 0;
|
|
1839
|
+
nextProps.shadowOpacity = void 0;
|
|
1840
|
+
}
|
|
1841
|
+
if (applyBackground) {
|
|
1842
|
+
nextProps.backgroundColor = backgroundColor;
|
|
1843
|
+
nextProps.backgroundOpacity = backgroundOpacity;
|
|
1844
|
+
} else {
|
|
1845
|
+
nextProps.backgroundColor = void 0;
|
|
1846
|
+
nextProps.backgroundOpacity = void 0;
|
|
1723
1847
|
}
|
|
1848
|
+
textElement.setProps(nextProps);
|
|
1724
1849
|
updateElement(textElement);
|
|
1725
1850
|
} else {
|
|
1726
1851
|
textElement = new timeline.TextElement(textContent).setFontSize(fontSize).setFontFamily(selectedFont).setFontWeight(isBold ? 700 : 400).setFontStyle(isItalic ? "italic" : "normal").setFill(textColor).setStrokeColor(strokeColor).setLineWidth(strokeWidth).setTextAlign("center");
|
|
1852
|
+
const nextProps = { ...textElement.getProps() };
|
|
1727
1853
|
if (applyShadow) {
|
|
1728
|
-
|
|
1729
|
-
|
|
1730
|
-
|
|
1731
|
-
|
|
1732
|
-
|
|
1733
|
-
|
|
1734
|
-
|
|
1854
|
+
nextProps.shadowColor = shadowColor;
|
|
1855
|
+
nextProps.shadowOffset = DEFAULT_TEXT_PROPS.shadowOffset;
|
|
1856
|
+
nextProps.shadowBlur = DEFAULT_TEXT_PROPS.shadowBlur;
|
|
1857
|
+
nextProps.shadowOpacity = DEFAULT_TEXT_PROPS.shadowOpacity;
|
|
1858
|
+
}
|
|
1859
|
+
if (applyBackground) {
|
|
1860
|
+
nextProps.backgroundColor = backgroundColor;
|
|
1861
|
+
nextProps.backgroundOpacity = backgroundOpacity;
|
|
1735
1862
|
}
|
|
1863
|
+
textElement.setProps(nextProps);
|
|
1736
1864
|
await addElement(textElement);
|
|
1737
1865
|
}
|
|
1738
1866
|
};
|
|
@@ -1752,6 +1880,12 @@ const useTextPanel = ({
|
|
|
1752
1880
|
if (hasShadow) {
|
|
1753
1881
|
setShadowColor(textProps.shadowColor ?? DEFAULT_TEXT_PROPS.shadowColor);
|
|
1754
1882
|
}
|
|
1883
|
+
const hasBackground = textProps.backgroundColor != null && textProps.backgroundColor !== "";
|
|
1884
|
+
setApplyBackground(hasBackground);
|
|
1885
|
+
if (hasBackground) {
|
|
1886
|
+
setBackgroundColor(textProps.backgroundColor ?? "#FACC15");
|
|
1887
|
+
setBackgroundOpacity(textProps.backgroundOpacity ?? 1);
|
|
1888
|
+
}
|
|
1755
1889
|
} else {
|
|
1756
1890
|
setTextContent(DEFAULT_TEXT_PROPS.text);
|
|
1757
1891
|
setFontSize(DEFAULT_TEXT_PROPS.fontSize);
|
|
@@ -1763,6 +1897,9 @@ const useTextPanel = ({
|
|
|
1763
1897
|
setStrokeWidth(DEFAULT_TEXT_PROPS.strokeWidth);
|
|
1764
1898
|
setApplyShadow(DEFAULT_TEXT_PROPS.applyShadow);
|
|
1765
1899
|
setShadowColor(DEFAULT_TEXT_PROPS.shadowColor);
|
|
1900
|
+
setApplyBackground(false);
|
|
1901
|
+
setBackgroundColor("#FACC15");
|
|
1902
|
+
setBackgroundOpacity(1);
|
|
1766
1903
|
}
|
|
1767
1904
|
}, [selectedElement]);
|
|
1768
1905
|
return {
|
|
@@ -1788,6 +1925,12 @@ const useTextPanel = ({
|
|
|
1788
1925
|
setApplyShadow,
|
|
1789
1926
|
setShadowColor,
|
|
1790
1927
|
setStrokeWidth,
|
|
1928
|
+
applyBackground,
|
|
1929
|
+
backgroundColor,
|
|
1930
|
+
backgroundOpacity,
|
|
1931
|
+
setApplyBackground,
|
|
1932
|
+
setBackgroundColor,
|
|
1933
|
+
setBackgroundOpacity,
|
|
1791
1934
|
handleApplyChanges
|
|
1792
1935
|
};
|
|
1793
1936
|
};
|
|
@@ -2498,7 +2641,7 @@ const useSubtitlesPanel = () => {
|
|
|
2498
2641
|
const subtitlesTrack = react.useRef(null);
|
|
2499
2642
|
const { editor } = timeline.useTimelineContext();
|
|
2500
2643
|
const fetchSubtitles = async () => {
|
|
2501
|
-
const editorSubtitlesTrack = editor.
|
|
2644
|
+
const editorSubtitlesTrack = editor.getSubtitlesTrack();
|
|
2502
2645
|
if (editorSubtitlesTrack) {
|
|
2503
2646
|
subtitlesTrack.current = editorSubtitlesTrack;
|
|
2504
2647
|
setSubtitles(
|
|
@@ -3525,7 +3668,7 @@ function PropertiesPanelContainer({
|
|
|
3525
3668
|
] });
|
|
3526
3669
|
}
|
|
3527
3670
|
const useStudioOperation = (studioConfig) => {
|
|
3528
|
-
const { editor, present } = timeline.useTimelineContext();
|
|
3671
|
+
const { editor, present, videoResolution } = timeline.useTimelineContext();
|
|
3529
3672
|
const { setSeekTime, setPlayerState } = livePlayer.useLivePlayerContext();
|
|
3530
3673
|
const [projectName, setProjectName] = react.useState("");
|
|
3531
3674
|
const onNewProject = () => {
|
|
@@ -3573,14 +3716,13 @@ const useStudioOperation = (studioConfig) => {
|
|
|
3573
3716
|
}
|
|
3574
3717
|
};
|
|
3575
3718
|
const onExportVideo = async () => {
|
|
3576
|
-
var _a, _b;
|
|
3577
3719
|
if ((studioConfig == null ? void 0 : studioConfig.exportVideo) && present) {
|
|
3578
3720
|
await studioConfig.exportVideo(present, {
|
|
3579
3721
|
outFile: "output.mp4",
|
|
3580
3722
|
fps: 30,
|
|
3581
3723
|
resolution: {
|
|
3582
|
-
width:
|
|
3583
|
-
height:
|
|
3724
|
+
width: videoResolution.width,
|
|
3725
|
+
height: videoResolution.height
|
|
3584
3726
|
}
|
|
3585
3727
|
});
|
|
3586
3728
|
} else {
|