lexgui 0.6.4 → 0.6.5
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/build/components/codeeditor.js +10 -10
- package/build/components/nodegraph.js +12 -12
- package/build/components/timeline.js +170 -175
- package/build/lexgui.js +1219 -1130
- package/build/lexgui.min.js +1 -1
- package/build/lexgui.module.js +1235 -1146
- package/build/lexgui.module.min.js +1 -1
- package/changelog.md +13 -1
- package/demo.js +1 -1
- package/examples/all_widgets.html +1 -1
- package/examples/editor.html +1 -1
- package/package.json +1 -1
|
@@ -1010,9 +1010,9 @@ class Timeline {
|
|
|
1010
1010
|
* [ trackIdx ]
|
|
1011
1011
|
* @param {Array} itemsName array of numbers identifying tracks
|
|
1012
1012
|
*/
|
|
1013
|
-
setSelectedItems( items ) {
|
|
1013
|
+
setSelectedItems( items, skipCallback = false ) {
|
|
1014
1014
|
this.selectedItems = [];
|
|
1015
|
-
this.changeSelectedItems( items, null );
|
|
1015
|
+
this.changeSelectedItems( items, null, skipCallback );
|
|
1016
1016
|
}
|
|
1017
1017
|
|
|
1018
1018
|
/**
|
|
@@ -1101,7 +1101,11 @@ class Timeline {
|
|
|
1101
1101
|
tracks[ i ].isSelected = false;
|
|
1102
1102
|
}
|
|
1103
1103
|
}
|
|
1104
|
-
|
|
1104
|
+
|
|
1105
|
+
unselectAllElements(){
|
|
1106
|
+
|
|
1107
|
+
}
|
|
1108
|
+
|
|
1105
1109
|
/**
|
|
1106
1110
|
* @method setTrackState
|
|
1107
1111
|
* @param {int} trackIdx
|
|
@@ -1117,6 +1121,62 @@ class Timeline {
|
|
|
1117
1121
|
this.onSetTrackState(track, oldState);
|
|
1118
1122
|
}
|
|
1119
1123
|
|
|
1124
|
+
/**
|
|
1125
|
+
* @param {Number} trackIdx index of track in the animation (not local index)
|
|
1126
|
+
* @param {Bool} combineWithPrevious whether to create a new entry or unify changes into a single undo entry
|
|
1127
|
+
*/
|
|
1128
|
+
saveState( trackIdx, combineWithPrevious = false ) {
|
|
1129
|
+
if ( !this.historySaveEnabler ){ return; }
|
|
1130
|
+
|
|
1131
|
+
const undoStep = this.historyGenerateTrackStep( trackIdx );
|
|
1132
|
+
undoStep.trackIdx = trackIdx;
|
|
1133
|
+
|
|
1134
|
+
if ( combineWithPrevious && this.historyUndo.length ){
|
|
1135
|
+
this.historyUndo[ this.historyUndo.length - 1 ].push( undoStep );
|
|
1136
|
+
}
|
|
1137
|
+
else{
|
|
1138
|
+
this.historyUndo.push( [undoStep] );
|
|
1139
|
+
}
|
|
1140
|
+
|
|
1141
|
+
if ( this.historyUndo.length > this.historyMaxSteps ){ this.historyUndo.shift(); } // remove first (oldest) element
|
|
1142
|
+
this.historyRedo = [];
|
|
1143
|
+
}
|
|
1144
|
+
|
|
1145
|
+
#undoRedo(isUndo = true) {
|
|
1146
|
+
|
|
1147
|
+
let toBeShown = isUndo ? this.historyUndo : this.historyRedo;
|
|
1148
|
+
let toBeStored = isUndo ? this.historyRedo : this.historyUndo;
|
|
1149
|
+
|
|
1150
|
+
if (!toBeShown.length){ return false; }
|
|
1151
|
+
|
|
1152
|
+
this.unselectAllElements();
|
|
1153
|
+
|
|
1154
|
+
const combinedState = toBeShown.pop();
|
|
1155
|
+
const combinedStateToStore = [];
|
|
1156
|
+
|
|
1157
|
+
for( let i = 0; i < combinedState.length; ++i ){
|
|
1158
|
+
const state = combinedState[i];
|
|
1159
|
+
const trackIdx = state.trackIdx;
|
|
1160
|
+
|
|
1161
|
+
const stateToStore = this.historyApplyTrackStep( state, isUndo );
|
|
1162
|
+
stateToStore.trackIdx = trackIdx;
|
|
1163
|
+
combinedStateToStore.push( stateToStore );
|
|
1164
|
+
|
|
1165
|
+
// Update animation action interpolation info
|
|
1166
|
+
if(this.onUpdateTrack)
|
|
1167
|
+
this.onUpdateTrack( [state.trackIdx] );
|
|
1168
|
+
}
|
|
1169
|
+
|
|
1170
|
+
toBeStored.push(combinedStateToStore);
|
|
1171
|
+
|
|
1172
|
+
return true;
|
|
1173
|
+
}
|
|
1174
|
+
|
|
1175
|
+
undo() { return this.#undoRedo(true); }
|
|
1176
|
+
redo() { return this.#undoRedo(false); }
|
|
1177
|
+
// historyApplyTrackStep( state, isUndo ) MUST BE IMPLEMENTED BY CHILD CLASS
|
|
1178
|
+
// historyGenerateTrackStep( trackIdx ) MUST BE IMPLEMENTED BY CHILD CLASS
|
|
1179
|
+
|
|
1120
1180
|
/**
|
|
1121
1181
|
* @method resize
|
|
1122
1182
|
* @param {*} size
|
|
@@ -1185,6 +1245,7 @@ class Timeline {
|
|
|
1185
1245
|
Usually call a super.whateverFunction to generate its base form, and expand it with extra attributes
|
|
1186
1246
|
*/
|
|
1187
1247
|
|
|
1248
|
+
|
|
1188
1249
|
/**
|
|
1189
1250
|
* This functions uses the selectedItems and generates the data that will feed the LX.Tree widget.
|
|
1190
1251
|
* This function is used by updateLeftPanel. Some timelines might allow grouping of tracks. Such timelines may overwrite this function
|
|
@@ -1249,7 +1310,7 @@ class Timeline {
|
|
|
1249
1310
|
instantiateAnimationClip(options) {
|
|
1250
1311
|
options = options ?? {};
|
|
1251
1312
|
const animationClip = {
|
|
1252
|
-
|
|
1313
|
+
id: options.id ?? (options.name ?? "animationClip"),
|
|
1253
1314
|
duration: options.duration ?? 0,
|
|
1254
1315
|
tracks: [],
|
|
1255
1316
|
tracksPerGroup: options.tracksPerGroup ?? {},
|
|
@@ -1315,25 +1376,6 @@ class KeyFramesTimeline extends Timeline {
|
|
|
1315
1376
|
}
|
|
1316
1377
|
}
|
|
1317
1378
|
|
|
1318
|
-
|
|
1319
|
-
/**
|
|
1320
|
-
* @param {object} options options for the new track
|
|
1321
|
-
* { id: string, active: bool, locked: bool, }
|
|
1322
|
-
* @returns
|
|
1323
|
-
*/
|
|
1324
|
-
addNewTrack( options = {}, skipCallback = false ) {
|
|
1325
|
-
|
|
1326
|
-
const trackInfo = this.instantiateTrack(options);
|
|
1327
|
-
trackInfo.trackIdx = this.animationClip.tracks.length;
|
|
1328
|
-
this.animationClip.tracks.push( trackInfo );
|
|
1329
|
-
|
|
1330
|
-
if ( this.onAddNewTrack && !skipCallback ){
|
|
1331
|
-
this.onAddNewTrack( trackInfo, options ); // if user wants it on a group, they should use these callback
|
|
1332
|
-
}
|
|
1333
|
-
|
|
1334
|
-
return trackInfo.trackIdx;
|
|
1335
|
-
}
|
|
1336
|
-
|
|
1337
1379
|
// OVERRIDE
|
|
1338
1380
|
generateSelectedItemsTreeData(){
|
|
1339
1381
|
const treeTracks = [];
|
|
@@ -1495,6 +1537,12 @@ class KeyFramesTimeline extends Timeline {
|
|
|
1495
1537
|
return animationClip;
|
|
1496
1538
|
}
|
|
1497
1539
|
|
|
1540
|
+
// OVERRIDE
|
|
1541
|
+
unselectAllElements(){
|
|
1542
|
+
this.unSelectAllKeyFrames();
|
|
1543
|
+
this.unHoverAll();
|
|
1544
|
+
}
|
|
1545
|
+
|
|
1498
1546
|
/**
|
|
1499
1547
|
* OVERRIDE
|
|
1500
1548
|
* @param {*} itemsToAdd [ trackIdx, "groupId" ], array of strings and/or number identifying groups and/or tracks
|
|
@@ -2304,78 +2352,52 @@ class KeyFramesTimeline extends Timeline {
|
|
|
2304
2352
|
})
|
|
2305
2353
|
});
|
|
2306
2354
|
}
|
|
2307
|
-
|
|
2355
|
+
|
|
2308
2356
|
/**
|
|
2309
|
-
*
|
|
2310
|
-
* @param {
|
|
2357
|
+
* saveState function uses this to generate a "copy" of the track.
|
|
2358
|
+
* @param {Number} trackIdx
|
|
2359
|
+
* @returns All necessary information to reconstruct the track state
|
|
2311
2360
|
*/
|
|
2312
|
-
|
|
2313
|
-
if ( !this.historySaveEnabler ){ return; }
|
|
2314
|
-
|
|
2361
|
+
historyGenerateTrackStep( trackIdx ){
|
|
2315
2362
|
const trackInfo = this.animationClip.tracks[trackIdx];
|
|
2316
2363
|
|
|
2317
2364
|
const undoStep = {
|
|
2318
|
-
|
|
2319
|
-
|
|
2320
|
-
|
|
2321
|
-
|
|
2365
|
+
trackIdx: trackIdx, // already done by saveState
|
|
2366
|
+
t: trackInfo.times.slice(),
|
|
2367
|
+
v: trackInfo.values.slice(),
|
|
2368
|
+
edited: trackInfo.edited.slice(0, trackInfo.times.length)
|
|
2322
2369
|
};
|
|
2323
2370
|
|
|
2324
|
-
|
|
2325
|
-
|
|
2326
|
-
}
|
|
2327
|
-
else{
|
|
2328
|
-
this.historyUndo.push( [undoStep] );
|
|
2329
|
-
}
|
|
2371
|
+
return undoStep;
|
|
2372
|
+
}
|
|
2330
2373
|
|
|
2331
|
-
|
|
2332
|
-
|
|
2333
|
-
|
|
2334
|
-
|
|
2335
|
-
|
|
2336
|
-
|
|
2337
|
-
|
|
2338
|
-
|
|
2339
|
-
|
|
2340
|
-
|
|
2341
|
-
|
|
2342
|
-
|
|
2343
|
-
|
|
2344
|
-
|
|
2345
|
-
|
|
2346
|
-
|
|
2347
|
-
|
|
2348
|
-
for( let i = 0; i < combinedState.length; ++i ){
|
|
2349
|
-
const state = combinedState[i];
|
|
2350
|
-
const track = this.animationClip.tracks[state.trackIdx];
|
|
2351
|
-
|
|
2352
|
-
// same as savestate
|
|
2353
|
-
combinedStateToStore.push({
|
|
2354
|
-
trackIdx: state.trackIdx,
|
|
2355
|
-
t: track.times,
|
|
2356
|
-
v: track.values,
|
|
2357
|
-
edited: track.edited
|
|
2358
|
-
});
|
|
2359
|
-
|
|
2360
|
-
track.times = state.t;
|
|
2361
|
-
track.values = state.v;
|
|
2362
|
-
track.edited = state.edited;
|
|
2363
|
-
if ( track.selected.length != track.times.length ){ track.selected.length = track.times.length; }
|
|
2364
|
-
if ( track.hovered.length != track.times.length ){ track.hovered.length = track.times.length; }
|
|
2365
|
-
track.selected.fill(false);
|
|
2366
|
-
track.hovered.fill(false);
|
|
2367
|
-
|
|
2368
|
-
if(this.onUpdateTrack)
|
|
2369
|
-
this.onUpdateTrack( [state.trackIdx] );
|
|
2370
|
-
}
|
|
2374
|
+
/**
|
|
2375
|
+
* It should swap the previous state with the incoming state of the track. It must return the previous state.
|
|
2376
|
+
* historyGenerateTrackStep could be used to copy the previous state. However, as it is a swap, it suffices to just copy the references.
|
|
2377
|
+
* @param {Object} state object with a trackIdx:Number and whatever information was saved in historyGenerateTrackStep
|
|
2378
|
+
* @param {Boolean} isUndo
|
|
2379
|
+
* @returns previous state object
|
|
2380
|
+
*/
|
|
2381
|
+
historyApplyTrackStep( state, isUndo ){
|
|
2382
|
+
const track = this.animationClip.tracks[state.trackIdx];
|
|
2383
|
+
|
|
2384
|
+
const stateToReturn = {
|
|
2385
|
+
trackIdx: state.trackIdx,
|
|
2386
|
+
t: track.times,
|
|
2387
|
+
v: track.values,
|
|
2388
|
+
edited: track.edited
|
|
2389
|
+
};
|
|
2371
2390
|
|
|
2372
|
-
|
|
2391
|
+
track.times = state.t;
|
|
2392
|
+
track.values = state.v;
|
|
2393
|
+
track.edited = state.edited;
|
|
2394
|
+
if ( track.selected.length != track.times.length ){ track.selected.length = track.times.length; }
|
|
2395
|
+
if ( track.hovered.length != track.times.length ){ track.hovered.length = track.times.length; }
|
|
2396
|
+
track.selected.fill(false);
|
|
2397
|
+
track.hovered.fill(false);
|
|
2373
2398
|
|
|
2374
|
-
return
|
|
2399
|
+
return stateToReturn;
|
|
2375
2400
|
}
|
|
2376
|
-
|
|
2377
|
-
undo() { return this.#undoRedo(true); }
|
|
2378
|
-
redo() { return this.#undoRedo(false); }
|
|
2379
2401
|
|
|
2380
2402
|
/**
|
|
2381
2403
|
*
|
|
@@ -3079,6 +3101,12 @@ class ClipsTimeline extends Timeline {
|
|
|
3079
3101
|
this.changeSelectedItems();
|
|
3080
3102
|
}
|
|
3081
3103
|
|
|
3104
|
+
// OVERRIDE
|
|
3105
|
+
unselectAllElements(){
|
|
3106
|
+
this.unSelectAllClips();
|
|
3107
|
+
this.unHoverAll();
|
|
3108
|
+
}
|
|
3109
|
+
|
|
3082
3110
|
/**
|
|
3083
3111
|
* OVERRIDE ITEM SELECTION.
|
|
3084
3112
|
* CLIPS WILL OFFER NO SELECTION. All tracks are visible
|
|
@@ -3363,7 +3391,7 @@ class ClipsTimeline extends Timeline {
|
|
|
3363
3391
|
|
|
3364
3392
|
// save track state if necessary
|
|
3365
3393
|
const undoState = this.historyUndo[this.historyUndo.length-1];
|
|
3366
|
-
let state = 0
|
|
3394
|
+
let state = 0;
|
|
3367
3395
|
for( ; state < undoState.length; ++state ){
|
|
3368
3396
|
if ( newTrackIdx == undoState[state].trackIdx ){ break; }
|
|
3369
3397
|
}
|
|
@@ -3554,8 +3582,10 @@ class ClipsTimeline extends Timeline {
|
|
|
3554
3582
|
const track = e.track;
|
|
3555
3583
|
const localX = e.localX;
|
|
3556
3584
|
|
|
3557
|
-
|
|
3558
|
-
|
|
3585
|
+
if ( track ){
|
|
3586
|
+
const clipIdx = this.getClipOnTime(track, this.xToTime(localX), 0.001);
|
|
3587
|
+
this.selectClip(track.trackIdx, clipIdx); // unselect and try to select clip in localX, if any
|
|
3588
|
+
}
|
|
3559
3589
|
}
|
|
3560
3590
|
|
|
3561
3591
|
showContextMenu( e ) {
|
|
@@ -3751,9 +3781,10 @@ class ClipsTimeline extends Timeline {
|
|
|
3751
3781
|
* @param {obj} clip clip to be added
|
|
3752
3782
|
* @param {int} trackIdx (optional) track where to put the clip. -1 will find the first free slot. ***WARNING*** Must call getClipsInRange, before calling this function with a valid trackdIdx
|
|
3753
3783
|
* @param {float} offsetTime (optional) offset time of current time
|
|
3784
|
+
* @param {float} searchStartTrackIdx (optional) if trackIdx is set to -1, this idx will be used as the starting point to find a valid track
|
|
3754
3785
|
* @returns a zero/positive value if successful. Otherwise, -1
|
|
3755
3786
|
*/
|
|
3756
|
-
addClip( clip, trackIdx = -1, offsetTime = 0 ) {
|
|
3787
|
+
addClip( clip, trackIdx = -1, offsetTime = 0, searchStartTrackIdx = 0 ) {
|
|
3757
3788
|
if ( !this.animationClip ){ return -1; }
|
|
3758
3789
|
|
|
3759
3790
|
// Update clip information
|
|
@@ -3769,9 +3800,9 @@ class ClipsTimeline extends Timeline {
|
|
|
3769
3800
|
trackIdx = this.addNewTrack();
|
|
3770
3801
|
}
|
|
3771
3802
|
else if ( trackIdx < 0 ){ // find first free track slot
|
|
3772
|
-
for(let i =
|
|
3803
|
+
for(let i = searchStartTrackIdx; i < this.animationClip.tracks.length; i++) {
|
|
3773
3804
|
let clipInCurrentSlot = this.animationClip.tracks[i].clips.find( t => {
|
|
3774
|
-
return LX.
|
|
3805
|
+
return LX.compareThresholdRange(newStart, clip.start + clip.duration, t.start, t.start+t.duration);
|
|
3775
3806
|
});
|
|
3776
3807
|
|
|
3777
3808
|
if(!clipInCurrentSlot){
|
|
@@ -3823,17 +3854,18 @@ class ClipsTimeline extends Timeline {
|
|
|
3823
3854
|
return newIdx;
|
|
3824
3855
|
}
|
|
3825
3856
|
|
|
3826
|
-
|
|
3827
|
-
|
|
3828
|
-
* @
|
|
3829
|
-
* @
|
|
3830
|
-
|
|
3831
|
-
|
|
3832
|
-
|
|
3857
|
+
/**
|
|
3858
|
+
* Add an array of clips to the timeline in the first suitable tracks. It tries to put clips in the same track if possible. All clips will be in adjacent tracks to each other
|
|
3859
|
+
* @param {Array of objects} clips
|
|
3860
|
+
* @param {Number} offsetTime
|
|
3861
|
+
* @param {Int} searchStartTrackIdx
|
|
3862
|
+
* @returns
|
|
3863
|
+
*/
|
|
3864
|
+
addClips( clips, offsetTime = 0, searchStartTrackIdx = 0 ){
|
|
3833
3865
|
if( !this.animationClip || !clips.length ){ return false; }
|
|
3834
3866
|
|
|
3835
3867
|
let clipTrackIdxs = new Int16Array( clips.length );
|
|
3836
|
-
let baseTrackIdx = -1;
|
|
3868
|
+
let baseTrackIdx = searchStartTrackIdx -1; // every time the algorithm fails, it increments the starting track Idx
|
|
3837
3869
|
let currTrackIdx = -1;
|
|
3838
3870
|
const tracks = this.animationClip.tracks;
|
|
3839
3871
|
const lastTrackLength = tracks.length;
|
|
@@ -3845,9 +3877,10 @@ class ClipsTimeline extends Timeline {
|
|
|
3845
3877
|
if ( c == 0 ){ // last search failed, move one track down and check again
|
|
3846
3878
|
++baseTrackIdx;
|
|
3847
3879
|
currTrackIdx = baseTrackIdx;
|
|
3848
|
-
|
|
3849
|
-
|
|
3850
|
-
|
|
3880
|
+
|
|
3881
|
+
while ( currTrackIdx >= tracks.length ){ this.addNewTrack(null, false); }
|
|
3882
|
+
let clipsInCurrentSlot = tracks[baseTrackIdx].clips.find( t => { return LX.compareThresholdRange(clipStart, clipEnd, t.start, t.start+t.duration); });
|
|
3883
|
+
|
|
3851
3884
|
// reset search
|
|
3852
3885
|
if (clipsInCurrentSlot){
|
|
3853
3886
|
c = -1;
|
|
@@ -3859,19 +3892,19 @@ class ClipsTimeline extends Timeline {
|
|
|
3859
3892
|
}else{
|
|
3860
3893
|
|
|
3861
3894
|
// check if it fits in current track
|
|
3862
|
-
let clipsInCurrentSlot = tracks[currTrackIdx].clips.find( t => { return LX.
|
|
3895
|
+
let clipsInCurrentSlot = tracks[currTrackIdx].clips.find( t => { return LX.compareThresholdRange(clipStart, clipEnd, t.start, t.start+t.duration); });
|
|
3863
3896
|
|
|
3864
3897
|
// check no previous added clips are in the way
|
|
3865
3898
|
for( let i = c-1; i > -1; --i ){
|
|
3866
3899
|
if ( clipTrackIdxs[i] != currTrackIdx || clipsInCurrentSlot ){ break; }
|
|
3867
|
-
clipsInCurrentSlot = LX.
|
|
3900
|
+
clipsInCurrentSlot = LX.compareThresholdRange(clipStart, clipEnd, clips[i].start + offsetTime, clips[i].start + offsetTime + clips[i].duration);
|
|
3868
3901
|
}
|
|
3869
3902
|
|
|
3870
3903
|
// check if it fits in the next track
|
|
3871
3904
|
if ( clipsInCurrentSlot ){
|
|
3872
3905
|
++currTrackIdx;
|
|
3873
3906
|
if ( currTrackIdx >= tracks.length ){ this.addNewTrack(null, false); }
|
|
3874
|
-
clipsInCurrentSlot = tracks[currTrackIdx].clips.find( t => { return LX.
|
|
3907
|
+
clipsInCurrentSlot = tracks[currTrackIdx].clips.find( t => { return LX.compareThresholdRange(clipStart, clipEnd, t.start, t.start+t.duration); });
|
|
3875
3908
|
}
|
|
3876
3909
|
|
|
3877
3910
|
// reset search
|
|
@@ -4077,75 +4110,50 @@ class ClipsTimeline extends Timeline {
|
|
|
4077
4110
|
return;
|
|
4078
4111
|
}
|
|
4079
4112
|
|
|
4080
|
-
|
|
4081
|
-
|
|
4082
|
-
|
|
4113
|
+
/**
|
|
4114
|
+
* saveState function uses this to generate a "copy" of the track.
|
|
4115
|
+
* @param {Number} trackIdx
|
|
4116
|
+
* @returns All necessary information to reconstruct the track state
|
|
4117
|
+
*/
|
|
4118
|
+
historyGenerateTrackStep( trackIdx ){
|
|
4083
4119
|
const track = this.animationClip.tracks[trackIdx];
|
|
4084
4120
|
const clips = this.cloneClips(track.clips, 0);
|
|
4085
|
-
// storing as array so multiple tracks can be in a same "undo" step
|
|
4086
4121
|
|
|
4087
|
-
const undoStep = {
|
|
4088
|
-
trackIdx: trackIdx,
|
|
4122
|
+
const undoStep = {
|
|
4123
|
+
trackIdx: trackIdx, // already done by saveState
|
|
4089
4124
|
clips: clips,
|
|
4090
4125
|
edited: track.edited.slice(0,track.clips.length)
|
|
4091
4126
|
};
|
|
4092
4127
|
|
|
4093
|
-
|
|
4094
|
-
|
|
4095
|
-
}
|
|
4096
|
-
else{
|
|
4097
|
-
this.historyUndo.push( [ undoStep ] );
|
|
4098
|
-
}
|
|
4099
|
-
|
|
4100
|
-
if ( this.historyUndo.length > this.historyMaxSteps ){ this.historyUndo.shift(); } // remove first (oldest) element
|
|
4128
|
+
return undoStep;
|
|
4129
|
+
}
|
|
4101
4130
|
|
|
4102
|
-
|
|
4103
|
-
|
|
4131
|
+
/**
|
|
4132
|
+
* It should swap the previous state with the incoming state of the track. It must return the previous state.
|
|
4133
|
+
* historyGenerateTrackStep could be used to copy the previous state. However, as it is a swap, it suffices to just copy the references.
|
|
4134
|
+
* @param {Object} state object with a trackIdx:Number and whatever information was saved in historyGenerateTrackStep
|
|
4135
|
+
* @param {Boolean} isUndo
|
|
4136
|
+
* @returns previous state object
|
|
4137
|
+
*/
|
|
4138
|
+
historyApplyTrackStep( state, isUndo ){
|
|
4139
|
+
const track = this.animationClip.tracks[state.trackIdx];
|
|
4104
4140
|
|
|
4105
|
-
|
|
4106
|
-
|
|
4107
|
-
|
|
4108
|
-
|
|
4109
|
-
|
|
4110
|
-
if (!toBeShown.length){ return false; }
|
|
4111
|
-
|
|
4112
|
-
this.unSelectAllClips();
|
|
4113
|
-
this.unHoverAll();
|
|
4141
|
+
const stateToReturn = {
|
|
4142
|
+
trackIdx: state.trackIdx, // already done by saveState
|
|
4143
|
+
clips: track.clips,
|
|
4144
|
+
edited: track.edited
|
|
4145
|
+
};
|
|
4114
4146
|
|
|
4115
|
-
|
|
4116
|
-
|
|
4117
|
-
|
|
4118
|
-
|
|
4119
|
-
|
|
4120
|
-
|
|
4121
|
-
|
|
4122
|
-
|
|
4123
|
-
combinedStateToStore.push( {
|
|
4124
|
-
trackIdx: state.trackIdx,
|
|
4125
|
-
clips: track.clips,
|
|
4126
|
-
edited: track.edited
|
|
4127
|
-
});
|
|
4128
|
-
|
|
4129
|
-
track.clips = state.clips;
|
|
4130
|
-
track.edited = state.edited;
|
|
4131
|
-
if ( track.selected.length < track.clips.length ){ track.selected.length = track.clips.length; }
|
|
4132
|
-
if ( track.hovered.length < track.clips.length ){ track.hovered.length = track.clips.length; }
|
|
4133
|
-
track.selected.fill(false);
|
|
4134
|
-
track.hovered.fill(false);
|
|
4135
|
-
|
|
4136
|
-
// Update animation action interpolation info
|
|
4137
|
-
if(this.onUpdateTrack)
|
|
4138
|
-
this.onUpdateTrack( [state.trackIdx] );
|
|
4139
|
-
}
|
|
4140
|
-
|
|
4141
|
-
toBeStored.push(combinedStateToStore);
|
|
4142
|
-
|
|
4143
|
-
return true;
|
|
4147
|
+
track.clips = state.clips;
|
|
4148
|
+
track.edited = state.edited;
|
|
4149
|
+
if ( track.selected.length < track.clips.length ){ track.selected.length = track.clips.length; }
|
|
4150
|
+
if ( track.hovered.length < track.clips.length ){ track.hovered.length = track.clips.length; }
|
|
4151
|
+
track.selected.fill(false);
|
|
4152
|
+
track.hovered.fill(false);
|
|
4153
|
+
|
|
4154
|
+
return stateToReturn;
|
|
4144
4155
|
}
|
|
4145
4156
|
|
|
4146
|
-
undo() { return this.#undoRedo(true); }
|
|
4147
|
-
redo() { return this.#undoRedo(false); }
|
|
4148
|
-
|
|
4149
4157
|
getClipOnTime( track, time, threshold ) {
|
|
4150
4158
|
|
|
4151
4159
|
if(!track || !track.clips.length){
|
|
@@ -4355,20 +4363,7 @@ CanvasRenderingContext2D.prototype.roundRect = function(x, y, width, height, rad
|
|
|
4355
4363
|
}
|
|
4356
4364
|
}
|
|
4357
4365
|
|
|
4358
|
-
LX.
|
|
4359
|
-
var c;
|
|
4360
|
-
if(/^#([A-Fa-f0-9]{3}){1,2}$/.test(hex)){
|
|
4361
|
-
c= hex.substring(1).split('');
|
|
4362
|
-
if(c.length== 3){
|
|
4363
|
-
c= [c[0], c[0], c[1], c[1], c[2], c[2]];
|
|
4364
|
-
}
|
|
4365
|
-
c= '0x'+c.join('');
|
|
4366
|
-
return [(c>>16)&255, (c>>8)&255, c&255];
|
|
4367
|
-
}
|
|
4368
|
-
throw new Error('Bad Hex');
|
|
4369
|
-
}
|
|
4370
|
-
|
|
4371
|
-
LX.UTILS.concatTypedArray = (arrays, ArrayType) => {
|
|
4366
|
+
LX.concatTypedArray = (arrays, ArrayType) => {
|
|
4372
4367
|
let size = arrays.reduce((acc,arr) => acc + arr.length, 0);
|
|
4373
4368
|
let result = new ArrayType( size ); // generate just one array
|
|
4374
4369
|
let offset = 0;
|