@twick/timeline 0.14.6 → 0.14.8
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/core/editor/timeline.editor.d.ts +1 -0
- package/dist/core/elements/text.element.d.ts +3 -1
- package/dist/core/track/track.d.ts +4 -0
- package/dist/core/visitor/element-validator.d.ts +8 -0
- package/dist/index.js +61 -13
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +61 -13
- package/dist/index.mjs.map +1 -1
- package/dist/types.d.ts +8 -1
- package/package.json +4 -4
package/dist/index.mjs
CHANGED
|
@@ -991,13 +991,14 @@ class ImageElement extends TrackElement {
|
|
|
991
991
|
}
|
|
992
992
|
}
|
|
993
993
|
class TextElement extends TrackElement {
|
|
994
|
-
constructor(text) {
|
|
994
|
+
constructor(text, props) {
|
|
995
995
|
super(TIMELINE_ELEMENT_TYPE.TEXT);
|
|
996
996
|
__publicField(this, "textEffect");
|
|
997
997
|
this.props = {
|
|
998
998
|
text,
|
|
999
|
-
fill: "#888888"
|
|
1000
|
-
//default-grey
|
|
999
|
+
fill: "#888888",
|
|
1000
|
+
//default-grey,
|
|
1001
|
+
...props || {}
|
|
1001
1002
|
};
|
|
1002
1003
|
}
|
|
1003
1004
|
getTextEffect() {
|
|
@@ -1012,6 +1013,9 @@ class TextElement extends TrackElement {
|
|
|
1012
1013
|
getLineWidth() {
|
|
1013
1014
|
return this.props.lineWidth;
|
|
1014
1015
|
}
|
|
1016
|
+
getProps() {
|
|
1017
|
+
return this.props;
|
|
1018
|
+
}
|
|
1015
1019
|
setText(text) {
|
|
1016
1020
|
this.props.text = text;
|
|
1017
1021
|
return this;
|
|
@@ -1056,6 +1060,10 @@ class TextElement extends TrackElement {
|
|
|
1056
1060
|
this.props.lineWidth = lineWidth;
|
|
1057
1061
|
return this;
|
|
1058
1062
|
}
|
|
1063
|
+
setProps(props) {
|
|
1064
|
+
this.props = structuredClone(props);
|
|
1065
|
+
return this;
|
|
1066
|
+
}
|
|
1059
1067
|
accept(visitor) {
|
|
1060
1068
|
return visitor.visitTextElement(this);
|
|
1061
1069
|
}
|
|
@@ -1118,6 +1126,8 @@ class CircleElement extends TrackElement {
|
|
|
1118
1126
|
super(TIMELINE_ELEMENT_TYPE.CIRCLE);
|
|
1119
1127
|
this.props = {
|
|
1120
1128
|
radius,
|
|
1129
|
+
height: radius * 2,
|
|
1130
|
+
width: radius * 2,
|
|
1121
1131
|
fill,
|
|
1122
1132
|
strokeColor: fill,
|
|
1123
1133
|
lineWidth: 1
|
|
@@ -1141,6 +1151,8 @@ class CircleElement extends TrackElement {
|
|
|
1141
1151
|
}
|
|
1142
1152
|
setRadius(radius) {
|
|
1143
1153
|
this.props.radius = radius;
|
|
1154
|
+
this.props.width = radius * 2;
|
|
1155
|
+
this.props.height = radius * 2;
|
|
1144
1156
|
return this;
|
|
1145
1157
|
}
|
|
1146
1158
|
setStrokeColor(strokeColor) {
|
|
@@ -1560,6 +1572,14 @@ class ElementSerializer {
|
|
|
1560
1572
|
};
|
|
1561
1573
|
}
|
|
1562
1574
|
}
|
|
1575
|
+
const VALIDATION_ERROR_CODE = {
|
|
1576
|
+
ELEMENT_NOT_FOUND: "ELEMENT_NOT_FOUND",
|
|
1577
|
+
ELEMENT_NOT_ADDED: "ELEMENT_NOT_ADDED",
|
|
1578
|
+
ELEMENT_NOT_UPDATED: "ELEMENT_NOT_UPDATED",
|
|
1579
|
+
ELEMENT_NOT_REMOVED: "ELEMENT_NOT_REMOVED",
|
|
1580
|
+
COLLISION_ERROR: "COLLISION_ERROR",
|
|
1581
|
+
INVALID_TIMING: "INVALID_TIMING"
|
|
1582
|
+
};
|
|
1563
1583
|
class ValidationError extends Error {
|
|
1564
1584
|
constructor(message, errors, warnings = []) {
|
|
1565
1585
|
super(message);
|
|
@@ -1662,8 +1682,8 @@ class ElementValidator {
|
|
|
1662
1682
|
const basicValidation = this.validateBasicProperties(element);
|
|
1663
1683
|
const errors = [...basicValidation.errors];
|
|
1664
1684
|
const warnings = [...basicValidation.warnings];
|
|
1665
|
-
const
|
|
1666
|
-
if (!
|
|
1685
|
+
const text = element.getText();
|
|
1686
|
+
if (!text || text.trim() === "") {
|
|
1667
1687
|
errors.push("Caption element must have text content");
|
|
1668
1688
|
}
|
|
1669
1689
|
return { errors, warnings };
|
|
@@ -1840,11 +1860,13 @@ class Track {
|
|
|
1840
1860
|
__publicField(this, "id");
|
|
1841
1861
|
__publicField(this, "name");
|
|
1842
1862
|
__publicField(this, "type");
|
|
1863
|
+
__publicField(this, "props");
|
|
1843
1864
|
__publicField(this, "elements");
|
|
1844
1865
|
__publicField(this, "validator");
|
|
1845
1866
|
this.name = name;
|
|
1846
1867
|
this.id = id ?? `t-${generateShortUuid}`;
|
|
1847
1868
|
this.type = type;
|
|
1869
|
+
this.props = {};
|
|
1848
1870
|
this.elements = [];
|
|
1849
1871
|
this.validator = new ElementValidator();
|
|
1850
1872
|
}
|
|
@@ -1990,6 +2012,13 @@ class Track {
|
|
|
1990
2012
|
getElements() {
|
|
1991
2013
|
return [...this.elements];
|
|
1992
2014
|
}
|
|
2015
|
+
getProps() {
|
|
2016
|
+
return this.props;
|
|
2017
|
+
}
|
|
2018
|
+
setProps(props) {
|
|
2019
|
+
this.props = structuredClone(props);
|
|
2020
|
+
return this;
|
|
2021
|
+
}
|
|
1993
2022
|
/**
|
|
1994
2023
|
* Validates a single element using the track's validator.
|
|
1995
2024
|
* Checks if the element meets all validation requirements.
|
|
@@ -2063,17 +2092,21 @@ class Track {
|
|
|
2063
2092
|
try {
|
|
2064
2093
|
const isValid = this.validateElement(element);
|
|
2065
2094
|
if (isValid) {
|
|
2066
|
-
this.
|
|
2067
|
-
|
|
2095
|
+
if (this.isElementColliding(element)) {
|
|
2096
|
+
throw new ValidationError("Element is colliding with another element", ["COLLISION_ERROR"]);
|
|
2097
|
+
} else {
|
|
2098
|
+
this.elements.push(element);
|
|
2099
|
+
return true;
|
|
2100
|
+
}
|
|
2068
2101
|
}
|
|
2069
2102
|
} catch (error) {
|
|
2070
|
-
if (error instanceof ValidationError) {
|
|
2071
|
-
throw error;
|
|
2072
|
-
}
|
|
2073
2103
|
throw error;
|
|
2074
2104
|
}
|
|
2075
2105
|
return false;
|
|
2076
2106
|
}
|
|
2107
|
+
isElementColliding(element) {
|
|
2108
|
+
return this.elements.some((e2) => e2.getStart() < element.getEnd() && e2.getEnd() > element.getStart());
|
|
2109
|
+
}
|
|
2077
2110
|
/**
|
|
2078
2111
|
* Removes an element from the track.
|
|
2079
2112
|
* Protected method that should be accessed through TrackFriend.
|
|
@@ -2242,6 +2275,7 @@ class Track {
|
|
|
2242
2275
|
id: this.id,
|
|
2243
2276
|
name: this.name,
|
|
2244
2277
|
type: this.type,
|
|
2278
|
+
props: this.props,
|
|
2245
2279
|
elements: this.elements.map(
|
|
2246
2280
|
(element) => element.accept(serializer)
|
|
2247
2281
|
)
|
|
@@ -2279,6 +2313,7 @@ class Track {
|
|
|
2279
2313
|
static fromJSON(json) {
|
|
2280
2314
|
const track = new Track(json.name, json.type ?? "element", json.id);
|
|
2281
2315
|
track.type = json.type;
|
|
2316
|
+
track.props = json.props;
|
|
2282
2317
|
track.elements = (json.elements || []).map(ElementDeserializer.fromJSON);
|
|
2283
2318
|
return track;
|
|
2284
2319
|
}
|
|
@@ -2919,6 +2954,11 @@ class TimelineEditor {
|
|
|
2919
2954
|
const track = prevTimelineData == null ? void 0 : prevTimelineData.tracks.find((t2) => t2.getName() === name);
|
|
2920
2955
|
return track;
|
|
2921
2956
|
}
|
|
2957
|
+
getSubtiltesTrack() {
|
|
2958
|
+
const prevTimelineData = this.getTimelineData();
|
|
2959
|
+
const track = prevTimelineData == null ? void 0 : prevTimelineData.tracks.find((t2) => t2.getType() === "caption");
|
|
2960
|
+
return track;
|
|
2961
|
+
}
|
|
2922
2962
|
removeTrackById(id) {
|
|
2923
2963
|
var _a;
|
|
2924
2964
|
const tracks = ((_a = this.getTimelineData()) == null ? void 0 : _a.tracks) || [];
|
|
@@ -2947,8 +2987,9 @@ class TimelineEditor {
|
|
|
2947
2987
|
* @returns Promise<boolean> true if element was added successfully
|
|
2948
2988
|
*/
|
|
2949
2989
|
async addElementToTrack(track, element) {
|
|
2990
|
+
var _a;
|
|
2950
2991
|
if (!track) {
|
|
2951
|
-
|
|
2992
|
+
throw new Error("TRACK_NOT_FOUND");
|
|
2952
2993
|
}
|
|
2953
2994
|
try {
|
|
2954
2995
|
const elementAdder = new ElementAdder(track);
|
|
@@ -2958,10 +2999,16 @@ class TimelineEditor {
|
|
|
2958
2999
|
if (currentData) {
|
|
2959
3000
|
this.setTimelineData({ tracks: currentData.tracks, updatePlayerData: true });
|
|
2960
3001
|
}
|
|
3002
|
+
return true;
|
|
3003
|
+
} else {
|
|
3004
|
+
return false;
|
|
2961
3005
|
}
|
|
2962
|
-
return result;
|
|
2963
3006
|
} catch (error) {
|
|
2964
|
-
|
|
3007
|
+
if (error instanceof ValidationError && ((_a = error.errors) == null ? void 0 : _a.length) > 0) {
|
|
3008
|
+
throw error;
|
|
3009
|
+
} else {
|
|
3010
|
+
throw new Error("ELEMENT_NOT_ADDED");
|
|
3011
|
+
}
|
|
2965
3012
|
}
|
|
2966
3013
|
}
|
|
2967
3014
|
/**
|
|
@@ -8013,6 +8060,7 @@ export {
|
|
|
8013
8060
|
TimelineProvider,
|
|
8014
8061
|
Track,
|
|
8015
8062
|
TrackElement,
|
|
8063
|
+
VALIDATION_ERROR_CODE,
|
|
8016
8064
|
ValidationError,
|
|
8017
8065
|
VideoElement,
|
|
8018
8066
|
WORDS_PER_PHRASE,
|