@twick/studio 0.15.24 → 0.15.26
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/properties/generate-captions.d.ts +1 -1
- package/dist/helpers/constant.d.ts +15 -0
- package/dist/hooks/use-generate-captions.d.ts +1 -1
- package/dist/hooks/use-studio-operation.d.ts +0 -2
- package/dist/index.js +407 -177
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +408 -178
- package/dist/index.mjs.map +1 -1
- package/dist/studio.css +119 -1
- package/dist/types/index.d.ts +6 -1
- package/package.json +15 -15
package/dist/index.mjs
CHANGED
|
@@ -3,7 +3,7 @@ var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { en
|
|
|
3
3
|
var __publicField = (obj, key, value) => __defNormalProp(obj, typeof key !== "symbol" ? key + "" : key, value);
|
|
4
4
|
import { jsx, jsxs, Fragment } from "react/jsx-runtime";
|
|
5
5
|
import { forwardRef, createElement, useState, useEffect, useRef, useCallback, createContext, useContext, useMemo } from "react";
|
|
6
|
-
import { useTimelineContext, TrackElement, Track, ImageElement, AudioElement, VideoElement, TextElement, TIMELINE_ELEMENT_TYPE, EffectElement, CAPTION_STYLE, CaptionElement, TRACK_TYPES, LineElement, ArrowElement, RectElement, CircleElement, ElementTextEffect, ElementAnimation, CAPTION_STYLE_OPTIONS, exportChaptersAsYouTube, exportChaptersAsJSON, getCaptionLanguages, exportCaptionsAsSRT, exportCaptionsAsVTT, PLAYER_STATE } from "@twick/timeline";
|
|
6
|
+
import { useTimelineContext, TrackElement, Track, ImageElement, AudioElement, VideoElement, TextElement, TIMELINE_ELEMENT_TYPE, EffectElement, computeCaptionGeometry, CAPTION_STYLE, CaptionElement, TRACK_TYPES, LineElement, ArrowElement, RectElement, CircleElement, ElementTextEffect, ElementAnimation, CAPTION_STYLE_OPTIONS, exportChaptersAsYouTube, exportChaptersAsJSON, getCaptionLanguages, exportCaptionsAsSRT, exportCaptionsAsVTT, PLAYER_STATE } from "@twick/timeline";
|
|
7
7
|
import { AudioElement as AudioElement2, CAPTION_COLOR, CAPTION_FONT, CAPTION_STYLE as CAPTION_STYLE2, CAPTION_STYLE_OPTIONS as CAPTION_STYLE_OPTIONS2, CaptionElement as CaptionElement2, CircleElement as CircleElement2, ElementAdder, ElementAnimation as ElementAnimation2, ElementCloner, ElementDeserializer, ElementFrameEffect, ElementRemover, ElementSerializer, ElementSplitter, ElementTextEffect as ElementTextEffect2, ElementUpdater, ElementValidator, INITIAL_TIMELINE_DATA, IconElement, ImageElement as ImageElement2, PROCESS_STATE, RectElement as RectElement2, TIMELINE_ACTION, TIMELINE_ELEMENT_TYPE as TIMELINE_ELEMENT_TYPE2, TextElement as TextElement2, TimelineEditor, TimelineProvider, Track as Track2, TrackElement as TrackElement2, VideoElement as VideoElement2, WORDS_PER_PHRASE, generateShortUuid, getCurrentElements, getTotalDuration, isElementId, isTrackId, useTimelineContext as useTimelineContext2 } from "@twick/timeline";
|
|
8
8
|
import VideoEditor, { useEditorManager, BrowserMediaManager, TIMELINE_DROP_MEDIA_TYPE, throttle, AVAILABLE_TEXT_FONTS, TEXT_EFFECTS, ANIMATIONS } from "@twick/video-editor";
|
|
9
9
|
import { ANIMATIONS as ANIMATIONS2, BaseMediaManager, BrowserMediaManager as BrowserMediaManager2, PlayerControls, TEXT_EFFECTS as TEXT_EFFECTS2, TimelineManager, default as default2, animationGifs, getAnimationGif, setElementColors, useEditorManager as useEditorManager2, usePlayerControl, useTimelineControl } from "@twick/video-editor";
|
|
@@ -3029,10 +3029,10 @@ const TEXT_STYLE_PRESETS = [
|
|
|
3029
3029
|
applyBackground: false
|
|
3030
3030
|
},
|
|
3031
3031
|
{
|
|
3032
|
-
id: "
|
|
3033
|
-
label: "
|
|
3032
|
+
id: "bold-caption",
|
|
3033
|
+
label: "Bold Caption",
|
|
3034
3034
|
description: "Bold white with strong outline",
|
|
3035
|
-
fontFamily: AVAILABLE_TEXT_FONTS.
|
|
3035
|
+
fontFamily: AVAILABLE_TEXT_FONTS.ROBOTO,
|
|
3036
3036
|
fontSize: 34,
|
|
3037
3037
|
fontWeight: 700,
|
|
3038
3038
|
textColor: "#FFFFFF",
|
|
@@ -3132,7 +3132,7 @@ const TEXT_STYLE_PRESETS = [
|
|
|
3132
3132
|
id: "cta-pill",
|
|
3133
3133
|
label: "CTA Pill",
|
|
3134
3134
|
description: "Call-to-action pill",
|
|
3135
|
-
fontFamily: AVAILABLE_TEXT_FONTS.
|
|
3135
|
+
fontFamily: AVAILABLE_TEXT_FONTS.LUCKIEST_GUY,
|
|
3136
3136
|
fontSize: 28,
|
|
3137
3137
|
fontWeight: 700,
|
|
3138
3138
|
textColor: "#FFFFFF",
|
|
@@ -4672,6 +4672,16 @@ function EffectStylePanelContainer({
|
|
|
4672
4672
|
}
|
|
4673
4673
|
);
|
|
4674
4674
|
}
|
|
4675
|
+
const formatTime = (seconds) => {
|
|
4676
|
+
if (!Number.isFinite(seconds) || seconds < 0) return "0:00.00";
|
|
4677
|
+
const totalMs = Math.round(seconds * 1e3);
|
|
4678
|
+
const totalSeconds = Math.floor(totalMs / 1e3);
|
|
4679
|
+
const minutes = Math.floor(totalSeconds / 60);
|
|
4680
|
+
const secs = totalSeconds % 60;
|
|
4681
|
+
const ms = Math.floor(totalMs % 1e3 / 10);
|
|
4682
|
+
const pad = (n, l = 2) => String(n).padStart(l, "0");
|
|
4683
|
+
return `${minutes}:${pad(secs)}.${pad(ms)}`;
|
|
4684
|
+
};
|
|
4675
4685
|
function CaptionsPanel({
|
|
4676
4686
|
captions,
|
|
4677
4687
|
addCaption,
|
|
@@ -4679,54 +4689,102 @@ function CaptionsPanel({
|
|
|
4679
4689
|
deleteCaption,
|
|
4680
4690
|
updateCaption
|
|
4681
4691
|
}) {
|
|
4682
|
-
return /* @__PURE__ */ jsxs("div", { className: "panel-container", children: [
|
|
4683
|
-
/* @__PURE__ */
|
|
4684
|
-
|
|
4685
|
-
"div",
|
|
4686
|
-
|
|
4687
|
-
|
|
4688
|
-
|
|
4689
|
-
|
|
4690
|
-
|
|
4691
|
-
|
|
4692
|
-
|
|
4693
|
-
|
|
4694
|
-
|
|
4695
|
-
|
|
4696
|
-
|
|
4697
|
-
|
|
4698
|
-
|
|
4699
|
-
|
|
4700
|
-
|
|
4701
|
-
|
|
4702
|
-
|
|
4703
|
-
|
|
4704
|
-
|
|
4705
|
-
|
|
4706
|
-
|
|
4707
|
-
|
|
4708
|
-
|
|
4709
|
-
|
|
4710
|
-
|
|
4711
|
-
|
|
4712
|
-
|
|
4713
|
-
|
|
4714
|
-
|
|
4715
|
-
|
|
4716
|
-
|
|
4717
|
-
|
|
4718
|
-
|
|
4719
|
-
|
|
4720
|
-
|
|
4721
|
-
|
|
4722
|
-
|
|
4723
|
-
|
|
4692
|
+
return /* @__PURE__ */ jsxs("div", { className: "panel-container captions-panel", children: [
|
|
4693
|
+
/* @__PURE__ */ jsxs("div", { className: "captions-panel-header", children: [
|
|
4694
|
+
/* @__PURE__ */ jsx("h3", { className: "panel-title", children: "Captions" }),
|
|
4695
|
+
/* @__PURE__ */ jsxs("div", { className: "captions-panel-header-meta", children: [
|
|
4696
|
+
captions.length === 0 ? /* @__PURE__ */ jsx("span", { className: "captions-panel-count", children: "No captions yet" }) : null,
|
|
4697
|
+
/* @__PURE__ */ jsx(
|
|
4698
|
+
"button",
|
|
4699
|
+
{
|
|
4700
|
+
onClick: addCaption,
|
|
4701
|
+
className: "btn-primary captions-panel-add-button",
|
|
4702
|
+
title: "Add caption",
|
|
4703
|
+
children: "Add caption"
|
|
4704
|
+
}
|
|
4705
|
+
)
|
|
4706
|
+
] })
|
|
4707
|
+
] }),
|
|
4708
|
+
captions.length === 0 ? /* @__PURE__ */ jsxs("div", { className: "panel-section captions-panel-empty", children: [
|
|
4709
|
+
/* @__PURE__ */ jsx("p", { className: "captions-panel-empty-title", children: "Start your first caption" }),
|
|
4710
|
+
/* @__PURE__ */ jsx("p", { className: "captions-panel-empty-subtitle", children: "Use the button above to add the first caption block for the active track." }),
|
|
4711
|
+
/* @__PURE__ */ jsx(
|
|
4712
|
+
"button",
|
|
4713
|
+
{
|
|
4714
|
+
onClick: addCaption,
|
|
4715
|
+
className: "btn-primary captions-panel-empty-button",
|
|
4716
|
+
title: "Add first caption",
|
|
4717
|
+
children: "Add caption"
|
|
4718
|
+
}
|
|
4719
|
+
)
|
|
4720
|
+
] }) : /* @__PURE__ */ jsx("div", { className: "panel-section captions-panel-list", children: captions.map((caption, i) => {
|
|
4721
|
+
return /* @__PURE__ */ jsxs(
|
|
4722
|
+
"div",
|
|
4723
|
+
{
|
|
4724
|
+
className: "captions-panel-item",
|
|
4725
|
+
children: [
|
|
4726
|
+
/* @__PURE__ */ jsxs("div", { className: "captions-panel-item-header", children: [
|
|
4727
|
+
/* @__PURE__ */ jsx("span", { className: "captions-panel-time captions-panel-time-start", children: formatTime(caption.s) }),
|
|
4728
|
+
/* @__PURE__ */ jsx("span", { className: "captions-panel-time captions-panel-time-end", children: formatTime(caption.e) })
|
|
4729
|
+
] }),
|
|
4730
|
+
/* @__PURE__ */ jsxs("div", { className: "captions-panel-item-body", children: [
|
|
4731
|
+
/* @__PURE__ */ jsx(
|
|
4732
|
+
"textarea",
|
|
4733
|
+
{
|
|
4734
|
+
placeholder: "Enter caption text",
|
|
4735
|
+
value: caption.t,
|
|
4736
|
+
onChange: (e) => updateCaption(i, { ...caption, t: e.target.value }),
|
|
4737
|
+
className: "input-dark captions-panel-textarea"
|
|
4738
|
+
}
|
|
4739
|
+
),
|
|
4740
|
+
/* @__PURE__ */ jsxs("div", { className: "captions-panel-actions", children: [
|
|
4741
|
+
/* @__PURE__ */ jsx(
|
|
4742
|
+
"button",
|
|
4743
|
+
{
|
|
4744
|
+
onClick: () => splitCaption(i),
|
|
4745
|
+
className: "btn-ghost captions-panel-action-button",
|
|
4746
|
+
title: "Split caption at midpoint",
|
|
4747
|
+
children: /* @__PURE__ */ jsx(Scissors, { className: "icon-sm" })
|
|
4748
|
+
}
|
|
4749
|
+
),
|
|
4750
|
+
/* @__PURE__ */ jsx(
|
|
4751
|
+
"button",
|
|
4752
|
+
{
|
|
4753
|
+
onClick: () => deleteCaption(i),
|
|
4754
|
+
className: "btn-ghost captions-panel-action-button",
|
|
4755
|
+
title: "Delete caption",
|
|
4756
|
+
children: /* @__PURE__ */ jsx(
|
|
4757
|
+
Trash2,
|
|
4758
|
+
{
|
|
4759
|
+
className: "icon-sm",
|
|
4760
|
+
color: "var(--color-red-500)"
|
|
4761
|
+
}
|
|
4762
|
+
)
|
|
4763
|
+
}
|
|
4764
|
+
)
|
|
4765
|
+
] })
|
|
4766
|
+
] })
|
|
4767
|
+
]
|
|
4768
|
+
},
|
|
4769
|
+
i
|
|
4770
|
+
);
|
|
4771
|
+
}) })
|
|
4724
4772
|
] });
|
|
4725
4773
|
}
|
|
4774
|
+
const HIGHLIGHT_BG_FONT_SIZE = 46;
|
|
4775
|
+
const WORD_BY_WORD_FONT_SIZE = 46;
|
|
4776
|
+
const WORD_BY_WORD_WITH_BG_FONT_SIZE = 46;
|
|
4777
|
+
const OUTLINE_ONLY_FONT_SIZE = 42;
|
|
4778
|
+
const SOFT_BOX_FONT_SIZE = 40;
|
|
4779
|
+
const HIGHLIGHT_BG_GEOMETRY = computeCaptionGeometry(HIGHLIGHT_BG_FONT_SIZE, CAPTION_STYLE.WORD_BG_HIGHLIGHT);
|
|
4780
|
+
const WORD_BY_WORD_GEOMETRY = computeCaptionGeometry(WORD_BY_WORD_FONT_SIZE, CAPTION_STYLE.WORD_BY_WORD);
|
|
4781
|
+
const WORD_BY_WORD_WITH_BG_GEOMETRY = computeCaptionGeometry(WORD_BY_WORD_WITH_BG_FONT_SIZE, CAPTION_STYLE.WORD_BY_WORD_WITH_BG);
|
|
4782
|
+
const OUTLINE_ONLY_GEOMETRY = computeCaptionGeometry(OUTLINE_ONLY_FONT_SIZE, CAPTION_STYLE.OUTLINE_ONLY);
|
|
4783
|
+
const SOFT_BOX_GEOMETRY = computeCaptionGeometry(SOFT_BOX_FONT_SIZE, CAPTION_STYLE.SOFT_BOX);
|
|
4726
4784
|
const CAPTION_PROPS = {
|
|
4727
4785
|
[CAPTION_STYLE.WORD_BG_HIGHLIGHT]: {
|
|
4728
4786
|
font: {
|
|
4729
|
-
size:
|
|
4787
|
+
size: HIGHLIGHT_BG_FONT_SIZE,
|
|
4730
4788
|
weight: 700,
|
|
4731
4789
|
family: "Bangers"
|
|
4732
4790
|
},
|
|
@@ -4735,15 +4793,16 @@ const CAPTION_PROPS = {
|
|
|
4735
4793
|
highlight: "#ff4081",
|
|
4736
4794
|
bgColor: "#444444"
|
|
4737
4795
|
},
|
|
4738
|
-
lineWidth:
|
|
4796
|
+
lineWidth: HIGHLIGHT_BG_GEOMETRY.lineWidth,
|
|
4797
|
+
rectProps: HIGHLIGHT_BG_GEOMETRY.rectProps,
|
|
4739
4798
|
stroke: "#000000",
|
|
4740
4799
|
fontWeight: 700,
|
|
4741
|
-
shadowOffset: [-
|
|
4800
|
+
shadowOffset: [-1, 1],
|
|
4742
4801
|
shadowColor: "#000000"
|
|
4743
4802
|
},
|
|
4744
4803
|
[CAPTION_STYLE.WORD_BY_WORD]: {
|
|
4745
4804
|
font: {
|
|
4746
|
-
size:
|
|
4805
|
+
size: WORD_BY_WORD_FONT_SIZE,
|
|
4747
4806
|
weight: 700,
|
|
4748
4807
|
family: "Bangers"
|
|
4749
4808
|
},
|
|
@@ -4752,15 +4811,16 @@ const CAPTION_PROPS = {
|
|
|
4752
4811
|
highlight: "#ff4081",
|
|
4753
4812
|
bgColor: "#444444"
|
|
4754
4813
|
},
|
|
4755
|
-
lineWidth:
|
|
4814
|
+
lineWidth: WORD_BY_WORD_GEOMETRY.lineWidth,
|
|
4815
|
+
rectProps: WORD_BY_WORD_GEOMETRY.rectProps,
|
|
4756
4816
|
stroke: "#000000",
|
|
4757
|
-
shadowOffset: [-
|
|
4817
|
+
shadowOffset: [-1, 1],
|
|
4758
4818
|
shadowColor: "#000000",
|
|
4759
4819
|
shadowBlur: 5
|
|
4760
4820
|
},
|
|
4761
4821
|
[CAPTION_STYLE.WORD_BY_WORD_WITH_BG]: {
|
|
4762
4822
|
font: {
|
|
4763
|
-
size:
|
|
4823
|
+
size: WORD_BY_WORD_WITH_BG_FONT_SIZE,
|
|
4764
4824
|
weight: 700,
|
|
4765
4825
|
family: "Bangers"
|
|
4766
4826
|
},
|
|
@@ -4769,14 +4829,15 @@ const CAPTION_PROPS = {
|
|
|
4769
4829
|
highlight: "#ff4081",
|
|
4770
4830
|
bgColor: "#444444"
|
|
4771
4831
|
},
|
|
4772
|
-
lineWidth:
|
|
4773
|
-
|
|
4832
|
+
lineWidth: WORD_BY_WORD_WITH_BG_GEOMETRY.lineWidth,
|
|
4833
|
+
rectProps: WORD_BY_WORD_WITH_BG_GEOMETRY.rectProps,
|
|
4834
|
+
shadowOffset: [-1, 1],
|
|
4774
4835
|
shadowColor: "#000000",
|
|
4775
4836
|
shadowBlur: 5
|
|
4776
4837
|
},
|
|
4777
4838
|
[CAPTION_STYLE.OUTLINE_ONLY]: {
|
|
4778
4839
|
font: {
|
|
4779
|
-
size:
|
|
4840
|
+
size: OUTLINE_ONLY_FONT_SIZE,
|
|
4780
4841
|
weight: 600,
|
|
4781
4842
|
family: "Arial"
|
|
4782
4843
|
},
|
|
@@ -4785,7 +4846,8 @@ const CAPTION_PROPS = {
|
|
|
4785
4846
|
highlight: "#ff4081",
|
|
4786
4847
|
bgColor: "#000000"
|
|
4787
4848
|
},
|
|
4788
|
-
lineWidth:
|
|
4849
|
+
lineWidth: OUTLINE_ONLY_GEOMETRY.lineWidth,
|
|
4850
|
+
rectProps: OUTLINE_ONLY_GEOMETRY.rectProps,
|
|
4789
4851
|
stroke: "#000000",
|
|
4790
4852
|
fontWeight: 600,
|
|
4791
4853
|
shadowOffset: [0, 0],
|
|
@@ -4794,7 +4856,7 @@ const CAPTION_PROPS = {
|
|
|
4794
4856
|
},
|
|
4795
4857
|
[CAPTION_STYLE.SOFT_BOX]: {
|
|
4796
4858
|
font: {
|
|
4797
|
-
size:
|
|
4859
|
+
size: SOFT_BOX_FONT_SIZE,
|
|
4798
4860
|
weight: 600,
|
|
4799
4861
|
family: "Montserrat"
|
|
4800
4862
|
},
|
|
@@ -4803,7 +4865,8 @@ const CAPTION_PROPS = {
|
|
|
4803
4865
|
highlight: "#ff4081",
|
|
4804
4866
|
bgColor: "#333333"
|
|
4805
4867
|
},
|
|
4806
|
-
lineWidth:
|
|
4868
|
+
lineWidth: SOFT_BOX_GEOMETRY.lineWidth,
|
|
4869
|
+
rectProps: SOFT_BOX_GEOMETRY.rectProps,
|
|
4807
4870
|
stroke: "#000000",
|
|
4808
4871
|
fontWeight: 600,
|
|
4809
4872
|
shadowOffset: [-1, 1],
|
|
@@ -6322,6 +6385,116 @@ const CAPTION_COLOR2 = {
|
|
|
6322
6385
|
bgColor: "#8C52FF",
|
|
6323
6386
|
outlineColor: "#000000"
|
|
6324
6387
|
};
|
|
6388
|
+
const CAPTION_STYLE_COLOR_META = {
|
|
6389
|
+
// Word background highlight - white text on colored pill
|
|
6390
|
+
highlight_bg: {
|
|
6391
|
+
// Text color, and background pill color used in animation.
|
|
6392
|
+
usedColors: ["text", "bgColor"],
|
|
6393
|
+
labels: {
|
|
6394
|
+
text: "Text Color",
|
|
6395
|
+
bgColor: "Highlight Background"
|
|
6396
|
+
}
|
|
6397
|
+
},
|
|
6398
|
+
// Simple word-by-word – text only
|
|
6399
|
+
word_by_word: {
|
|
6400
|
+
// Visualizer uses text as fill + outlineColor for stroke, and highlight for active word.
|
|
6401
|
+
usedColors: ["text", "highlight", "outlineColor"],
|
|
6402
|
+
labels: {
|
|
6403
|
+
text: "Text Color",
|
|
6404
|
+
highlight: "Highlight Color",
|
|
6405
|
+
outlineColor: "Outline Color"
|
|
6406
|
+
}
|
|
6407
|
+
},
|
|
6408
|
+
// Word-by-word with a phrase bar background
|
|
6409
|
+
word_by_word_with_bg: {
|
|
6410
|
+
// Text color (fill), highlight for active word, outlineColor (stroke), bgColor used by phrase rect.
|
|
6411
|
+
usedColors: ["text", "highlight", "bgColor", "outlineColor"],
|
|
6412
|
+
labels: {
|
|
6413
|
+
text: "Text Color",
|
|
6414
|
+
bgColor: "Bar Background",
|
|
6415
|
+
highlight: "Highlight Color",
|
|
6416
|
+
outlineColor: "Outline Color"
|
|
6417
|
+
}
|
|
6418
|
+
},
|
|
6419
|
+
// Classic outlined text
|
|
6420
|
+
outline_only: {
|
|
6421
|
+
// Outline-only style: fill + outline color; highlight not used in animation.
|
|
6422
|
+
usedColors: ["text", "outlineColor"],
|
|
6423
|
+
labels: {
|
|
6424
|
+
text: "Fill Color",
|
|
6425
|
+
outlineColor: "Outline Color"
|
|
6426
|
+
}
|
|
6427
|
+
},
|
|
6428
|
+
// Soft rounded box behind text
|
|
6429
|
+
soft_box: {
|
|
6430
|
+
usedColors: ["text", "bgColor", "highlight", "outlineColor"],
|
|
6431
|
+
labels: {
|
|
6432
|
+
text: "Text Color",
|
|
6433
|
+
highlight: "Highlight Color",
|
|
6434
|
+
bgColor: "Box Background",
|
|
6435
|
+
outlineColor: "Outline Color"
|
|
6436
|
+
}
|
|
6437
|
+
},
|
|
6438
|
+
// Broadcast style lower-third bar
|
|
6439
|
+
lower_third: {
|
|
6440
|
+
// Title text, bar background, highlight color and outline color.
|
|
6441
|
+
usedColors: ["text", "bgColor", "outlineColor"],
|
|
6442
|
+
labels: {
|
|
6443
|
+
text: "Title Text Color",
|
|
6444
|
+
bgColor: "Bar Background",
|
|
6445
|
+
highlight: "Highlight Color",
|
|
6446
|
+
outlineColor: "Outline Color"
|
|
6447
|
+
}
|
|
6448
|
+
},
|
|
6449
|
+
// Typewriter – text only
|
|
6450
|
+
typewriter: {
|
|
6451
|
+
// Text color and outline color (stroke) used by visualizer; highlight not animated.
|
|
6452
|
+
usedColors: ["text", "outlineColor"],
|
|
6453
|
+
labels: {
|
|
6454
|
+
text: "Text Color",
|
|
6455
|
+
outlineColor: "Outline Color"
|
|
6456
|
+
}
|
|
6457
|
+
},
|
|
6458
|
+
// Karaoke – base text plus active word highlight
|
|
6459
|
+
karaoke: {
|
|
6460
|
+
// Base text color, active word highlight color, outline color.
|
|
6461
|
+
usedColors: ["text", "highlight", "outlineColor"],
|
|
6462
|
+
labels: {
|
|
6463
|
+
text: "Text Color",
|
|
6464
|
+
highlight: "Highlight Color",
|
|
6465
|
+
outlineColor: "Outline Color"
|
|
6466
|
+
}
|
|
6467
|
+
},
|
|
6468
|
+
// Karaoke-word – single active word, previous words dimmed
|
|
6469
|
+
"karaoke-word": {
|
|
6470
|
+
// Same color needs as karaoke.
|
|
6471
|
+
usedColors: ["text", "highlight", "outlineColor"],
|
|
6472
|
+
labels: {
|
|
6473
|
+
text: "Text Color",
|
|
6474
|
+
highlight: "Highlight Color",
|
|
6475
|
+
outlineColor: "Outline Color"
|
|
6476
|
+
}
|
|
6477
|
+
},
|
|
6478
|
+
// Pop / scale – text only
|
|
6479
|
+
pop_scale: {
|
|
6480
|
+
// Text color, highlight color for active word, and outline color; no background.
|
|
6481
|
+
usedColors: ["text", "highlight", "outlineColor"],
|
|
6482
|
+
labels: {
|
|
6483
|
+
text: "Text Color",
|
|
6484
|
+
highlight: "Highlight Color",
|
|
6485
|
+
outlineColor: "Outline Color"
|
|
6486
|
+
}
|
|
6487
|
+
}
|
|
6488
|
+
};
|
|
6489
|
+
const DEFAULT_COLOR_META = {
|
|
6490
|
+
usedColors: ["text", "bgColor", "outlineColor"],
|
|
6491
|
+
labels: {
|
|
6492
|
+
text: "Text Color",
|
|
6493
|
+
bgColor: "Background Color",
|
|
6494
|
+
outlineColor: "Outline Color"
|
|
6495
|
+
}
|
|
6496
|
+
};
|
|
6497
|
+
const CAPTION_FONTS = Object.values(AVAILABLE_TEXT_FONTS);
|
|
6325
6498
|
function CaptionPropPanel({
|
|
6326
6499
|
selectedElement,
|
|
6327
6500
|
updateElement
|
|
@@ -6339,24 +6512,42 @@ function CaptionPropPanel({
|
|
|
6339
6512
|
bgColor: CAPTION_COLOR2.bgColor,
|
|
6340
6513
|
outlineColor: CAPTION_COLOR2.outlineColor
|
|
6341
6514
|
});
|
|
6515
|
+
const [useHighlight, setUseHighlight] = useState(true);
|
|
6516
|
+
const [useOutline, setUseOutline] = useState(true);
|
|
6342
6517
|
const track = selectedElement instanceof CaptionElement ? editor.getTrackById(selectedElement.getTrackId()) : null;
|
|
6343
6518
|
const trackProps = (track == null ? void 0 : track.getProps()) ?? {};
|
|
6344
6519
|
const applyToAll = (trackProps == null ? void 0 : trackProps.applyToAll) ?? false;
|
|
6345
6520
|
const handleUpdateCaption = (updates) => {
|
|
6346
6521
|
const captionElement = selectedElement;
|
|
6347
6522
|
if (!captionElement) return;
|
|
6523
|
+
const nextFontSize = updates.fontSize ?? fontSize;
|
|
6524
|
+
const geometry = computeCaptionGeometry(nextFontSize, updates.style ?? (capStyle == null ? void 0 : capStyle.value) ?? "");
|
|
6525
|
+
const highlightEnabled = updates.useHighlightOverride ?? useHighlight;
|
|
6526
|
+
const outlineEnabled = updates.useOutlineOverride ?? useOutline;
|
|
6527
|
+
const rawNextColors = updates.colors ?? colors;
|
|
6528
|
+
let effectiveColors = { ...rawNextColors };
|
|
6529
|
+
if (!highlightEnabled) {
|
|
6530
|
+
const { highlight, ...rest } = effectiveColors;
|
|
6531
|
+
effectiveColors = rest;
|
|
6532
|
+
}
|
|
6533
|
+
if (!outlineEnabled) {
|
|
6534
|
+
const { outlineColor, ...rest } = effectiveColors;
|
|
6535
|
+
effectiveColors = rest;
|
|
6536
|
+
}
|
|
6348
6537
|
if (applyToAll && track) {
|
|
6349
6538
|
const nextFont = {
|
|
6350
|
-
size:
|
|
6539
|
+
size: nextFontSize,
|
|
6351
6540
|
family: updates.fontFamily ?? fontFamily
|
|
6352
6541
|
};
|
|
6353
|
-
const nextColors =
|
|
6542
|
+
const nextColors = effectiveColors;
|
|
6354
6543
|
const nextCapStyle = updates.style ?? (capStyle == null ? void 0 : capStyle.value);
|
|
6355
6544
|
track.setProps({
|
|
6356
6545
|
...trackProps,
|
|
6357
6546
|
capStyle: nextCapStyle,
|
|
6358
6547
|
font: { ...(trackProps == null ? void 0 : trackProps.font) ?? {}, ...nextFont },
|
|
6359
|
-
colors: nextColors
|
|
6548
|
+
colors: nextColors,
|
|
6549
|
+
lineWidth: geometry.lineWidth,
|
|
6550
|
+
rectProps: geometry.rectProps
|
|
6360
6551
|
});
|
|
6361
6552
|
editor.refresh();
|
|
6362
6553
|
} else {
|
|
@@ -6365,10 +6556,11 @@ function CaptionPropPanel({
|
|
|
6365
6556
|
...elementProps,
|
|
6366
6557
|
capStyle: updates.style ?? (capStyle == null ? void 0 : capStyle.value),
|
|
6367
6558
|
font: {
|
|
6368
|
-
size:
|
|
6559
|
+
size: nextFontSize,
|
|
6369
6560
|
family: updates.fontFamily ?? fontFamily
|
|
6370
6561
|
},
|
|
6371
|
-
colors:
|
|
6562
|
+
colors: effectiveColors,
|
|
6563
|
+
lineWidth: geometry.lineWidth
|
|
6372
6564
|
});
|
|
6373
6565
|
updateElement == null ? void 0 : updateElement(captionElement);
|
|
6374
6566
|
}
|
|
@@ -6394,11 +6586,62 @@ function CaptionPropPanel({
|
|
|
6394
6586
|
bgColor: (c == null ? void 0 : c.bgColor) ?? CAPTION_COLOR2.bgColor,
|
|
6395
6587
|
outlineColor: (c == null ? void 0 : c.outlineColor) ?? CAPTION_COLOR2.outlineColor
|
|
6396
6588
|
});
|
|
6589
|
+
setUseHighlight((c == null ? void 0 : c.highlight) != null);
|
|
6590
|
+
setUseOutline((c == null ? void 0 : c.outlineColor) != null);
|
|
6397
6591
|
}
|
|
6398
6592
|
}, [selectedElement, applyToAll, changeLog]);
|
|
6399
6593
|
if (!(selectedElement instanceof CaptionElement)) {
|
|
6400
6594
|
return null;
|
|
6401
6595
|
}
|
|
6596
|
+
const currentStyleKey = capStyle == null ? void 0 : capStyle.value;
|
|
6597
|
+
const currentColorMeta = currentStyleKey && CAPTION_STYLE_COLOR_META[currentStyleKey] || DEFAULT_COLOR_META;
|
|
6598
|
+
const defaultColorLabels = {
|
|
6599
|
+
text: "Text Color",
|
|
6600
|
+
bgColor: "Background Color",
|
|
6601
|
+
highlight: "Highlight Color",
|
|
6602
|
+
outlineColor: "Outline Color"
|
|
6603
|
+
};
|
|
6604
|
+
const renderColorControl = (key) => {
|
|
6605
|
+
if (key === "highlight" && !useHighlight) {
|
|
6606
|
+
return null;
|
|
6607
|
+
}
|
|
6608
|
+
if (key === "outlineColor" && !useOutline) {
|
|
6609
|
+
return null;
|
|
6610
|
+
}
|
|
6611
|
+
const label = currentColorMeta.labels[key] ?? defaultColorLabels[key];
|
|
6612
|
+
const value = colors[key];
|
|
6613
|
+
const handleChange = (next) => {
|
|
6614
|
+
const nextColors = { ...colors, [key]: next };
|
|
6615
|
+
setColors(nextColors);
|
|
6616
|
+
handleUpdateCaption({ colors: nextColors });
|
|
6617
|
+
};
|
|
6618
|
+
if (value == null) {
|
|
6619
|
+
return null;
|
|
6620
|
+
}
|
|
6621
|
+
return /* @__PURE__ */ jsxs("div", { className: "color-control", children: [
|
|
6622
|
+
/* @__PURE__ */ jsx("label", { className: "label-small", children: label }),
|
|
6623
|
+
/* @__PURE__ */ jsxs("div", { className: "color-inputs", children: [
|
|
6624
|
+
/* @__PURE__ */ jsx(
|
|
6625
|
+
"input",
|
|
6626
|
+
{
|
|
6627
|
+
type: "color",
|
|
6628
|
+
value,
|
|
6629
|
+
onChange: (e) => handleChange(e.target.value),
|
|
6630
|
+
className: "color-picker"
|
|
6631
|
+
}
|
|
6632
|
+
),
|
|
6633
|
+
/* @__PURE__ */ jsx(
|
|
6634
|
+
"input",
|
|
6635
|
+
{
|
|
6636
|
+
type: "text",
|
|
6637
|
+
value,
|
|
6638
|
+
onChange: (e) => handleChange(e.target.value),
|
|
6639
|
+
className: "color-text"
|
|
6640
|
+
}
|
|
6641
|
+
)
|
|
6642
|
+
] })
|
|
6643
|
+
] }, key);
|
|
6644
|
+
};
|
|
6402
6645
|
return /* @__PURE__ */ jsxs("div", { className: "panel-container", children: [
|
|
6403
6646
|
/* @__PURE__ */ jsxs("div", { className: "panel-section", children: [
|
|
6404
6647
|
/* @__PURE__ */ jsx("label", { className: "label-dark", children: "Caption Style" }),
|
|
@@ -6445,7 +6688,7 @@ function CaptionPropPanel({
|
|
|
6445
6688
|
] }),
|
|
6446
6689
|
/* @__PURE__ */ jsxs("div", { className: "panel-section", children: [
|
|
6447
6690
|
/* @__PURE__ */ jsx("label", { className: "label-dark", children: "Font" }),
|
|
6448
|
-
/* @__PURE__ */
|
|
6691
|
+
/* @__PURE__ */ jsx(
|
|
6449
6692
|
"select",
|
|
6450
6693
|
{
|
|
6451
6694
|
value: fontFamily,
|
|
@@ -6455,111 +6698,59 @@ function CaptionPropPanel({
|
|
|
6455
6698
|
handleUpdateCaption({ fontFamily: value });
|
|
6456
6699
|
},
|
|
6457
6700
|
className: "select-dark w-full",
|
|
6458
|
-
children:
|
|
6459
|
-
/* @__PURE__ */ jsx("option", { value: "Bangers", children: "Bangers" }),
|
|
6460
|
-
/* @__PURE__ */ jsx("option", { value: "Arial", children: "Arial" }),
|
|
6461
|
-
/* @__PURE__ */ jsx("option", { value: "Helvetica", children: "Helvetica" }),
|
|
6462
|
-
/* @__PURE__ */ jsx("option", { value: "Times New Roman", children: "Times New Roman" })
|
|
6463
|
-
]
|
|
6701
|
+
children: CAPTION_FONTS.map((font) => /* @__PURE__ */ jsx("option", { value: font, children: font }, font))
|
|
6464
6702
|
}
|
|
6465
6703
|
)
|
|
6466
6704
|
] }),
|
|
6467
6705
|
/* @__PURE__ */ jsxs("div", { className: "panel-section", children: [
|
|
6468
6706
|
/* @__PURE__ */ jsx("label", { className: "label-dark", children: "Colors" }),
|
|
6469
6707
|
/* @__PURE__ */ jsxs("div", { className: "color-section", children: [
|
|
6470
|
-
/* @__PURE__ */
|
|
6471
|
-
/* @__PURE__ */ jsx(
|
|
6472
|
-
|
|
6473
|
-
|
|
6474
|
-
"
|
|
6475
|
-
|
|
6476
|
-
|
|
6477
|
-
|
|
6478
|
-
|
|
6479
|
-
|
|
6480
|
-
|
|
6481
|
-
|
|
6482
|
-
|
|
6483
|
-
|
|
6484
|
-
|
|
6485
|
-
|
|
6486
|
-
|
|
6487
|
-
|
|
6488
|
-
|
|
6489
|
-
|
|
6490
|
-
|
|
6491
|
-
|
|
6492
|
-
|
|
6493
|
-
|
|
6494
|
-
|
|
6495
|
-
|
|
6496
|
-
|
|
6497
|
-
|
|
6498
|
-
|
|
6499
|
-
|
|
6500
|
-
|
|
6501
|
-
|
|
6502
|
-
|
|
6503
|
-
|
|
6504
|
-
|
|
6505
|
-
|
|
6506
|
-
|
|
6507
|
-
|
|
6508
|
-
|
|
6509
|
-
|
|
6510
|
-
|
|
6511
|
-
|
|
6512
|
-
|
|
6513
|
-
|
|
6514
|
-
|
|
6515
|
-
|
|
6516
|
-
),
|
|
6517
|
-
/* @__PURE__ */ jsx(
|
|
6518
|
-
"input",
|
|
6519
|
-
{
|
|
6520
|
-
type: "text",
|
|
6521
|
-
value: colors.bgColor,
|
|
6522
|
-
onChange: (e) => {
|
|
6523
|
-
const newColors = { ...colors, bgColor: e.target.value };
|
|
6524
|
-
setColors(newColors);
|
|
6525
|
-
handleUpdateCaption({ colors: newColors });
|
|
6526
|
-
},
|
|
6527
|
-
className: "color-text"
|
|
6528
|
-
}
|
|
6529
|
-
)
|
|
6530
|
-
] })
|
|
6531
|
-
] }),
|
|
6532
|
-
/* @__PURE__ */ jsxs("div", { className: "color-control", children: [
|
|
6533
|
-
/* @__PURE__ */ jsx("label", { className: "label-small", children: "Outline Color" }),
|
|
6534
|
-
/* @__PURE__ */ jsxs("div", { className: "color-inputs", children: [
|
|
6535
|
-
/* @__PURE__ */ jsx(
|
|
6536
|
-
"input",
|
|
6537
|
-
{
|
|
6538
|
-
type: "color",
|
|
6539
|
-
value: colors.outlineColor,
|
|
6540
|
-
onChange: (e) => {
|
|
6541
|
-
const newColors = { ...colors, outlineColor: e.target.value };
|
|
6542
|
-
setColors(newColors);
|
|
6543
|
-
handleUpdateCaption({ colors: newColors });
|
|
6544
|
-
},
|
|
6545
|
-
className: "color-picker"
|
|
6546
|
-
}
|
|
6547
|
-
),
|
|
6548
|
-
/* @__PURE__ */ jsx(
|
|
6549
|
-
"input",
|
|
6550
|
-
{
|
|
6551
|
-
type: "text",
|
|
6552
|
-
value: colors.outlineColor,
|
|
6553
|
-
onChange: (e) => {
|
|
6554
|
-
const newColors = { ...colors, outlineColor: e.target.value };
|
|
6555
|
-
setColors(newColors);
|
|
6556
|
-
handleUpdateCaption({ colors: newColors });
|
|
6557
|
-
},
|
|
6558
|
-
className: "color-text"
|
|
6559
|
-
}
|
|
6560
|
-
)
|
|
6561
|
-
] })
|
|
6562
|
-
] })
|
|
6708
|
+
currentColorMeta.usedColors.includes("highlight") && /* @__PURE__ */ jsx("div", { className: "checkbox-control", children: /* @__PURE__ */ jsxs("label", { className: "checkbox-label", children: [
|
|
6709
|
+
/* @__PURE__ */ jsx(
|
|
6710
|
+
"input",
|
|
6711
|
+
{
|
|
6712
|
+
type: "checkbox",
|
|
6713
|
+
checked: useHighlight,
|
|
6714
|
+
onChange: (e) => {
|
|
6715
|
+
const enabled = e.target.checked;
|
|
6716
|
+
setUseHighlight(enabled);
|
|
6717
|
+
const nextColors = enabled ? { ...colors, highlight: colors.highlight || CAPTION_COLOR2.highlight } : { ...colors };
|
|
6718
|
+
setColors(nextColors);
|
|
6719
|
+
handleUpdateCaption({
|
|
6720
|
+
colors: nextColors,
|
|
6721
|
+
useHighlightOverride: enabled
|
|
6722
|
+
});
|
|
6723
|
+
},
|
|
6724
|
+
className: "checkbox-purple"
|
|
6725
|
+
}
|
|
6726
|
+
),
|
|
6727
|
+
"Use Highlight Color"
|
|
6728
|
+
] }) }),
|
|
6729
|
+
currentColorMeta.usedColors.includes("outlineColor") && /* @__PURE__ */ jsx("div", { className: "checkbox-control", children: /* @__PURE__ */ jsxs("label", { className: "checkbox-label", children: [
|
|
6730
|
+
/* @__PURE__ */ jsx(
|
|
6731
|
+
"input",
|
|
6732
|
+
{
|
|
6733
|
+
type: "checkbox",
|
|
6734
|
+
checked: useOutline,
|
|
6735
|
+
onChange: (e) => {
|
|
6736
|
+
const enabled = e.target.checked;
|
|
6737
|
+
setUseOutline(enabled);
|
|
6738
|
+
const nextColors = enabled ? {
|
|
6739
|
+
...colors,
|
|
6740
|
+
outlineColor: colors.outlineColor || CAPTION_COLOR2.outlineColor
|
|
6741
|
+
} : { ...colors };
|
|
6742
|
+
setColors(nextColors);
|
|
6743
|
+
handleUpdateCaption({
|
|
6744
|
+
colors: nextColors,
|
|
6745
|
+
useOutlineOverride: enabled
|
|
6746
|
+
});
|
|
6747
|
+
},
|
|
6748
|
+
className: "checkbox-purple"
|
|
6749
|
+
}
|
|
6750
|
+
),
|
|
6751
|
+
"Use Outline Color"
|
|
6752
|
+
] }) }),
|
|
6753
|
+
currentColorMeta.usedColors.map((key) => renderColorControl(key))
|
|
6563
6754
|
] })
|
|
6564
6755
|
] })
|
|
6565
6756
|
] });
|
|
@@ -6753,6 +6944,8 @@ function GenerateCaptionsPanel({
|
|
|
6753
6944
|
const [isGenerating, setIsGenerating] = useState(false);
|
|
6754
6945
|
const [pollingStatus, setPollingStatus] = useState("idle");
|
|
6755
6946
|
const [errorMessage, setErrorMessage] = useState(null);
|
|
6947
|
+
const [selectedLanguage, setSelectedLanguage] = useState("auto");
|
|
6948
|
+
const [wordsPerPhrase, setWordsPerPhrase] = useState(4);
|
|
6756
6949
|
const pollingIntervalRef = useRef(null);
|
|
6757
6950
|
const currentReqIdRef = useRef(null);
|
|
6758
6951
|
useEffect(() => {
|
|
@@ -6813,7 +7006,12 @@ function GenerateCaptionsPanel({
|
|
|
6813
7006
|
setPollingStatus("polling");
|
|
6814
7007
|
const videoElement = selectedElement;
|
|
6815
7008
|
try {
|
|
6816
|
-
const
|
|
7009
|
+
const language = selectedLanguage === "auto" ? void 0 : selectedLanguage;
|
|
7010
|
+
const reqId = await onGenerateCaptions(
|
|
7011
|
+
videoElement,
|
|
7012
|
+
language,
|
|
7013
|
+
wordsPerPhrase
|
|
7014
|
+
);
|
|
6817
7015
|
if (!reqId) {
|
|
6818
7016
|
setPollingStatus("error");
|
|
6819
7017
|
setIsGenerating(false);
|
|
@@ -6872,6 +7070,46 @@ function GenerateCaptionsPanel({
|
|
|
6872
7070
|
/* @__PURE__ */ jsx(Volume2, { className: "empty-state-icon" }),
|
|
6873
7071
|
/* @__PURE__ */ jsx("p", { className: "empty-state-text", children: "Audio detected! You can now generate captions" })
|
|
6874
7072
|
] }) }) }),
|
|
7073
|
+
!isLoading && containsAudio === true && /* @__PURE__ */ jsxs("div", { className: "panel-section", children: [
|
|
7074
|
+
/* @__PURE__ */ jsx("label", { className: "label-dark", htmlFor: "caption-language", children: "Audio Language" }),
|
|
7075
|
+
/* @__PURE__ */ jsxs(
|
|
7076
|
+
"select",
|
|
7077
|
+
{
|
|
7078
|
+
id: "caption-language",
|
|
7079
|
+
className: "select-dark",
|
|
7080
|
+
value: selectedLanguage,
|
|
7081
|
+
onChange: (e) => setSelectedLanguage(e.target.value),
|
|
7082
|
+
children: [
|
|
7083
|
+
/* @__PURE__ */ jsx("option", { value: "auto", children: "Auto (detect)" }),
|
|
7084
|
+
/* @__PURE__ */ jsx("option", { value: "english", children: "English" }),
|
|
7085
|
+
/* @__PURE__ */ jsx("option", { value: "italian", children: "Italian" }),
|
|
7086
|
+
/* @__PURE__ */ jsx("option", { value: "spanish", children: "Spanish" }),
|
|
7087
|
+
/* @__PURE__ */ jsx("option", { value: "portuguese", children: "Portuguese" }),
|
|
7088
|
+
/* @__PURE__ */ jsx("option", { value: "french", children: "French" }),
|
|
7089
|
+
/* @__PURE__ */ jsx("option", { value: "german", children: "German" }),
|
|
7090
|
+
/* @__PURE__ */ jsx("option", { value: "turkish", children: "Turkish" }),
|
|
7091
|
+
/* @__PURE__ */ jsx("option", { value: "indonesian", children: "Indonesian" }),
|
|
7092
|
+
/* @__PURE__ */ jsx("option", { value: "hindi", children: "Hindi" })
|
|
7093
|
+
]
|
|
7094
|
+
}
|
|
7095
|
+
)
|
|
7096
|
+
] }),
|
|
7097
|
+
!isLoading && containsAudio === true && /* @__PURE__ */ jsxs("div", { className: "panel-section", children: [
|
|
7098
|
+
/* @__PURE__ */ jsx("label", { className: "label-dark", htmlFor: "caption-words-per-phrase", children: "Words per phrase" }),
|
|
7099
|
+
/* @__PURE__ */ jsx(
|
|
7100
|
+
"select",
|
|
7101
|
+
{
|
|
7102
|
+
id: "caption-words-per-phrase",
|
|
7103
|
+
className: "select-dark",
|
|
7104
|
+
value: String(wordsPerPhrase),
|
|
7105
|
+
onChange: (e) => setWordsPerPhrase(Number(e.target.value) || 4),
|
|
7106
|
+
children: Array.from({ length: 10 }).map((_, index) => {
|
|
7107
|
+
const value = index + 1;
|
|
7108
|
+
return /* @__PURE__ */ jsx("option", { value, children: value }, value);
|
|
7109
|
+
})
|
|
7110
|
+
}
|
|
7111
|
+
)
|
|
7112
|
+
] }),
|
|
6875
7113
|
!isLoading && isGenerating && pollingStatus === "polling" && /* @__PURE__ */ jsx("div", { className: "panel-section", children: /* @__PURE__ */ jsx("div", { className: "empty-state", children: /* @__PURE__ */ jsxs("div", { className: "empty-state-content", children: [
|
|
6876
7114
|
/* @__PURE__ */ jsx(LoaderCircle, { className: "empty-state-icon animate-spin" }),
|
|
6877
7115
|
/* @__PURE__ */ jsx("p", { className: "empty-state-text", children: "Generating captions... Please wait" })
|
|
@@ -7407,15 +7645,6 @@ const useStudioOperation = (studioConfig) => {
|
|
|
7407
7645
|
const fileName = `${(projectName || "chapters").replace(/\.json$/i, "")}.${format === "youtube" ? "txt" : "json"}`;
|
|
7408
7646
|
await saveAsFile(content, "text/plain", fileName);
|
|
7409
7647
|
};
|
|
7410
|
-
const onGenerateCaptions = async (videoElement) => {
|
|
7411
|
-
if (studioConfig == null ? void 0 : studioConfig.captionGenerationService) {
|
|
7412
|
-
const service = studioConfig.captionGenerationService;
|
|
7413
|
-
const reqId = await service.generateCaptions(videoElement, present);
|
|
7414
|
-
return reqId;
|
|
7415
|
-
}
|
|
7416
|
-
alert("Generate captions not supported in demo mode");
|
|
7417
|
-
return null;
|
|
7418
|
-
};
|
|
7419
7648
|
const addCaptionsToTimeline = (captions) => {
|
|
7420
7649
|
var _a;
|
|
7421
7650
|
const updatedProjectJSON = (_a = studioConfig == null ? void 0 : studioConfig.captionGenerationService) == null ? void 0 : _a.updateProjectWithCaptions(captions);
|
|
@@ -7440,7 +7669,6 @@ const useStudioOperation = (studioConfig) => {
|
|
|
7440
7669
|
onNewProject,
|
|
7441
7670
|
onExportCaptions,
|
|
7442
7671
|
onExportChapters,
|
|
7443
|
-
onGenerateCaptions,
|
|
7444
7672
|
addCaptionsToTimeline,
|
|
7445
7673
|
getCaptionstatus
|
|
7446
7674
|
};
|
|
@@ -7549,12 +7777,14 @@ function TwickStudio({ studioConfig }) {
|
|
|
7549
7777
|
const useGenerateCaptions = (studioConfig) => {
|
|
7550
7778
|
var _a;
|
|
7551
7779
|
const { editor, present } = useTimelineContext();
|
|
7552
|
-
const onGenerateCaptions = async (videoElement) => {
|
|
7780
|
+
const onGenerateCaptions = async (videoElement, language, wordsPerPhrase) => {
|
|
7553
7781
|
if (studioConfig == null ? void 0 : studioConfig.captionGenerationService) {
|
|
7554
7782
|
const service = studioConfig.captionGenerationService;
|
|
7555
7783
|
const reqId = await service.generateCaptions(
|
|
7556
7784
|
videoElement,
|
|
7557
|
-
present
|
|
7785
|
+
present,
|
|
7786
|
+
language,
|
|
7787
|
+
wordsPerPhrase
|
|
7558
7788
|
);
|
|
7559
7789
|
return reqId;
|
|
7560
7790
|
}
|