@angular/animations 14.0.0-next.0 → 14.0.0-next.1
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/animations.d.ts +7 -2
- package/browser/browser.d.ts +14 -89
- package/browser/testing/testing.d.ts +8 -15
- package/esm2020/browser/src/dsl/animation.mjs +1 -1
- package/esm2020/browser/src/dsl/animation_ast.mjs +1 -1
- package/esm2020/browser/src/dsl/animation_ast_builder.mjs +40 -49
- package/esm2020/browser/src/dsl/animation_dsl_visitor.mjs +1 -1
- package/esm2020/browser/src/dsl/animation_timeline_builder.mjs +72 -85
- package/esm2020/browser/src/dsl/animation_timeline_instruction.mjs +1 -1
- package/esm2020/browser/src/dsl/animation_transition_factory.mjs +16 -17
- package/esm2020/browser/src/dsl/animation_transition_instruction.mjs +8 -1
- package/esm2020/browser/src/dsl/animation_trigger.mjs +9 -9
- package/esm2020/browser/src/dsl/style_normalization/web_animations_style_normalizer.mjs +33 -9
- package/esm2020/browser/src/private_export.mjs +3 -5
- package/esm2020/browser/src/render/animation_driver.mjs +4 -4
- package/esm2020/browser/src/render/shared.mjs +18 -27
- package/esm2020/browser/src/render/special_cased_styles.mjs +7 -16
- package/esm2020/browser/src/render/timeline_animation_engine.mjs +15 -15
- package/esm2020/browser/src/render/transition_animation_engine.mjs +55 -73
- package/esm2020/browser/src/render/web_animations/web_animations_driver.mjs +10 -29
- package/esm2020/browser/src/render/web_animations/web_animations_player.mjs +16 -9
- package/esm2020/browser/src/util.mjs +38 -28
- package/esm2020/browser/testing/src/mock_animation_driver.mjs +14 -14
- package/esm2020/src/animation_metadata.mjs +1 -1
- package/esm2020/src/animations.mjs +1 -1
- package/esm2020/src/version.mjs +1 -1
- package/fesm2015/animations.mjs +1 -1
- package/fesm2015/animations.mjs.map +1 -1
- package/fesm2015/browser/testing.mjs +14 -14
- package/fesm2015/browser/testing.mjs.map +1 -1
- package/fesm2015/browser.mjs +326 -788
- package/fesm2015/browser.mjs.map +1 -1
- package/fesm2020/animations.mjs +1 -1
- package/fesm2020/animations.mjs.map +1 -1
- package/fesm2020/browser/testing.mjs +14 -14
- package/fesm2020/browser/testing.mjs.map +1 -1
- package/fesm2020/browser.mjs +325 -787
- package/fesm2020/browser.mjs.map +1 -1
- package/package.json +2 -2
- package/esm2020/browser/src/render/css_keyframes/css_keyframes_driver.mjs +0 -121
- package/esm2020/browser/src/render/css_keyframes/css_keyframes_player.mjs +0 -133
- package/esm2020/browser/src/render/css_keyframes/direct_style_player.mjs +0 -51
- package/esm2020/browser/src/render/css_keyframes/element_animation_style_handler.mjs +0 -137
package/fesm2015/browser.mjs
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* @license Angular v14.0.0-next.
|
|
2
|
+
* @license Angular v14.0.0-next.1
|
|
3
3
|
* (c) 2010-2022 Google LLC. https://angular.io/
|
|
4
4
|
* License: MIT
|
|
5
5
|
*/
|
|
@@ -36,26 +36,26 @@ function optimizeGroupPlayer(players) {
|
|
|
36
36
|
return new ɵAnimationGroupPlayer(players);
|
|
37
37
|
}
|
|
38
38
|
}
|
|
39
|
-
function normalizeKeyframes(driver, normalizer, element, keyframes, preStyles =
|
|
39
|
+
function normalizeKeyframes$1(driver, normalizer, element, keyframes, preStyles = new Map(), postStyles = new Map()) {
|
|
40
40
|
const errors = [];
|
|
41
41
|
const normalizedKeyframes = [];
|
|
42
42
|
let previousOffset = -1;
|
|
43
43
|
let previousKeyframe = null;
|
|
44
44
|
keyframes.forEach(kf => {
|
|
45
|
-
const offset = kf
|
|
45
|
+
const offset = kf.get('offset');
|
|
46
46
|
const isSameOffset = offset == previousOffset;
|
|
47
|
-
const normalizedKeyframe = (isSameOffset && previousKeyframe) ||
|
|
48
|
-
|
|
47
|
+
const normalizedKeyframe = (isSameOffset && previousKeyframe) || new Map();
|
|
48
|
+
kf.forEach((val, prop) => {
|
|
49
49
|
let normalizedProp = prop;
|
|
50
|
-
let normalizedValue =
|
|
50
|
+
let normalizedValue = val;
|
|
51
51
|
if (prop !== 'offset') {
|
|
52
52
|
normalizedProp = normalizer.normalizePropertyName(normalizedProp, errors);
|
|
53
53
|
switch (normalizedValue) {
|
|
54
54
|
case ɵPRE_STYLE:
|
|
55
|
-
normalizedValue = preStyles
|
|
55
|
+
normalizedValue = preStyles.get(prop);
|
|
56
56
|
break;
|
|
57
57
|
case AUTO_STYLE:
|
|
58
|
-
normalizedValue = postStyles
|
|
58
|
+
normalizedValue = postStyles.get(prop);
|
|
59
59
|
break;
|
|
60
60
|
default:
|
|
61
61
|
normalizedValue =
|
|
@@ -63,7 +63,7 @@ function normalizeKeyframes(driver, normalizer, element, keyframes, preStyles =
|
|
|
63
63
|
break;
|
|
64
64
|
}
|
|
65
65
|
}
|
|
66
|
-
normalizedKeyframe
|
|
66
|
+
normalizedKeyframe.set(normalizedProp, normalizedValue);
|
|
67
67
|
});
|
|
68
68
|
if (!isSameOffset) {
|
|
69
69
|
normalizedKeyframes.push(normalizedKeyframe);
|
|
@@ -103,19 +103,10 @@ function copyAnimationEvent(e, phaseName, player) {
|
|
|
103
103
|
function makeAnimationEvent(element, triggerName, fromState, toState, phaseName = '', totalTime = 0, disabled) {
|
|
104
104
|
return { element, triggerName, fromState, toState, phaseName, totalTime, disabled: !!disabled };
|
|
105
105
|
}
|
|
106
|
-
function
|
|
107
|
-
let value;
|
|
108
|
-
if (
|
|
109
|
-
value =
|
|
110
|
-
if (!value) {
|
|
111
|
-
map.set(key, value = defaultValue);
|
|
112
|
-
}
|
|
113
|
-
}
|
|
114
|
-
else {
|
|
115
|
-
value = map[key];
|
|
116
|
-
if (!value) {
|
|
117
|
-
value = map[key] = defaultValue;
|
|
118
|
-
}
|
|
106
|
+
function getOrSetDefaultValue(map, key, defaultValue) {
|
|
107
|
+
let value = map.get(key);
|
|
108
|
+
if (!value) {
|
|
109
|
+
map.set(key, value = defaultValue);
|
|
119
110
|
}
|
|
120
111
|
return value;
|
|
121
112
|
}
|
|
@@ -185,13 +176,13 @@ function getBodyNode() {
|
|
|
185
176
|
}
|
|
186
177
|
const containsElement = _contains;
|
|
187
178
|
const invokeQuery = _query;
|
|
188
|
-
function
|
|
189
|
-
const
|
|
190
|
-
|
|
179
|
+
function hypenatePropsKeys(original) {
|
|
180
|
+
const newMap = new Map();
|
|
181
|
+
original.forEach((val, prop) => {
|
|
191
182
|
const newProp = prop.replace(/([a-z])([A-Z])/g, '$1-$2');
|
|
192
|
-
|
|
183
|
+
newMap.set(newProp, val);
|
|
193
184
|
});
|
|
194
|
-
return
|
|
185
|
+
return newMap;
|
|
195
186
|
}
|
|
196
187
|
|
|
197
188
|
/**
|
|
@@ -225,9 +216,9 @@ class NoopAnimationDriver {
|
|
|
225
216
|
return new NoopAnimationPlayer(duration, delay);
|
|
226
217
|
}
|
|
227
218
|
}
|
|
228
|
-
NoopAnimationDriver.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.0.0-next.
|
|
229
|
-
NoopAnimationDriver.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.0.0-next.
|
|
230
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.0.0-next.
|
|
219
|
+
NoopAnimationDriver.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.0.0-next.1", ngImport: i0, type: NoopAnimationDriver, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
|
|
220
|
+
NoopAnimationDriver.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.0.0-next.1", ngImport: i0, type: NoopAnimationDriver });
|
|
221
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.0.0-next.1", ngImport: i0, type: NoopAnimationDriver, decorators: [{
|
|
231
222
|
type: Injectable
|
|
232
223
|
}] });
|
|
233
224
|
/**
|
|
@@ -244,7 +235,7 @@ AnimationDriver.NOOP = ( /* @__PURE__ */new NoopAnimationDriver());
|
|
|
244
235
|
* Use of this source code is governed by an MIT-style license that can be
|
|
245
236
|
* found in the LICENSE file at https://angular.io/license
|
|
246
237
|
*/
|
|
247
|
-
const ONE_SECOND
|
|
238
|
+
const ONE_SECOND = 1000;
|
|
248
239
|
const SUBSTITUTION_EXPR_START = '{{';
|
|
249
240
|
const SUBSTITUTION_EXPR_END = '}}';
|
|
250
241
|
const ENTER_CLASSNAME = 'ng-enter';
|
|
@@ -264,7 +255,7 @@ function resolveTimingValue(value) {
|
|
|
264
255
|
function _convertTimeValueToMS(value, unit) {
|
|
265
256
|
switch (unit) {
|
|
266
257
|
case 's':
|
|
267
|
-
return value * ONE_SECOND
|
|
258
|
+
return value * ONE_SECOND;
|
|
268
259
|
default: // ms or something else
|
|
269
260
|
return value;
|
|
270
261
|
}
|
|
@@ -321,27 +312,41 @@ function copyObj(obj, destination = {}) {
|
|
|
321
312
|
});
|
|
322
313
|
return destination;
|
|
323
314
|
}
|
|
315
|
+
function convertToMap(obj) {
|
|
316
|
+
const styleMap = new Map();
|
|
317
|
+
Object.keys(obj).forEach(prop => {
|
|
318
|
+
const val = obj[prop];
|
|
319
|
+
styleMap.set(prop, val);
|
|
320
|
+
});
|
|
321
|
+
return styleMap;
|
|
322
|
+
}
|
|
323
|
+
function normalizeKeyframes(keyframes) {
|
|
324
|
+
if (!keyframes.length) {
|
|
325
|
+
return [];
|
|
326
|
+
}
|
|
327
|
+
if (keyframes[0] instanceof Map) {
|
|
328
|
+
return keyframes;
|
|
329
|
+
}
|
|
330
|
+
return keyframes.map(kf => convertToMap(kf));
|
|
331
|
+
}
|
|
324
332
|
function normalizeStyles(styles) {
|
|
325
|
-
const normalizedStyles =
|
|
333
|
+
const normalizedStyles = new Map();
|
|
326
334
|
if (Array.isArray(styles)) {
|
|
327
|
-
styles.forEach(data => copyStyles(data,
|
|
335
|
+
styles.forEach(data => copyStyles(data, normalizedStyles));
|
|
328
336
|
}
|
|
329
337
|
else {
|
|
330
|
-
copyStyles(styles,
|
|
338
|
+
copyStyles(styles, normalizedStyles);
|
|
331
339
|
}
|
|
332
340
|
return normalizedStyles;
|
|
333
341
|
}
|
|
334
|
-
function copyStyles(styles,
|
|
335
|
-
if (
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
// revealed from the backFill map
|
|
339
|
-
for (let prop in styles) {
|
|
340
|
-
destination[prop] = styles[prop];
|
|
342
|
+
function copyStyles(styles, destination = new Map(), backfill) {
|
|
343
|
+
if (backfill) {
|
|
344
|
+
for (let [prop, val] of backfill) {
|
|
345
|
+
destination.set(prop, val);
|
|
341
346
|
}
|
|
342
347
|
}
|
|
343
|
-
|
|
344
|
-
|
|
348
|
+
for (let [prop, val] of styles) {
|
|
349
|
+
destination.set(prop, val);
|
|
345
350
|
}
|
|
346
351
|
return destination;
|
|
347
352
|
}
|
|
@@ -377,12 +382,12 @@ function writeStyleAttribute(element) {
|
|
|
377
382
|
}
|
|
378
383
|
function setStyles(element, styles, formerStyles) {
|
|
379
384
|
if (element['style']) {
|
|
380
|
-
|
|
385
|
+
styles.forEach((val, prop) => {
|
|
381
386
|
const camelProp = dashCaseToCamelCase(prop);
|
|
382
|
-
if (formerStyles && !formerStyles.
|
|
383
|
-
formerStyles
|
|
387
|
+
if (formerStyles && !formerStyles.has(prop)) {
|
|
388
|
+
formerStyles.set(prop, element.style[camelProp]);
|
|
384
389
|
}
|
|
385
|
-
element.style[camelProp] =
|
|
390
|
+
element.style[camelProp] = val;
|
|
386
391
|
});
|
|
387
392
|
// On the server set the 'style' attribute since it's not automatically reflected.
|
|
388
393
|
if (isNode()) {
|
|
@@ -392,7 +397,7 @@ function setStyles(element, styles, formerStyles) {
|
|
|
392
397
|
}
|
|
393
398
|
function eraseStyles(element, styles) {
|
|
394
399
|
if (element['style']) {
|
|
395
|
-
|
|
400
|
+
styles.forEach((_, prop) => {
|
|
396
401
|
const camelProp = dashCaseToCamelCase(prop);
|
|
397
402
|
element.style[camelProp] = '';
|
|
398
403
|
});
|
|
@@ -467,23 +472,19 @@ function allowPreviousPlayerStylesMerge(duration, delay) {
|
|
|
467
472
|
return duration === 0 || delay === 0;
|
|
468
473
|
}
|
|
469
474
|
function balancePreviousStylesIntoKeyframes(element, keyframes, previousStyles) {
|
|
470
|
-
|
|
471
|
-
if (previousStyleProps.length && keyframes.length) {
|
|
475
|
+
if (previousStyles.size && keyframes.length) {
|
|
472
476
|
let startingKeyframe = keyframes[0];
|
|
473
477
|
let missingStyleProps = [];
|
|
474
|
-
|
|
475
|
-
if (!startingKeyframe.
|
|
478
|
+
previousStyles.forEach((val, prop) => {
|
|
479
|
+
if (!startingKeyframe.has(prop)) {
|
|
476
480
|
missingStyleProps.push(prop);
|
|
477
481
|
}
|
|
478
|
-
startingKeyframe
|
|
482
|
+
startingKeyframe.set(prop, val);
|
|
479
483
|
});
|
|
480
484
|
if (missingStyleProps.length) {
|
|
481
|
-
|
|
482
|
-
for (var i = 1; i < keyframes.length; i++) {
|
|
485
|
+
for (let i = 1; i < keyframes.length; i++) {
|
|
483
486
|
let kf = keyframes[i];
|
|
484
|
-
missingStyleProps.forEach(
|
|
485
|
-
kf[prop] = computeStyle(element, prop);
|
|
486
|
-
});
|
|
487
|
+
missingStyleProps.forEach(prop => kf.set(prop, computeStyle(element, prop)));
|
|
487
488
|
}
|
|
488
489
|
}
|
|
489
490
|
}
|
|
@@ -663,8 +664,8 @@ class AnimationAstBuilderVisitor {
|
|
|
663
664
|
}
|
|
664
665
|
_resetContextStyleTimingState(context) {
|
|
665
666
|
context.currentQuerySelector = ROOT_SELECTOR;
|
|
666
|
-
context.collectedStyles =
|
|
667
|
-
context.collectedStyles
|
|
667
|
+
context.collectedStyles = new Map();
|
|
668
|
+
context.collectedStyles.set(ROOT_SELECTOR, new Map());
|
|
668
669
|
context.currentTime = 0;
|
|
669
670
|
}
|
|
670
671
|
visitTrigger(metadata, context) {
|
|
@@ -712,11 +713,10 @@ class AnimationAstBuilderVisitor {
|
|
|
712
713
|
if (styleAst.containsDynamicStyles) {
|
|
713
714
|
const missingSubs = new Set();
|
|
714
715
|
const params = astParams || {};
|
|
715
|
-
styleAst.styles.forEach(
|
|
716
|
-
if (
|
|
717
|
-
|
|
718
|
-
|
|
719
|
-
extractStyleParams(stylesObj[prop]).forEach(sub => {
|
|
716
|
+
styleAst.styles.forEach(style => {
|
|
717
|
+
if (style instanceof Map) {
|
|
718
|
+
style.forEach(value => {
|
|
719
|
+
extractStyleParams(value).forEach(sub => {
|
|
720
720
|
if (!params.hasOwnProperty(sub)) {
|
|
721
721
|
missingSubs.add(sub);
|
|
722
722
|
}
|
|
@@ -813,37 +813,30 @@ class AnimationAstBuilderVisitor {
|
|
|
813
813
|
}
|
|
814
814
|
_makeStyleAst(metadata, context) {
|
|
815
815
|
const styles = [];
|
|
816
|
-
|
|
817
|
-
|
|
818
|
-
|
|
819
|
-
|
|
820
|
-
|
|
821
|
-
}
|
|
822
|
-
else {
|
|
823
|
-
context.errors.push(`The provided style string value ${styleTuple} is not allowed.`);
|
|
824
|
-
}
|
|
816
|
+
const metadataStyles = Array.isArray(metadata.styles) ? metadata.styles : [metadata.styles];
|
|
817
|
+
for (let styleTuple of metadataStyles) {
|
|
818
|
+
if (typeof styleTuple === 'string') {
|
|
819
|
+
if (styleTuple === AUTO_STYLE) {
|
|
820
|
+
styles.push(styleTuple);
|
|
825
821
|
}
|
|
826
822
|
else {
|
|
827
|
-
|
|
823
|
+
context.errors.push(`The provided style string value ${styleTuple} is not allowed.`);
|
|
828
824
|
}
|
|
829
|
-
}
|
|
830
|
-
|
|
831
|
-
|
|
832
|
-
|
|
825
|
+
}
|
|
826
|
+
else {
|
|
827
|
+
styles.push(convertToMap(styleTuple));
|
|
828
|
+
}
|
|
833
829
|
}
|
|
834
830
|
let containsDynamicStyles = false;
|
|
835
831
|
let collectedEasing = null;
|
|
836
832
|
styles.forEach(styleData => {
|
|
837
|
-
if (
|
|
838
|
-
|
|
839
|
-
|
|
840
|
-
|
|
841
|
-
collectedEasing = easing;
|
|
842
|
-
delete styleMap['easing'];
|
|
833
|
+
if (styleData instanceof Map) {
|
|
834
|
+
if (styleData.has('easing')) {
|
|
835
|
+
collectedEasing = styleData.get('easing');
|
|
836
|
+
styleData.delete('easing');
|
|
843
837
|
}
|
|
844
838
|
if (!containsDynamicStyles) {
|
|
845
|
-
for (let
|
|
846
|
-
const value = styleMap[prop];
|
|
839
|
+
for (let value of styleData.values()) {
|
|
847
840
|
if (value.toString().indexOf(SUBSTITUTION_EXPR_START) >= 0) {
|
|
848
841
|
containsDynamicStyles = true;
|
|
849
842
|
break;
|
|
@@ -869,15 +862,17 @@ class AnimationAstBuilderVisitor {
|
|
|
869
862
|
startTime -= timings.duration + timings.delay;
|
|
870
863
|
}
|
|
871
864
|
ast.styles.forEach(tuple => {
|
|
872
|
-
if (typeof tuple
|
|
865
|
+
if (typeof tuple === 'string')
|
|
873
866
|
return;
|
|
874
|
-
|
|
867
|
+
tuple.forEach((value, prop) => {
|
|
875
868
|
if (!this._driver.validateStyleProperty(prop)) {
|
|
876
869
|
context.errors.push(`The provided animation property "${prop}" is not a supported CSS property for animations`);
|
|
877
870
|
return;
|
|
878
871
|
}
|
|
879
|
-
|
|
880
|
-
|
|
872
|
+
// This is guaranteed to have a defined Map at this querySelector location making it
|
|
873
|
+
// safe to add the assertion here. It is set as a default empty map in prior methods.
|
|
874
|
+
const collectedStyles = context.collectedStyles.get(context.currentQuerySelector);
|
|
875
|
+
const collectedEntry = collectedStyles.get(prop);
|
|
881
876
|
let updateCollectedStyle = true;
|
|
882
877
|
if (collectedEntry) {
|
|
883
878
|
if (startTime != endTime && startTime >= collectedEntry.startTime &&
|
|
@@ -892,10 +887,10 @@ class AnimationAstBuilderVisitor {
|
|
|
892
887
|
startTime = collectedEntry.startTime;
|
|
893
888
|
}
|
|
894
889
|
if (updateCollectedStyle) {
|
|
895
|
-
collectedStyles
|
|
890
|
+
collectedStyles.set(prop, { startTime, endTime });
|
|
896
891
|
}
|
|
897
892
|
if (context.options) {
|
|
898
|
-
validateStyleParams(
|
|
893
|
+
validateStyleParams(value, context.options, context.errors);
|
|
899
894
|
}
|
|
900
895
|
});
|
|
901
896
|
});
|
|
@@ -984,7 +979,7 @@ class AnimationAstBuilderVisitor {
|
|
|
984
979
|
const [selector, includeSelf] = normalizeSelector(metadata.selector);
|
|
985
980
|
context.currentQuerySelector =
|
|
986
981
|
parentSelector.length ? (parentSelector + ' ' + selector) : selector;
|
|
987
|
-
|
|
982
|
+
getOrSetDefaultValue(context.collectedStyles, context.currentQuerySelector, new Map());
|
|
988
983
|
const animation = visitDslNode(this, normalizeAnimationEntry(metadata.animation), context);
|
|
989
984
|
context.currentQuery = null;
|
|
990
985
|
context.currentQuerySelector = parentSelector;
|
|
@@ -1039,7 +1034,7 @@ class AnimationAstBuilderContext {
|
|
|
1039
1034
|
this.currentQuerySelector = null;
|
|
1040
1035
|
this.currentAnimateTimings = null;
|
|
1041
1036
|
this.currentTime = 0;
|
|
1042
|
-
this.collectedStyles =
|
|
1037
|
+
this.collectedStyles = new Map();
|
|
1043
1038
|
this.options = null;
|
|
1044
1039
|
}
|
|
1045
1040
|
}
|
|
@@ -1049,23 +1044,20 @@ function consumeOffset(styles) {
|
|
|
1049
1044
|
let offset = null;
|
|
1050
1045
|
if (Array.isArray(styles)) {
|
|
1051
1046
|
styles.forEach(styleTuple => {
|
|
1052
|
-
if (
|
|
1047
|
+
if (styleTuple instanceof Map && styleTuple.has('offset')) {
|
|
1053
1048
|
const obj = styleTuple;
|
|
1054
|
-
offset = parseFloat(obj
|
|
1055
|
-
delete
|
|
1049
|
+
offset = parseFloat(obj.get('offset'));
|
|
1050
|
+
obj.delete('offset');
|
|
1056
1051
|
}
|
|
1057
1052
|
});
|
|
1058
1053
|
}
|
|
1059
|
-
else if (
|
|
1054
|
+
else if (styles instanceof Map && styles.has('offset')) {
|
|
1060
1055
|
const obj = styles;
|
|
1061
|
-
offset = parseFloat(obj
|
|
1062
|
-
delete
|
|
1056
|
+
offset = parseFloat(obj.get('offset'));
|
|
1057
|
+
obj.delete('offset');
|
|
1063
1058
|
}
|
|
1064
1059
|
return offset;
|
|
1065
1060
|
}
|
|
1066
|
-
function isObject(value) {
|
|
1067
|
-
return !Array.isArray(value) && typeof value == 'object';
|
|
1068
|
-
}
|
|
1069
1061
|
function constructTimingAst(value, errors) {
|
|
1070
1062
|
let timings = null;
|
|
1071
1063
|
if (value.hasOwnProperty('duration')) {
|
|
@@ -1173,7 +1165,7 @@ const LEAVE_TOKEN_REGEX = new RegExp(LEAVE_TOKEN, 'g');
|
|
|
1173
1165
|
* ```
|
|
1174
1166
|
*
|
|
1175
1167
|
* For this operation to cover the combination of animation verbs (style, animate, group, etc...) a
|
|
1176
|
-
* combination of
|
|
1168
|
+
* combination of AST traversal and merge-sort-like algorithms are used.
|
|
1177
1169
|
*
|
|
1178
1170
|
* [AST Traversal]
|
|
1179
1171
|
* Each of the animation verbs, when executed, will return an string-map object representing what
|
|
@@ -1219,23 +1211,18 @@ const LEAVE_TOKEN_REGEX = new RegExp(LEAVE_TOKEN, 'g');
|
|
|
1219
1211
|
* from all previous animation steps. Therefore when a keyframe is created it would also be missing
|
|
1220
1212
|
* from all previous keyframes up until where it is first used. For the timeline keyframe generation
|
|
1221
1213
|
* to properly fill in the style it will place the previous value (the value from the parent
|
|
1222
|
-
* timeline) or a default value of `*` into the backFill
|
|
1223
|
-
*
|
|
1224
|
-
* value is added into the backFill then it will automatically propagate any missing values to all
|
|
1225
|
-
* keyframes. Therefore the missing `height` value will be properly filled into the already
|
|
1226
|
-
* processed keyframes.
|
|
1214
|
+
* timeline) or a default value of `*` into the backFill map. The `copyStyles` method in util.ts
|
|
1215
|
+
* handles propagating that backfill map to the styles object.
|
|
1227
1216
|
*
|
|
1228
1217
|
* When a sub-timeline is created it will have its own backFill property. This is done so that
|
|
1229
1218
|
* styles present within the sub-timeline do not accidentally seep into the previous/future timeline
|
|
1230
1219
|
* keyframes
|
|
1231
1220
|
*
|
|
1232
|
-
* (For prototypically-inherited contents to be detected a `for(i in obj)` loop must be used.)
|
|
1233
|
-
*
|
|
1234
1221
|
* [Validation]
|
|
1235
1222
|
* The code in this file is not responsible for validation. That functionality happens with within
|
|
1236
1223
|
* the `AnimationValidatorVisitor` code.
|
|
1237
1224
|
*/
|
|
1238
|
-
function buildAnimationTimelines(driver, rootElement, ast, enterClassName, leaveClassName, startingStyles =
|
|
1225
|
+
function buildAnimationTimelines(driver, rootElement, ast, enterClassName, leaveClassName, startingStyles = new Map(), finalStyles = new Map(), options, subInstructions, errors = []) {
|
|
1239
1226
|
return new AnimationTimelineBuilderVisitor().buildKeyframes(driver, rootElement, ast, enterClassName, leaveClassName, startingStyles, finalStyles, options, subInstructions, errors);
|
|
1240
1227
|
}
|
|
1241
1228
|
class AnimationTimelineBuilderVisitor {
|
|
@@ -1247,11 +1234,11 @@ class AnimationTimelineBuilderVisitor {
|
|
|
1247
1234
|
visitDslNode(this, ast, context);
|
|
1248
1235
|
// this checks to see if an actual animation happened
|
|
1249
1236
|
const timelines = context.timelines.filter(timeline => timeline.containsAnimation());
|
|
1250
|
-
|
|
1251
|
-
|
|
1252
|
-
|
|
1253
|
-
|
|
1254
|
-
|
|
1237
|
+
// note: we just want to apply the final styles for the rootElement, so we do not
|
|
1238
|
+
// just apply the styles to the last timeline but the last timeline which
|
|
1239
|
+
// element is the root one (basically `*`-styles are replaced with the actual
|
|
1240
|
+
// state style values only for the root element)
|
|
1241
|
+
if (timelines.length && finalStyles.size) {
|
|
1255
1242
|
let lastRootTimeline;
|
|
1256
1243
|
for (let i = timelines.length - 1; i >= 0; i--) {
|
|
1257
1244
|
const timeline = timelines[i];
|
|
@@ -1401,7 +1388,7 @@ class AnimationTimelineBuilderVisitor {
|
|
|
1401
1388
|
const timings = context.currentAnimateTimings;
|
|
1402
1389
|
// this is a special case for when a style() call
|
|
1403
1390
|
// directly follows an animate() call (but not inside of an animate() call)
|
|
1404
|
-
if (!timings && timeline.
|
|
1391
|
+
if (!timings && timeline.hasCurrentStyleProperties()) {
|
|
1405
1392
|
timeline.forwardFrame();
|
|
1406
1393
|
}
|
|
1407
1394
|
const easing = (timings && timings.easing) || ast.easing;
|
|
@@ -1442,7 +1429,7 @@ class AnimationTimelineBuilderVisitor {
|
|
|
1442
1429
|
const delay = options.delay ? resolveTimingValue(options.delay) : 0;
|
|
1443
1430
|
if (delay &&
|
|
1444
1431
|
(context.previousNode.type === 6 /* Style */ ||
|
|
1445
|
-
(startTime == 0 && context.currentTimeline.
|
|
1432
|
+
(startTime == 0 && context.currentTimeline.hasCurrentStyleProperties()))) {
|
|
1446
1433
|
context.currentTimeline.snapshotCurrentStyles();
|
|
1447
1434
|
context.previousNode = DEFAULT_NOOP_PREVIOUS_NODE;
|
|
1448
1435
|
}
|
|
@@ -1636,17 +1623,17 @@ class TimelineBuilder {
|
|
|
1636
1623
|
this.startTime = startTime;
|
|
1637
1624
|
this._elementTimelineStylesLookup = _elementTimelineStylesLookup;
|
|
1638
1625
|
this.duration = 0;
|
|
1639
|
-
this._previousKeyframe =
|
|
1640
|
-
this._currentKeyframe =
|
|
1626
|
+
this._previousKeyframe = new Map();
|
|
1627
|
+
this._currentKeyframe = new Map();
|
|
1641
1628
|
this._keyframes = new Map();
|
|
1642
|
-
this._styleSummary =
|
|
1643
|
-
this.
|
|
1644
|
-
this.
|
|
1629
|
+
this._styleSummary = new Map();
|
|
1630
|
+
this._localTimelineStyles = new Map();
|
|
1631
|
+
this._pendingStyles = new Map();
|
|
1632
|
+
this._backFill = new Map();
|
|
1645
1633
|
this._currentEmptyStepKeyframe = null;
|
|
1646
1634
|
if (!this._elementTimelineStylesLookup) {
|
|
1647
1635
|
this._elementTimelineStylesLookup = new Map();
|
|
1648
1636
|
}
|
|
1649
|
-
this._localTimelineStyles = Object.create(this._backFill, {});
|
|
1650
1637
|
this._globalTimelineStyles = this._elementTimelineStylesLookup.get(element);
|
|
1651
1638
|
if (!this._globalTimelineStyles) {
|
|
1652
1639
|
this._globalTimelineStyles = this._localTimelineStyles;
|
|
@@ -1659,13 +1646,13 @@ class TimelineBuilder {
|
|
|
1659
1646
|
case 0:
|
|
1660
1647
|
return false;
|
|
1661
1648
|
case 1:
|
|
1662
|
-
return this.
|
|
1649
|
+
return this.hasCurrentStyleProperties();
|
|
1663
1650
|
default:
|
|
1664
1651
|
return true;
|
|
1665
1652
|
}
|
|
1666
1653
|
}
|
|
1667
|
-
|
|
1668
|
-
return
|
|
1654
|
+
hasCurrentStyleProperties() {
|
|
1655
|
+
return this._currentKeyframe.size > 0;
|
|
1669
1656
|
}
|
|
1670
1657
|
get currentTime() {
|
|
1671
1658
|
return this.startTime + this.duration;
|
|
@@ -1675,7 +1662,7 @@ class TimelineBuilder {
|
|
|
1675
1662
|
// and that style() step is the very first style() value in the animation
|
|
1676
1663
|
// then we need to make a copy of the keyframe [0, copy, 1] so that the delay
|
|
1677
1664
|
// properly applies the style() values to work with the stagger...
|
|
1678
|
-
const hasPreStyleStep = this._keyframes.size
|
|
1665
|
+
const hasPreStyleStep = this._keyframes.size === 1 && this._pendingStyles.size;
|
|
1679
1666
|
if (this.duration || hasPreStyleStep) {
|
|
1680
1667
|
this.forwardTime(this.currentTime + delay);
|
|
1681
1668
|
if (hasPreStyleStep) {
|
|
@@ -1696,7 +1683,7 @@ class TimelineBuilder {
|
|
|
1696
1683
|
}
|
|
1697
1684
|
this._currentKeyframe = this._keyframes.get(this.duration);
|
|
1698
1685
|
if (!this._currentKeyframe) {
|
|
1699
|
-
this._currentKeyframe =
|
|
1686
|
+
this._currentKeyframe = new Map();
|
|
1700
1687
|
this._keyframes.set(this.duration, this._currentKeyframe);
|
|
1701
1688
|
}
|
|
1702
1689
|
}
|
|
@@ -1710,16 +1697,16 @@ class TimelineBuilder {
|
|
|
1710
1697
|
this._loadKeyframe();
|
|
1711
1698
|
}
|
|
1712
1699
|
_updateStyle(prop, value) {
|
|
1713
|
-
this._localTimelineStyles
|
|
1714
|
-
this._globalTimelineStyles
|
|
1715
|
-
this._styleSummary
|
|
1700
|
+
this._localTimelineStyles.set(prop, value);
|
|
1701
|
+
this._globalTimelineStyles.set(prop, value);
|
|
1702
|
+
this._styleSummary.set(prop, { time: this.currentTime, value });
|
|
1716
1703
|
}
|
|
1717
1704
|
allowOnlyTimelineStyles() {
|
|
1718
1705
|
return this._currentEmptyStepKeyframe !== this._currentKeyframe;
|
|
1719
1706
|
}
|
|
1720
1707
|
applyEmptyStep(easing) {
|
|
1721
1708
|
if (easing) {
|
|
1722
|
-
this._previousKeyframe
|
|
1709
|
+
this._previousKeyframe.set('easing', easing);
|
|
1723
1710
|
}
|
|
1724
1711
|
// special case for animate(duration):
|
|
1725
1712
|
// all missing styles are filled with a `*` value then
|
|
@@ -1727,51 +1714,45 @@ class TimelineBuilder {
|
|
|
1727
1714
|
// keyframe then they will override the overridden styles
|
|
1728
1715
|
// We use `_globalTimelineStyles` here because there may be
|
|
1729
1716
|
// styles in previous keyframes that are not present in this timeline
|
|
1730
|
-
|
|
1731
|
-
this._backFill
|
|
1732
|
-
this._currentKeyframe
|
|
1733
|
-
}
|
|
1717
|
+
for (let [prop, value] of this._globalTimelineStyles) {
|
|
1718
|
+
this._backFill.set(prop, value || AUTO_STYLE);
|
|
1719
|
+
this._currentKeyframe.set(prop, AUTO_STYLE);
|
|
1720
|
+
}
|
|
1734
1721
|
this._currentEmptyStepKeyframe = this._currentKeyframe;
|
|
1735
1722
|
}
|
|
1736
1723
|
setStyles(input, easing, errors, options) {
|
|
1737
1724
|
if (easing) {
|
|
1738
|
-
this._previousKeyframe
|
|
1725
|
+
this._previousKeyframe.set('easing', easing);
|
|
1739
1726
|
}
|
|
1740
1727
|
const params = (options && options.params) || {};
|
|
1741
1728
|
const styles = flattenStyles(input, this._globalTimelineStyles);
|
|
1742
|
-
|
|
1743
|
-
const val = interpolateParams(
|
|
1744
|
-
this._pendingStyles
|
|
1745
|
-
if (!this._localTimelineStyles.
|
|
1746
|
-
this._backFill
|
|
1747
|
-
this._globalTimelineStyles[prop] :
|
|
1748
|
-
AUTO_STYLE;
|
|
1729
|
+
for (let [prop, value] of styles) {
|
|
1730
|
+
const val = interpolateParams(value, params, errors);
|
|
1731
|
+
this._pendingStyles.set(prop, val);
|
|
1732
|
+
if (!this._localTimelineStyles.has(prop)) {
|
|
1733
|
+
this._backFill.set(prop, this._globalTimelineStyles.get(prop) || AUTO_STYLE);
|
|
1749
1734
|
}
|
|
1750
1735
|
this._updateStyle(prop, val);
|
|
1751
|
-
}
|
|
1736
|
+
}
|
|
1752
1737
|
}
|
|
1753
1738
|
applyStylesToKeyframe() {
|
|
1754
|
-
|
|
1755
|
-
const props = Object.keys(styles);
|
|
1756
|
-
if (props.length == 0)
|
|
1739
|
+
if (this._pendingStyles.size == 0)
|
|
1757
1740
|
return;
|
|
1758
|
-
this._pendingStyles
|
|
1759
|
-
|
|
1760
|
-
const val = styles[prop];
|
|
1761
|
-
this._currentKeyframe[prop] = val;
|
|
1741
|
+
this._pendingStyles.forEach((val, prop) => {
|
|
1742
|
+
this._currentKeyframe.set(prop, val);
|
|
1762
1743
|
});
|
|
1763
|
-
|
|
1764
|
-
|
|
1765
|
-
|
|
1744
|
+
this._pendingStyles.clear();
|
|
1745
|
+
this._localTimelineStyles.forEach((val, prop) => {
|
|
1746
|
+
if (!this._currentKeyframe.has(prop)) {
|
|
1747
|
+
this._currentKeyframe.set(prop, val);
|
|
1766
1748
|
}
|
|
1767
1749
|
});
|
|
1768
1750
|
}
|
|
1769
1751
|
snapshotCurrentStyles() {
|
|
1770
|
-
|
|
1771
|
-
|
|
1772
|
-
this._pendingStyles[prop] = val;
|
|
1752
|
+
for (let [prop, val] of this._localTimelineStyles) {
|
|
1753
|
+
this._pendingStyles.set(prop, val);
|
|
1773
1754
|
this._updateStyle(prop, val);
|
|
1774
|
-
}
|
|
1755
|
+
}
|
|
1775
1756
|
}
|
|
1776
1757
|
getFinalKeyframe() {
|
|
1777
1758
|
return this._keyframes.get(this.duration);
|
|
@@ -1784,9 +1765,8 @@ class TimelineBuilder {
|
|
|
1784
1765
|
return properties;
|
|
1785
1766
|
}
|
|
1786
1767
|
mergeTimelineCollectedStyles(timeline) {
|
|
1787
|
-
|
|
1788
|
-
const details0 = this._styleSummary
|
|
1789
|
-
const details1 = timeline._styleSummary[prop];
|
|
1768
|
+
timeline._styleSummary.forEach((details1, prop) => {
|
|
1769
|
+
const details0 = this._styleSummary.get(prop);
|
|
1790
1770
|
if (!details0 || details1.time > details0.time) {
|
|
1791
1771
|
this._updateStyle(prop, details1.value);
|
|
1792
1772
|
}
|
|
@@ -1799,18 +1779,17 @@ class TimelineBuilder {
|
|
|
1799
1779
|
const isEmpty = this._keyframes.size === 1 && this.duration === 0;
|
|
1800
1780
|
let finalKeyframes = [];
|
|
1801
1781
|
this._keyframes.forEach((keyframe, time) => {
|
|
1802
|
-
const finalKeyframe = copyStyles(keyframe,
|
|
1803
|
-
|
|
1804
|
-
|
|
1805
|
-
if (value == ɵPRE_STYLE) {
|
|
1782
|
+
const finalKeyframe = copyStyles(keyframe, new Map(), this._backFill);
|
|
1783
|
+
finalKeyframe.forEach((value, prop) => {
|
|
1784
|
+
if (value === ɵPRE_STYLE) {
|
|
1806
1785
|
preStyleProps.add(prop);
|
|
1807
1786
|
}
|
|
1808
|
-
else if (value
|
|
1787
|
+
else if (value === AUTO_STYLE) {
|
|
1809
1788
|
postStyleProps.add(prop);
|
|
1810
1789
|
}
|
|
1811
1790
|
});
|
|
1812
1791
|
if (!isEmpty) {
|
|
1813
|
-
finalKeyframe
|
|
1792
|
+
finalKeyframe.set('offset', time / this.duration);
|
|
1814
1793
|
}
|
|
1815
1794
|
finalKeyframes.push(finalKeyframe);
|
|
1816
1795
|
});
|
|
@@ -1819,9 +1798,9 @@ class TimelineBuilder {
|
|
|
1819
1798
|
// special case for a 0-second animation (which is designed just to place styles onscreen)
|
|
1820
1799
|
if (isEmpty) {
|
|
1821
1800
|
const kf0 = finalKeyframes[0];
|
|
1822
|
-
const kf1 =
|
|
1823
|
-
kf0
|
|
1824
|
-
kf1
|
|
1801
|
+
const kf1 = new Map(kf0);
|
|
1802
|
+
kf0.set('offset', 0);
|
|
1803
|
+
kf1.set('offset', 1);
|
|
1825
1804
|
finalKeyframes = [kf0, kf1];
|
|
1826
1805
|
}
|
|
1827
1806
|
return createTimelineInstruction(this.element, finalKeyframes, preProps, postProps, this.duration, this.startTime, this.easing, false);
|
|
@@ -1847,11 +1826,11 @@ class SubTimelineBuilder extends TimelineBuilder {
|
|
|
1847
1826
|
const totalTime = duration + delay;
|
|
1848
1827
|
const startingGap = delay / totalTime;
|
|
1849
1828
|
// the original starting keyframe now starts once the delay is done
|
|
1850
|
-
const newFirstKeyframe = copyStyles(keyframes[0]
|
|
1851
|
-
newFirstKeyframe
|
|
1829
|
+
const newFirstKeyframe = copyStyles(keyframes[0]);
|
|
1830
|
+
newFirstKeyframe.set('offset', 0);
|
|
1852
1831
|
newKeyframes.push(newFirstKeyframe);
|
|
1853
|
-
const oldFirstKeyframe = copyStyles(keyframes[0]
|
|
1854
|
-
oldFirstKeyframe
|
|
1832
|
+
const oldFirstKeyframe = copyStyles(keyframes[0]);
|
|
1833
|
+
oldFirstKeyframe.set('offset', roundOffset(startingGap));
|
|
1855
1834
|
newKeyframes.push(oldFirstKeyframe);
|
|
1856
1835
|
/*
|
|
1857
1836
|
When the keyframe is stretched then it means that the delay before the animation
|
|
@@ -1870,10 +1849,10 @@ class SubTimelineBuilder extends TimelineBuilder {
|
|
|
1870
1849
|
// offsets between 1 ... n -1 are all warped by the keyframe stretch
|
|
1871
1850
|
const limit = keyframes.length - 1;
|
|
1872
1851
|
for (let i = 1; i <= limit; i++) {
|
|
1873
|
-
let kf = copyStyles(keyframes[i]
|
|
1874
|
-
const oldOffset = kf
|
|
1852
|
+
let kf = copyStyles(keyframes[i]);
|
|
1853
|
+
const oldOffset = kf.get('offset');
|
|
1875
1854
|
const timeAtKeyframe = delay + oldOffset * duration;
|
|
1876
|
-
kf
|
|
1855
|
+
kf.set('offset', roundOffset(timeAtKeyframe / totalTime));
|
|
1877
1856
|
newKeyframes.push(kf);
|
|
1878
1857
|
}
|
|
1879
1858
|
// the new starting keyframe should be added at the start
|
|
@@ -1890,17 +1869,17 @@ function roundOffset(offset, decimalPoints = 3) {
|
|
|
1890
1869
|
return Math.round(offset * mult) / mult;
|
|
1891
1870
|
}
|
|
1892
1871
|
function flattenStyles(input, allStyles) {
|
|
1893
|
-
const styles =
|
|
1872
|
+
const styles = new Map();
|
|
1894
1873
|
let allProperties;
|
|
1895
1874
|
input.forEach(token => {
|
|
1896
1875
|
if (token === '*') {
|
|
1897
|
-
allProperties = allProperties ||
|
|
1898
|
-
|
|
1899
|
-
styles
|
|
1900
|
-
}
|
|
1876
|
+
allProperties = allProperties || allStyles.keys();
|
|
1877
|
+
for (let prop of allProperties) {
|
|
1878
|
+
styles.set(prop, AUTO_STYLE);
|
|
1879
|
+
}
|
|
1901
1880
|
}
|
|
1902
1881
|
else {
|
|
1903
|
-
copyStyles(token,
|
|
1882
|
+
copyStyles(token, styles);
|
|
1904
1883
|
}
|
|
1905
1884
|
});
|
|
1906
1885
|
return styles;
|
|
@@ -1964,6 +1943,37 @@ class NoopAnimationStyleNormalizer {
|
|
|
1964
1943
|
* Use of this source code is governed by an MIT-style license that can be
|
|
1965
1944
|
* found in the LICENSE file at https://angular.io/license
|
|
1966
1945
|
*/
|
|
1946
|
+
const DIMENSIONAL_PROP_SET = new Set([
|
|
1947
|
+
'width',
|
|
1948
|
+
'height',
|
|
1949
|
+
'minWidth',
|
|
1950
|
+
'minHeight',
|
|
1951
|
+
'maxWidth',
|
|
1952
|
+
'maxHeight',
|
|
1953
|
+
'left',
|
|
1954
|
+
'top',
|
|
1955
|
+
'bottom',
|
|
1956
|
+
'right',
|
|
1957
|
+
'fontSize',
|
|
1958
|
+
'outlineWidth',
|
|
1959
|
+
'outlineOffset',
|
|
1960
|
+
'paddingTop',
|
|
1961
|
+
'paddingLeft',
|
|
1962
|
+
'paddingBottom',
|
|
1963
|
+
'paddingRight',
|
|
1964
|
+
'marginTop',
|
|
1965
|
+
'marginLeft',
|
|
1966
|
+
'marginBottom',
|
|
1967
|
+
'marginRight',
|
|
1968
|
+
'borderRadius',
|
|
1969
|
+
'borderWidth',
|
|
1970
|
+
'borderTopWidth',
|
|
1971
|
+
'borderLeftWidth',
|
|
1972
|
+
'borderRightWidth',
|
|
1973
|
+
'borderBottomWidth',
|
|
1974
|
+
'textIndent',
|
|
1975
|
+
'perspective'
|
|
1976
|
+
]);
|
|
1967
1977
|
class WebAnimationsStyleNormalizer extends AnimationStyleNormalizer {
|
|
1968
1978
|
normalizePropertyName(propertyName, errors) {
|
|
1969
1979
|
return dashCaseToCamelCase(propertyName);
|
|
@@ -1971,7 +1981,7 @@ class WebAnimationsStyleNormalizer extends AnimationStyleNormalizer {
|
|
|
1971
1981
|
normalizeStyleValue(userProvidedProperty, normalizedProperty, value, errors) {
|
|
1972
1982
|
let unit = '';
|
|
1973
1983
|
const strVal = value.toString().trim();
|
|
1974
|
-
if (
|
|
1984
|
+
if (DIMENSIONAL_PROP_SET.has(normalizedProperty) && value !== 0 && value !== '0') {
|
|
1975
1985
|
if (typeof value === 'number') {
|
|
1976
1986
|
unit = 'px';
|
|
1977
1987
|
}
|
|
@@ -1985,14 +1995,14 @@ class WebAnimationsStyleNormalizer extends AnimationStyleNormalizer {
|
|
|
1985
1995
|
return strVal + unit;
|
|
1986
1996
|
}
|
|
1987
1997
|
}
|
|
1988
|
-
const DIMENSIONAL_PROP_MAP = (() => makeBooleanMap('width,height,minWidth,minHeight,maxWidth,maxHeight,left,top,bottom,right,fontSize,outlineWidth,outlineOffset,paddingTop,paddingLeft,paddingBottom,paddingRight,marginTop,marginLeft,marginBottom,marginRight,borderRadius,borderWidth,borderTopWidth,borderLeftWidth,borderRightWidth,borderBottomWidth,textIndent,perspective'
|
|
1989
|
-
.split(',')))();
|
|
1990
|
-
function makeBooleanMap(keys) {
|
|
1991
|
-
const map = {};
|
|
1992
|
-
keys.forEach(key => map[key] = true);
|
|
1993
|
-
return map;
|
|
1994
|
-
}
|
|
1995
1998
|
|
|
1999
|
+
/**
|
|
2000
|
+
* @license
|
|
2001
|
+
* Copyright Google LLC All Rights Reserved.
|
|
2002
|
+
*
|
|
2003
|
+
* Use of this source code is governed by an MIT-style license that can be
|
|
2004
|
+
* found in the LICENSE file at https://angular.io/license
|
|
2005
|
+
*/
|
|
1996
2006
|
function createTransitionInstruction(element, triggerName, fromState, toState, isRemovalTransition, fromStyles, toStyles, timelines, queriedElements, preStyleProps, postStyleProps, totalTime, errors) {
|
|
1997
2007
|
return {
|
|
1998
2008
|
type: 0 /* TransitionAnimation */,
|
|
@@ -2023,10 +2033,11 @@ class AnimationTransitionFactory {
|
|
|
2023
2033
|
return oneOrMoreTransitionsMatch(this.ast.matchers, currentState, nextState, element, params);
|
|
2024
2034
|
}
|
|
2025
2035
|
buildStyles(stateName, params, errors) {
|
|
2026
|
-
|
|
2027
|
-
|
|
2028
|
-
|
|
2029
|
-
|
|
2036
|
+
let styler = this._stateStyles.get('*');
|
|
2037
|
+
if (stateName !== undefined) {
|
|
2038
|
+
styler = this._stateStyles.get(stateName === null || stateName === void 0 ? void 0 : stateName.toString()) || styler;
|
|
2039
|
+
}
|
|
2040
|
+
return styler ? styler.buildStyles(params, errors) : new Map();
|
|
2030
2041
|
}
|
|
2031
2042
|
build(driver, element, currentState, nextState, enterClassName, leaveClassName, currentOptions, nextOptions, subInstructions, skipAstBuild) {
|
|
2032
2043
|
const errors = [];
|
|
@@ -2052,10 +2063,10 @@ class AnimationTransitionFactory {
|
|
|
2052
2063
|
}
|
|
2053
2064
|
timelines.forEach(tl => {
|
|
2054
2065
|
const elm = tl.element;
|
|
2055
|
-
const preProps =
|
|
2056
|
-
tl.preStyleProps.forEach(prop => preProps
|
|
2057
|
-
const postProps =
|
|
2058
|
-
tl.postStyleProps.forEach(prop => postProps
|
|
2066
|
+
const preProps = getOrSetDefaultValue(preStyleMap, elm, new Set());
|
|
2067
|
+
tl.preStyleProps.forEach(prop => preProps.add(prop));
|
|
2068
|
+
const postProps = getOrSetDefaultValue(postStyleMap, elm, new Set());
|
|
2069
|
+
tl.postStyleProps.forEach(prop => postProps.add(prop));
|
|
2059
2070
|
if (elm !== element) {
|
|
2060
2071
|
queriedElements.add(elm);
|
|
2061
2072
|
}
|
|
@@ -2074,25 +2085,23 @@ class AnimationStateStyles {
|
|
|
2074
2085
|
this.normalizer = normalizer;
|
|
2075
2086
|
}
|
|
2076
2087
|
buildStyles(params, errors) {
|
|
2077
|
-
const finalStyles =
|
|
2088
|
+
const finalStyles = new Map();
|
|
2078
2089
|
const combinedParams = copyObj(this.defaultParams);
|
|
2079
2090
|
Object.keys(params).forEach(key => {
|
|
2080
2091
|
const value = params[key];
|
|
2081
|
-
if (value
|
|
2092
|
+
if (value !== null) {
|
|
2082
2093
|
combinedParams[key] = value;
|
|
2083
2094
|
}
|
|
2084
2095
|
});
|
|
2085
2096
|
this.styles.styles.forEach(value => {
|
|
2086
2097
|
if (typeof value !== 'string') {
|
|
2087
|
-
|
|
2088
|
-
|
|
2089
|
-
let val = styleObj[prop];
|
|
2090
|
-
if (val.length > 1) {
|
|
2098
|
+
value.forEach((val, prop) => {
|
|
2099
|
+
if (val) {
|
|
2091
2100
|
val = interpolateParams(val, combinedParams, errors);
|
|
2092
2101
|
}
|
|
2093
2102
|
const normalizedProp = this.normalizer.normalizePropertyName(prop, errors);
|
|
2094
2103
|
val = this.normalizer.normalizeStyleValue(prop, normalizedProp, val, errors);
|
|
2095
|
-
finalStyles
|
|
2104
|
+
finalStyles.set(normalizedProp, val);
|
|
2096
2105
|
});
|
|
2097
2106
|
}
|
|
2098
2107
|
});
|
|
@@ -2109,10 +2118,10 @@ class AnimationTrigger {
|
|
|
2109
2118
|
this.ast = ast;
|
|
2110
2119
|
this._normalizer = _normalizer;
|
|
2111
2120
|
this.transitionFactories = [];
|
|
2112
|
-
this.states =
|
|
2121
|
+
this.states = new Map();
|
|
2113
2122
|
ast.states.forEach(ast => {
|
|
2114
2123
|
const defaultParams = (ast.options && ast.options.params) || {};
|
|
2115
|
-
this.states
|
|
2124
|
+
this.states.set(ast.name, new AnimationStateStyles(ast.style, defaultParams, _normalizer));
|
|
2116
2125
|
});
|
|
2117
2126
|
balanceProperties(this.states, 'true', '1');
|
|
2118
2127
|
balanceProperties(this.states, 'false', '0');
|
|
@@ -2145,14 +2154,14 @@ function createFallbackTransition(triggerName, states, normalizer) {
|
|
|
2145
2154
|
};
|
|
2146
2155
|
return new AnimationTransitionFactory(triggerName, transition, states);
|
|
2147
2156
|
}
|
|
2148
|
-
function balanceProperties(
|
|
2149
|
-
if (
|
|
2150
|
-
if (!
|
|
2151
|
-
|
|
2157
|
+
function balanceProperties(stateMap, key1, key2) {
|
|
2158
|
+
if (stateMap.has(key1)) {
|
|
2159
|
+
if (!stateMap.has(key2)) {
|
|
2160
|
+
stateMap.set(key2, stateMap.get(key1));
|
|
2152
2161
|
}
|
|
2153
2162
|
}
|
|
2154
|
-
else if (
|
|
2155
|
-
|
|
2163
|
+
else if (stateMap.has(key2)) {
|
|
2164
|
+
stateMap.set(key1, stateMap.get(key2));
|
|
2156
2165
|
}
|
|
2157
2166
|
}
|
|
2158
2167
|
|
|
@@ -2169,8 +2178,8 @@ class TimelineAnimationEngine {
|
|
|
2169
2178
|
this.bodyNode = bodyNode;
|
|
2170
2179
|
this._driver = _driver;
|
|
2171
2180
|
this._normalizer = _normalizer;
|
|
2172
|
-
this._animations =
|
|
2173
|
-
this._playersById =
|
|
2181
|
+
this._animations = new Map();
|
|
2182
|
+
this._playersById = new Map();
|
|
2174
2183
|
this.players = [];
|
|
2175
2184
|
}
|
|
2176
2185
|
register(id, metadata) {
|
|
@@ -2180,24 +2189,24 @@ class TimelineAnimationEngine {
|
|
|
2180
2189
|
throw new Error(`Unable to build the animation due to the following errors: ${errors.join('\n')}`);
|
|
2181
2190
|
}
|
|
2182
2191
|
else {
|
|
2183
|
-
this._animations
|
|
2192
|
+
this._animations.set(id, ast);
|
|
2184
2193
|
}
|
|
2185
2194
|
}
|
|
2186
2195
|
_buildPlayer(i, preStyles, postStyles) {
|
|
2187
2196
|
const element = i.element;
|
|
2188
|
-
const keyframes = normalizeKeyframes(this._driver, this._normalizer, element, i.keyframes, preStyles, postStyles);
|
|
2197
|
+
const keyframes = normalizeKeyframes$1(this._driver, this._normalizer, element, i.keyframes, preStyles, postStyles);
|
|
2189
2198
|
return this._driver.animate(element, keyframes, i.duration, i.delay, i.easing, [], true);
|
|
2190
2199
|
}
|
|
2191
2200
|
create(id, element, options = {}) {
|
|
2192
2201
|
const errors = [];
|
|
2193
|
-
const ast = this._animations
|
|
2202
|
+
const ast = this._animations.get(id);
|
|
2194
2203
|
let instructions;
|
|
2195
2204
|
const autoStylesMap = new Map();
|
|
2196
2205
|
if (ast) {
|
|
2197
|
-
instructions = buildAnimationTimelines(this._driver, element, ast, ENTER_CLASSNAME, LEAVE_CLASSNAME,
|
|
2206
|
+
instructions = buildAnimationTimelines(this._driver, element, ast, ENTER_CLASSNAME, LEAVE_CLASSNAME, new Map(), new Map(), options, EMPTY_INSTRUCTION_MAP, errors);
|
|
2198
2207
|
instructions.forEach(inst => {
|
|
2199
|
-
const styles =
|
|
2200
|
-
inst.postStyleProps.forEach(prop => styles
|
|
2208
|
+
const styles = getOrSetDefaultValue(autoStylesMap, inst.element, new Map());
|
|
2209
|
+
inst.postStyleProps.forEach(prop => styles.set(prop, null));
|
|
2201
2210
|
});
|
|
2202
2211
|
}
|
|
2203
2212
|
else {
|
|
@@ -2208,16 +2217,16 @@ class TimelineAnimationEngine {
|
|
|
2208
2217
|
throw new Error(`Unable to create the animation due to the following errors: ${errors.join('\n')}`);
|
|
2209
2218
|
}
|
|
2210
2219
|
autoStylesMap.forEach((styles, element) => {
|
|
2211
|
-
|
|
2212
|
-
styles
|
|
2220
|
+
styles.forEach((_, prop) => {
|
|
2221
|
+
styles.set(prop, this._driver.computeStyle(element, prop, AUTO_STYLE));
|
|
2213
2222
|
});
|
|
2214
2223
|
});
|
|
2215
2224
|
const players = instructions.map(i => {
|
|
2216
2225
|
const styles = autoStylesMap.get(i.element);
|
|
2217
|
-
return this._buildPlayer(i,
|
|
2226
|
+
return this._buildPlayer(i, new Map(), styles);
|
|
2218
2227
|
});
|
|
2219
2228
|
const player = optimizeGroupPlayer(players);
|
|
2220
|
-
this._playersById
|
|
2229
|
+
this._playersById.set(id, player);
|
|
2221
2230
|
player.onDestroy(() => this.destroy(id));
|
|
2222
2231
|
this.players.push(player);
|
|
2223
2232
|
return player;
|
|
@@ -2225,14 +2234,14 @@ class TimelineAnimationEngine {
|
|
|
2225
2234
|
destroy(id) {
|
|
2226
2235
|
const player = this._getPlayer(id);
|
|
2227
2236
|
player.destroy();
|
|
2228
|
-
|
|
2237
|
+
this._playersById.delete(id);
|
|
2229
2238
|
const index = this.players.indexOf(player);
|
|
2230
2239
|
if (index >= 0) {
|
|
2231
2240
|
this.players.splice(index, 1);
|
|
2232
2241
|
}
|
|
2233
2242
|
}
|
|
2234
2243
|
_getPlayer(id) {
|
|
2235
|
-
const player = this._playersById
|
|
2244
|
+
const player = this._playersById.get(id);
|
|
2236
2245
|
if (!player) {
|
|
2237
2246
|
throw new Error(`Unable to find the timeline player referenced by ${id}`);
|
|
2238
2247
|
}
|
|
@@ -2354,14 +2363,14 @@ class AnimationTransitionNamespace {
|
|
|
2354
2363
|
this.hostElement = hostElement;
|
|
2355
2364
|
this._engine = _engine;
|
|
2356
2365
|
this.players = [];
|
|
2357
|
-
this._triggers =
|
|
2366
|
+
this._triggers = new Map();
|
|
2358
2367
|
this._queue = [];
|
|
2359
2368
|
this._elementListeners = new Map();
|
|
2360
2369
|
this._hostClassName = 'ng-tns-' + id;
|
|
2361
2370
|
addClass(hostElement, this._hostClassName);
|
|
2362
2371
|
}
|
|
2363
2372
|
listen(element, name, phase, callback) {
|
|
2364
|
-
if (!this._triggers.
|
|
2373
|
+
if (!this._triggers.has(name)) {
|
|
2365
2374
|
throw new Error(`Unable to listen on the animation trigger event "${phase}" because the animation trigger "${name}" doesn\'t exist!`);
|
|
2366
2375
|
}
|
|
2367
2376
|
if (phase == null || phase.length == 0) {
|
|
@@ -2370,14 +2379,14 @@ class AnimationTransitionNamespace {
|
|
|
2370
2379
|
if (!isTriggerEventValid(phase)) {
|
|
2371
2380
|
throw new Error(`The provided animation trigger event "${phase}" for the animation trigger "${name}" is not supported!`);
|
|
2372
2381
|
}
|
|
2373
|
-
const listeners =
|
|
2382
|
+
const listeners = getOrSetDefaultValue(this._elementListeners, element, []);
|
|
2374
2383
|
const data = { name, phase, callback };
|
|
2375
2384
|
listeners.push(data);
|
|
2376
|
-
const triggersWithStates =
|
|
2377
|
-
if (!triggersWithStates.
|
|
2385
|
+
const triggersWithStates = getOrSetDefaultValue(this._engine.statesByElement, element, new Map());
|
|
2386
|
+
if (!triggersWithStates.has(name)) {
|
|
2378
2387
|
addClass(element, NG_TRIGGER_CLASSNAME);
|
|
2379
2388
|
addClass(element, NG_TRIGGER_CLASSNAME + '-' + name);
|
|
2380
|
-
triggersWithStates
|
|
2389
|
+
triggersWithStates.set(name, DEFAULT_STATE_VALUE);
|
|
2381
2390
|
}
|
|
2382
2391
|
return () => {
|
|
2383
2392
|
// the event listener is removed AFTER the flush has occurred such
|
|
@@ -2388,24 +2397,24 @@ class AnimationTransitionNamespace {
|
|
|
2388
2397
|
if (index >= 0) {
|
|
2389
2398
|
listeners.splice(index, 1);
|
|
2390
2399
|
}
|
|
2391
|
-
if (!this._triggers
|
|
2392
|
-
delete
|
|
2400
|
+
if (!this._triggers.has(name)) {
|
|
2401
|
+
triggersWithStates.delete(name);
|
|
2393
2402
|
}
|
|
2394
2403
|
});
|
|
2395
2404
|
};
|
|
2396
2405
|
}
|
|
2397
2406
|
register(name, ast) {
|
|
2398
|
-
if (this._triggers
|
|
2407
|
+
if (this._triggers.has(name)) {
|
|
2399
2408
|
// throw
|
|
2400
2409
|
return false;
|
|
2401
2410
|
}
|
|
2402
2411
|
else {
|
|
2403
|
-
this._triggers
|
|
2412
|
+
this._triggers.set(name, ast);
|
|
2404
2413
|
return true;
|
|
2405
2414
|
}
|
|
2406
2415
|
}
|
|
2407
2416
|
_getTrigger(name) {
|
|
2408
|
-
const trigger = this._triggers
|
|
2417
|
+
const trigger = this._triggers.get(name);
|
|
2409
2418
|
if (!trigger) {
|
|
2410
2419
|
throw new Error(`The provided animation trigger "${name}" has not been registered!`);
|
|
2411
2420
|
}
|
|
@@ -2418,15 +2427,15 @@ class AnimationTransitionNamespace {
|
|
|
2418
2427
|
if (!triggersWithStates) {
|
|
2419
2428
|
addClass(element, NG_TRIGGER_CLASSNAME);
|
|
2420
2429
|
addClass(element, NG_TRIGGER_CLASSNAME + '-' + triggerName);
|
|
2421
|
-
this._engine.statesByElement.set(element, triggersWithStates =
|
|
2430
|
+
this._engine.statesByElement.set(element, triggersWithStates = new Map());
|
|
2422
2431
|
}
|
|
2423
|
-
let fromState = triggersWithStates
|
|
2432
|
+
let fromState = triggersWithStates.get(triggerName);
|
|
2424
2433
|
const toState = new StateValue(value, this.id);
|
|
2425
2434
|
const isObj = value && value.hasOwnProperty('value');
|
|
2426
2435
|
if (!isObj && fromState) {
|
|
2427
2436
|
toState.absorbOptions(fromState.options);
|
|
2428
2437
|
}
|
|
2429
|
-
triggersWithStates
|
|
2438
|
+
triggersWithStates.set(triggerName, toState);
|
|
2430
2439
|
if (!fromState) {
|
|
2431
2440
|
fromState = DEFAULT_STATE_VALUE;
|
|
2432
2441
|
}
|
|
@@ -2456,7 +2465,7 @@ class AnimationTransitionNamespace {
|
|
|
2456
2465
|
}
|
|
2457
2466
|
return;
|
|
2458
2467
|
}
|
|
2459
|
-
const playersOnElement =
|
|
2468
|
+
const playersOnElement = getOrSetDefaultValue(this._engine.playersByElement, element, []);
|
|
2460
2469
|
playersOnElement.forEach(player => {
|
|
2461
2470
|
// only remove the player if it is queued on the EXACT same trigger/namespace
|
|
2462
2471
|
// we only also deal with queued players here because if the animation has
|
|
@@ -2500,10 +2509,8 @@ class AnimationTransitionNamespace {
|
|
|
2500
2509
|
return player;
|
|
2501
2510
|
}
|
|
2502
2511
|
deregister(name) {
|
|
2503
|
-
|
|
2504
|
-
this._engine.statesByElement.forEach(
|
|
2505
|
-
delete stateMap[name];
|
|
2506
|
-
});
|
|
2512
|
+
this._triggers.delete(name);
|
|
2513
|
+
this._engine.statesByElement.forEach(stateMap => stateMap.delete(name));
|
|
2507
2514
|
this._elementListeners.forEach((listeners, element) => {
|
|
2508
2515
|
this._elementListeners.set(element, listeners.filter(entry => {
|
|
2509
2516
|
return entry.name != name;
|
|
@@ -2546,11 +2553,11 @@ class AnimationTransitionNamespace {
|
|
|
2546
2553
|
const previousTriggersValues = new Map();
|
|
2547
2554
|
if (triggerStates) {
|
|
2548
2555
|
const players = [];
|
|
2549
|
-
|
|
2550
|
-
previousTriggersValues.set(triggerName,
|
|
2556
|
+
triggerStates.forEach((state, triggerName) => {
|
|
2557
|
+
previousTriggersValues.set(triggerName, state.value);
|
|
2551
2558
|
// this check is here in the event that an element is removed
|
|
2552
2559
|
// twice (both on the host level and the component level)
|
|
2553
|
-
if (this._triggers
|
|
2560
|
+
if (this._triggers.has(triggerName)) {
|
|
2554
2561
|
const player = this.trigger(element, triggerName, VOID_VALUE, defaultToFallback);
|
|
2555
2562
|
if (player) {
|
|
2556
2563
|
players.push(player);
|
|
@@ -2579,9 +2586,9 @@ class AnimationTransitionNamespace {
|
|
|
2579
2586
|
if (visitedTriggers.has(triggerName))
|
|
2580
2587
|
return;
|
|
2581
2588
|
visitedTriggers.add(triggerName);
|
|
2582
|
-
const trigger = this._triggers
|
|
2589
|
+
const trigger = this._triggers.get(triggerName);
|
|
2583
2590
|
const transition = trigger.fallbackTransition;
|
|
2584
|
-
const fromState = elementStates
|
|
2591
|
+
const fromState = elementStates.get(triggerName) || DEFAULT_STATE_VALUE;
|
|
2585
2592
|
const toState = new StateValue(VOID_VALUE);
|
|
2586
2593
|
const player = new TransitionAnimationPlayer(this.id, triggerName, element);
|
|
2587
2594
|
this._engine.totalQueuedPlayers++;
|
|
@@ -2823,11 +2830,9 @@ class TransitionAnimationEngine {
|
|
|
2823
2830
|
const namespaces = new Set();
|
|
2824
2831
|
const elementStates = this.statesByElement.get(element);
|
|
2825
2832
|
if (elementStates) {
|
|
2826
|
-
|
|
2827
|
-
|
|
2828
|
-
|
|
2829
|
-
if (nsId) {
|
|
2830
|
-
const ns = this._fetchNamespace(nsId);
|
|
2833
|
+
for (let stateValue of elementStates.values()) {
|
|
2834
|
+
if (stateValue.namespaceId) {
|
|
2835
|
+
const ns = this._fetchNamespace(stateValue.namespaceId);
|
|
2831
2836
|
if (ns) {
|
|
2832
2837
|
namespaces.add(ns);
|
|
2833
2838
|
}
|
|
@@ -3135,8 +3140,10 @@ class TransitionAnimationEngine {
|
|
|
3135
3140
|
// we need to restore the previous trigger value since the element has
|
|
3136
3141
|
// only been moved and hasn't actually left the DOM
|
|
3137
3142
|
const triggersWithStates = this.statesByElement.get(entry.element);
|
|
3138
|
-
if (triggersWithStates && triggersWithStates
|
|
3139
|
-
triggersWithStates
|
|
3143
|
+
if (triggersWithStates && triggersWithStates.has(entry.triggerName)) {
|
|
3144
|
+
const state = triggersWithStates.get(entry.triggerName);
|
|
3145
|
+
state.value = previousValue;
|
|
3146
|
+
triggersWithStates.set(entry.triggerName, state);
|
|
3140
3147
|
}
|
|
3141
3148
|
}
|
|
3142
3149
|
player.destroy();
|
|
@@ -3186,24 +3193,22 @@ class TransitionAnimationEngine {
|
|
|
3186
3193
|
subTimelines.append(element, instruction.timelines);
|
|
3187
3194
|
const tuple = { instruction, player, element };
|
|
3188
3195
|
queuedInstructions.push(tuple);
|
|
3189
|
-
instruction.queriedElements.forEach(element =>
|
|
3196
|
+
instruction.queriedElements.forEach(element => getOrSetDefaultValue(queriedElements, element, []).push(player));
|
|
3190
3197
|
instruction.preStyleProps.forEach((stringMap, element) => {
|
|
3191
|
-
|
|
3192
|
-
if (props.length) {
|
|
3198
|
+
if (stringMap.size) {
|
|
3193
3199
|
let setVal = allPreStyleElements.get(element);
|
|
3194
3200
|
if (!setVal) {
|
|
3195
3201
|
allPreStyleElements.set(element, setVal = new Set());
|
|
3196
3202
|
}
|
|
3197
|
-
|
|
3203
|
+
stringMap.forEach((_, prop) => setVal.add(prop));
|
|
3198
3204
|
}
|
|
3199
3205
|
});
|
|
3200
3206
|
instruction.postStyleProps.forEach((stringMap, element) => {
|
|
3201
|
-
const props = Object.keys(stringMap);
|
|
3202
3207
|
let setVal = allPostStyleElements.get(element);
|
|
3203
3208
|
if (!setVal) {
|
|
3204
3209
|
allPostStyleElements.set(element, setVal = new Set());
|
|
3205
3210
|
}
|
|
3206
|
-
|
|
3211
|
+
stringMap.forEach((_, prop) => setVal.add(prop));
|
|
3207
3212
|
});
|
|
3208
3213
|
});
|
|
3209
3214
|
}
|
|
@@ -3233,7 +3238,7 @@ class TransitionAnimationEngine {
|
|
|
3233
3238
|
const element = player.element;
|
|
3234
3239
|
const previousPlayers = this._getPreviousPlayers(element, false, player.namespaceId, player.triggerName, null);
|
|
3235
3240
|
previousPlayers.forEach(prevPlayer => {
|
|
3236
|
-
|
|
3241
|
+
getOrSetDefaultValue(allPreviousPlayersMap, element, []).push(prevPlayer);
|
|
3237
3242
|
prevPlayer.destroy();
|
|
3238
3243
|
});
|
|
3239
3244
|
});
|
|
@@ -3261,9 +3266,10 @@ class TransitionAnimationEngine {
|
|
|
3261
3266
|
cloakAndComputeStyles(preStylesMap, this.driver, new Set(nodes), allPreStyleElements, ɵPRE_STYLE);
|
|
3262
3267
|
});
|
|
3263
3268
|
replaceNodes.forEach(node => {
|
|
3269
|
+
var _a, _b;
|
|
3264
3270
|
const post = postStylesMap.get(node);
|
|
3265
3271
|
const pre = preStylesMap.get(node);
|
|
3266
|
-
postStylesMap.set(node,
|
|
3272
|
+
postStylesMap.set(node, new Map([...Array.from((_a = post === null || post === void 0 ? void 0 : post.entries()) !== null && _a !== void 0 ? _a : []), ...Array.from((_b = pre === null || pre === void 0 ? void 0 : pre.entries()) !== null && _b !== void 0 ? _b : [])]));
|
|
3267
3273
|
});
|
|
3268
3274
|
const rootPlayers = [];
|
|
3269
3275
|
const subPlayers = [];
|
|
@@ -3457,7 +3463,7 @@ class TransitionAnimationEngine {
|
|
|
3457
3463
|
for (const timelineInstruction of instruction.timelines) {
|
|
3458
3464
|
const element = timelineInstruction.element;
|
|
3459
3465
|
const isQueriedElement = element !== rootElement;
|
|
3460
|
-
const players =
|
|
3466
|
+
const players = getOrSetDefaultValue(allPreviousPlayersMap, element, []);
|
|
3461
3467
|
const previousPlayers = this._getPreviousPlayers(element, isQueriedElement, targetNameSpaceId, targetTriggerName, instruction.toState);
|
|
3462
3468
|
previousPlayers.forEach(player => {
|
|
3463
3469
|
const realPlayer = player.getRealPlayer();
|
|
@@ -3500,7 +3506,7 @@ class TransitionAnimationEngine {
|
|
|
3500
3506
|
});
|
|
3501
3507
|
const preStyles = preStylesMap.get(element);
|
|
3502
3508
|
const postStyles = postStylesMap.get(element);
|
|
3503
|
-
const keyframes = normalizeKeyframes(this.driver, this._normalizer, element, timelineInstruction.keyframes, preStyles, postStyles);
|
|
3509
|
+
const keyframes = normalizeKeyframes$1(this.driver, this._normalizer, element, timelineInstruction.keyframes, preStyles, postStyles);
|
|
3504
3510
|
const player = this._buildPlayer(timelineInstruction, keyframes, previousPlayers);
|
|
3505
3511
|
// this means that this particular player belongs to a sub trigger. It is
|
|
3506
3512
|
// important that we match this player up with the corresponding (@trigger.listener)
|
|
@@ -3515,7 +3521,7 @@ class TransitionAnimationEngine {
|
|
|
3515
3521
|
return player;
|
|
3516
3522
|
});
|
|
3517
3523
|
allQueriedPlayers.forEach(player => {
|
|
3518
|
-
|
|
3524
|
+
getOrSetDefaultValue(this.playersByQueriedElement, player.element, []).push(player);
|
|
3519
3525
|
player.onDone(() => deleteOrUnsetInMap(this.playersByQueriedElement, player.element, player));
|
|
3520
3526
|
});
|
|
3521
3527
|
allConsumedElements.forEach(element => addClass(element, NG_ANIMATING_CLASSNAME));
|
|
@@ -3527,7 +3533,7 @@ class TransitionAnimationEngine {
|
|
|
3527
3533
|
// this basically makes all of the callbacks for sub element animations
|
|
3528
3534
|
// be dependent on the upper players for when they finish
|
|
3529
3535
|
allSubElements.forEach(element => {
|
|
3530
|
-
|
|
3536
|
+
getOrSetDefaultValue(skippedPlayersMap, element, []).push(player);
|
|
3531
3537
|
});
|
|
3532
3538
|
return player;
|
|
3533
3539
|
}
|
|
@@ -3547,7 +3553,7 @@ class TransitionAnimationPlayer {
|
|
|
3547
3553
|
this.element = element;
|
|
3548
3554
|
this._player = new NoopAnimationPlayer();
|
|
3549
3555
|
this._containsRealPlayer = false;
|
|
3550
|
-
this._queuedCallbacks =
|
|
3556
|
+
this._queuedCallbacks = new Map();
|
|
3551
3557
|
this.destroyed = false;
|
|
3552
3558
|
this.markedForDestroy = false;
|
|
3553
3559
|
this.disabled = false;
|
|
@@ -3558,10 +3564,10 @@ class TransitionAnimationPlayer {
|
|
|
3558
3564
|
if (this._containsRealPlayer)
|
|
3559
3565
|
return;
|
|
3560
3566
|
this._player = player;
|
|
3561
|
-
|
|
3562
|
-
|
|
3567
|
+
this._queuedCallbacks.forEach((callbacks, phase) => {
|
|
3568
|
+
callbacks.forEach(callback => listenOnPlayer(player, phase, undefined, callback));
|
|
3563
3569
|
});
|
|
3564
|
-
this._queuedCallbacks
|
|
3570
|
+
this._queuedCallbacks.clear();
|
|
3565
3571
|
this._containsRealPlayer = true;
|
|
3566
3572
|
this.overrideTotalTime(player.totalTime);
|
|
3567
3573
|
this.queued = false;
|
|
@@ -3581,7 +3587,7 @@ class TransitionAnimationPlayer {
|
|
|
3581
3587
|
player.onDestroy(() => this.destroy());
|
|
3582
3588
|
}
|
|
3583
3589
|
_queueEvent(name, callback) {
|
|
3584
|
-
|
|
3590
|
+
getOrSetDefaultValue(this._queuedCallbacks, name, []).push(callback);
|
|
3585
3591
|
}
|
|
3586
3592
|
onDone(fn) {
|
|
3587
3593
|
if (this.queued) {
|
|
@@ -3643,29 +3649,14 @@ class TransitionAnimationPlayer {
|
|
|
3643
3649
|
}
|
|
3644
3650
|
}
|
|
3645
3651
|
function deleteOrUnsetInMap(map, key, value) {
|
|
3646
|
-
let currentValues;
|
|
3647
|
-
if (
|
|
3648
|
-
currentValues
|
|
3649
|
-
|
|
3650
|
-
|
|
3651
|
-
const index = currentValues.indexOf(value);
|
|
3652
|
-
currentValues.splice(index, 1);
|
|
3653
|
-
}
|
|
3654
|
-
if (currentValues.length == 0) {
|
|
3655
|
-
map.delete(key);
|
|
3656
|
-
}
|
|
3652
|
+
let currentValues = map.get(key);
|
|
3653
|
+
if (currentValues) {
|
|
3654
|
+
if (currentValues.length) {
|
|
3655
|
+
const index = currentValues.indexOf(value);
|
|
3656
|
+
currentValues.splice(index, 1);
|
|
3657
3657
|
}
|
|
3658
|
-
|
|
3659
|
-
|
|
3660
|
-
currentValues = map[key];
|
|
3661
|
-
if (currentValues) {
|
|
3662
|
-
if (currentValues.length) {
|
|
3663
|
-
const index = currentValues.indexOf(value);
|
|
3664
|
-
currentValues.splice(index, 1);
|
|
3665
|
-
}
|
|
3666
|
-
if (currentValues.length == 0) {
|
|
3667
|
-
delete map[key];
|
|
3668
|
-
}
|
|
3658
|
+
if (currentValues.length == 0) {
|
|
3659
|
+
map.delete(key);
|
|
3669
3660
|
}
|
|
3670
3661
|
}
|
|
3671
3662
|
return currentValues;
|
|
@@ -3692,9 +3683,10 @@ function cloakAndComputeStyles(valuesMap, driver, elements, elementPropsMap, def
|
|
|
3692
3683
|
elements.forEach(element => cloakVals.push(cloakElement(element)));
|
|
3693
3684
|
const failedElements = [];
|
|
3694
3685
|
elementPropsMap.forEach((props, element) => {
|
|
3695
|
-
const styles =
|
|
3686
|
+
const styles = new Map();
|
|
3696
3687
|
props.forEach(prop => {
|
|
3697
|
-
const value =
|
|
3688
|
+
const value = driver.computeStyle(element, prop, defaultStyle);
|
|
3689
|
+
styles.set(prop, value);
|
|
3698
3690
|
// there is no easy way to detect this because a sub element could be removed
|
|
3699
3691
|
// by a parent animation element being detached.
|
|
3700
3692
|
if (!value || value.length == 0) {
|
|
@@ -3880,13 +3872,6 @@ class AnimationEngine {
|
|
|
3880
3872
|
}
|
|
3881
3873
|
}
|
|
3882
3874
|
|
|
3883
|
-
/**
|
|
3884
|
-
* @license
|
|
3885
|
-
* Copyright Google LLC All Rights Reserved.
|
|
3886
|
-
*
|
|
3887
|
-
* Use of this source code is governed by an MIT-style license that can be
|
|
3888
|
-
* found in the LICENSE file at https://angular.io/license
|
|
3889
|
-
*/
|
|
3890
3875
|
/**
|
|
3891
3876
|
* Returns an instance of `SpecialCasedStyles` if and when any special (non animateable) styles are
|
|
3892
3877
|
* detected.
|
|
@@ -3907,7 +3892,7 @@ function packageNonAnimatableStyles(element, styles) {
|
|
|
3907
3892
|
endStyles = filterNonAnimatableStyles(styles[styles.length - 1]);
|
|
3908
3893
|
}
|
|
3909
3894
|
}
|
|
3910
|
-
else if (styles) {
|
|
3895
|
+
else if (styles instanceof Map) {
|
|
3911
3896
|
startStyles = filterNonAnimatableStyles(styles);
|
|
3912
3897
|
}
|
|
3913
3898
|
return (startStyles || endStyles) ? new SpecialCasedStyles(element, startStyles, endStyles) :
|
|
@@ -3929,7 +3914,7 @@ class SpecialCasedStyles {
|
|
|
3929
3914
|
this._state = 0 /* Pending */;
|
|
3930
3915
|
let initialStyles = SpecialCasedStyles.initialStylesByElement.get(_element);
|
|
3931
3916
|
if (!initialStyles) {
|
|
3932
|
-
SpecialCasedStyles.initialStylesByElement.set(_element, initialStyles =
|
|
3917
|
+
SpecialCasedStyles.initialStylesByElement.set(_element, initialStyles = new Map());
|
|
3933
3918
|
}
|
|
3934
3919
|
this._initialStyles = initialStyles;
|
|
3935
3920
|
}
|
|
@@ -3972,454 +3957,18 @@ class SpecialCasedStyles {
|
|
|
3972
3957
|
SpecialCasedStyles.initialStylesByElement = ( /* @__PURE__ */new WeakMap());
|
|
3973
3958
|
function filterNonAnimatableStyles(styles) {
|
|
3974
3959
|
let result = null;
|
|
3975
|
-
|
|
3976
|
-
for (let i = 0; i < props.length; i++) {
|
|
3977
|
-
const prop = props[i];
|
|
3960
|
+
styles.forEach((val, prop) => {
|
|
3978
3961
|
if (isNonAnimatableStyle(prop)) {
|
|
3979
|
-
result = result ||
|
|
3980
|
-
result
|
|
3962
|
+
result = result || new Map();
|
|
3963
|
+
result.set(prop, val);
|
|
3981
3964
|
}
|
|
3982
|
-
}
|
|
3965
|
+
});
|
|
3983
3966
|
return result;
|
|
3984
3967
|
}
|
|
3985
3968
|
function isNonAnimatableStyle(prop) {
|
|
3986
3969
|
return prop === 'display' || prop === 'position';
|
|
3987
3970
|
}
|
|
3988
3971
|
|
|
3989
|
-
/**
|
|
3990
|
-
* @license
|
|
3991
|
-
* Copyright Google LLC All Rights Reserved.
|
|
3992
|
-
*
|
|
3993
|
-
* Use of this source code is governed by an MIT-style license that can be
|
|
3994
|
-
* found in the LICENSE file at https://angular.io/license
|
|
3995
|
-
*/
|
|
3996
|
-
const ELAPSED_TIME_MAX_DECIMAL_PLACES = 3;
|
|
3997
|
-
const ANIMATION_PROP = 'animation';
|
|
3998
|
-
const ANIMATIONEND_EVENT = 'animationend';
|
|
3999
|
-
const ONE_SECOND = 1000;
|
|
4000
|
-
class ElementAnimationStyleHandler {
|
|
4001
|
-
constructor(_element, _name, _duration, _delay, _easing, _fillMode, _onDoneFn) {
|
|
4002
|
-
this._element = _element;
|
|
4003
|
-
this._name = _name;
|
|
4004
|
-
this._duration = _duration;
|
|
4005
|
-
this._delay = _delay;
|
|
4006
|
-
this._easing = _easing;
|
|
4007
|
-
this._fillMode = _fillMode;
|
|
4008
|
-
this._onDoneFn = _onDoneFn;
|
|
4009
|
-
this._finished = false;
|
|
4010
|
-
this._destroyed = false;
|
|
4011
|
-
this._startTime = 0;
|
|
4012
|
-
this._position = 0;
|
|
4013
|
-
this._eventFn = (e) => this._handleCallback(e);
|
|
4014
|
-
}
|
|
4015
|
-
apply() {
|
|
4016
|
-
applyKeyframeAnimation(this._element, `${this._duration}ms ${this._easing} ${this._delay}ms 1 normal ${this._fillMode} ${this._name}`);
|
|
4017
|
-
addRemoveAnimationEvent(this._element, this._eventFn, false);
|
|
4018
|
-
this._startTime = Date.now();
|
|
4019
|
-
}
|
|
4020
|
-
pause() {
|
|
4021
|
-
playPauseAnimation(this._element, this._name, 'paused');
|
|
4022
|
-
}
|
|
4023
|
-
resume() {
|
|
4024
|
-
playPauseAnimation(this._element, this._name, 'running');
|
|
4025
|
-
}
|
|
4026
|
-
setPosition(position) {
|
|
4027
|
-
const index = findIndexForAnimation(this._element, this._name);
|
|
4028
|
-
this._position = position * this._duration;
|
|
4029
|
-
setAnimationStyle(this._element, 'Delay', `-${this._position}ms`, index);
|
|
4030
|
-
}
|
|
4031
|
-
getPosition() {
|
|
4032
|
-
return this._position;
|
|
4033
|
-
}
|
|
4034
|
-
_handleCallback(event) {
|
|
4035
|
-
const timestamp = event._ngTestManualTimestamp || Date.now();
|
|
4036
|
-
const elapsedTime = parseFloat(event.elapsedTime.toFixed(ELAPSED_TIME_MAX_DECIMAL_PLACES)) * ONE_SECOND;
|
|
4037
|
-
if (event.animationName == this._name &&
|
|
4038
|
-
Math.max(timestamp - this._startTime, 0) >= this._delay && elapsedTime >= this._duration) {
|
|
4039
|
-
this.finish();
|
|
4040
|
-
}
|
|
4041
|
-
}
|
|
4042
|
-
finish() {
|
|
4043
|
-
if (this._finished)
|
|
4044
|
-
return;
|
|
4045
|
-
this._finished = true;
|
|
4046
|
-
this._onDoneFn();
|
|
4047
|
-
addRemoveAnimationEvent(this._element, this._eventFn, true);
|
|
4048
|
-
}
|
|
4049
|
-
destroy() {
|
|
4050
|
-
if (this._destroyed)
|
|
4051
|
-
return;
|
|
4052
|
-
this._destroyed = true;
|
|
4053
|
-
this.finish();
|
|
4054
|
-
removeKeyframeAnimation(this._element, this._name);
|
|
4055
|
-
}
|
|
4056
|
-
}
|
|
4057
|
-
function playPauseAnimation(element, name, status) {
|
|
4058
|
-
const index = findIndexForAnimation(element, name);
|
|
4059
|
-
setAnimationStyle(element, 'PlayState', status, index);
|
|
4060
|
-
}
|
|
4061
|
-
function applyKeyframeAnimation(element, value) {
|
|
4062
|
-
const anim = getAnimationStyle(element, '').trim();
|
|
4063
|
-
let index = 0;
|
|
4064
|
-
if (anim.length) {
|
|
4065
|
-
index = countChars(anim, ',') + 1;
|
|
4066
|
-
value = `${anim}, ${value}`;
|
|
4067
|
-
}
|
|
4068
|
-
setAnimationStyle(element, '', value);
|
|
4069
|
-
return index;
|
|
4070
|
-
}
|
|
4071
|
-
function removeKeyframeAnimation(element, name) {
|
|
4072
|
-
const anim = getAnimationStyle(element, '');
|
|
4073
|
-
const tokens = anim.split(',');
|
|
4074
|
-
const index = findMatchingTokenIndex(tokens, name);
|
|
4075
|
-
if (index >= 0) {
|
|
4076
|
-
tokens.splice(index, 1);
|
|
4077
|
-
const newValue = tokens.join(',');
|
|
4078
|
-
setAnimationStyle(element, '', newValue);
|
|
4079
|
-
}
|
|
4080
|
-
}
|
|
4081
|
-
function findIndexForAnimation(element, value) {
|
|
4082
|
-
const anim = getAnimationStyle(element, '');
|
|
4083
|
-
if (anim.indexOf(',') > 0) {
|
|
4084
|
-
const tokens = anim.split(',');
|
|
4085
|
-
return findMatchingTokenIndex(tokens, value);
|
|
4086
|
-
}
|
|
4087
|
-
return findMatchingTokenIndex([anim], value);
|
|
4088
|
-
}
|
|
4089
|
-
function findMatchingTokenIndex(tokens, searchToken) {
|
|
4090
|
-
for (let i = 0; i < tokens.length; i++) {
|
|
4091
|
-
if (tokens[i].indexOf(searchToken) >= 0) {
|
|
4092
|
-
return i;
|
|
4093
|
-
}
|
|
4094
|
-
}
|
|
4095
|
-
return -1;
|
|
4096
|
-
}
|
|
4097
|
-
function addRemoveAnimationEvent(element, fn, doRemove) {
|
|
4098
|
-
doRemove ? element.removeEventListener(ANIMATIONEND_EVENT, fn) :
|
|
4099
|
-
element.addEventListener(ANIMATIONEND_EVENT, fn);
|
|
4100
|
-
}
|
|
4101
|
-
function setAnimationStyle(element, name, value, index) {
|
|
4102
|
-
const prop = ANIMATION_PROP + name;
|
|
4103
|
-
if (index != null) {
|
|
4104
|
-
const oldValue = element.style[prop];
|
|
4105
|
-
if (oldValue.length) {
|
|
4106
|
-
const tokens = oldValue.split(',');
|
|
4107
|
-
tokens[index] = value;
|
|
4108
|
-
value = tokens.join(',');
|
|
4109
|
-
}
|
|
4110
|
-
}
|
|
4111
|
-
element.style[prop] = value;
|
|
4112
|
-
}
|
|
4113
|
-
function getAnimationStyle(element, name) {
|
|
4114
|
-
return element.style[ANIMATION_PROP + name] || '';
|
|
4115
|
-
}
|
|
4116
|
-
function countChars(value, char) {
|
|
4117
|
-
let count = 0;
|
|
4118
|
-
for (let i = 0; i < value.length; i++) {
|
|
4119
|
-
const c = value.charAt(i);
|
|
4120
|
-
if (c === char)
|
|
4121
|
-
count++;
|
|
4122
|
-
}
|
|
4123
|
-
return count;
|
|
4124
|
-
}
|
|
4125
|
-
|
|
4126
|
-
const DEFAULT_FILL_MODE = 'forwards';
|
|
4127
|
-
const DEFAULT_EASING = 'linear';
|
|
4128
|
-
class CssKeyframesPlayer {
|
|
4129
|
-
constructor(element, keyframes, animationName, _duration, _delay, easing, _finalStyles, _specialStyles) {
|
|
4130
|
-
this.element = element;
|
|
4131
|
-
this.keyframes = keyframes;
|
|
4132
|
-
this.animationName = animationName;
|
|
4133
|
-
this._duration = _duration;
|
|
4134
|
-
this._delay = _delay;
|
|
4135
|
-
this._finalStyles = _finalStyles;
|
|
4136
|
-
this._specialStyles = _specialStyles;
|
|
4137
|
-
this._onDoneFns = [];
|
|
4138
|
-
this._onStartFns = [];
|
|
4139
|
-
this._onDestroyFns = [];
|
|
4140
|
-
this.currentSnapshot = {};
|
|
4141
|
-
this._state = 0;
|
|
4142
|
-
this.easing = easing || DEFAULT_EASING;
|
|
4143
|
-
this.totalTime = _duration + _delay;
|
|
4144
|
-
this._buildStyler();
|
|
4145
|
-
}
|
|
4146
|
-
onStart(fn) {
|
|
4147
|
-
this._onStartFns.push(fn);
|
|
4148
|
-
}
|
|
4149
|
-
onDone(fn) {
|
|
4150
|
-
this._onDoneFns.push(fn);
|
|
4151
|
-
}
|
|
4152
|
-
onDestroy(fn) {
|
|
4153
|
-
this._onDestroyFns.push(fn);
|
|
4154
|
-
}
|
|
4155
|
-
destroy() {
|
|
4156
|
-
this.init();
|
|
4157
|
-
if (this._state >= 4 /* DESTROYED */)
|
|
4158
|
-
return;
|
|
4159
|
-
this._state = 4 /* DESTROYED */;
|
|
4160
|
-
this._styler.destroy();
|
|
4161
|
-
this._flushStartFns();
|
|
4162
|
-
this._flushDoneFns();
|
|
4163
|
-
if (this._specialStyles) {
|
|
4164
|
-
this._specialStyles.destroy();
|
|
4165
|
-
}
|
|
4166
|
-
this._onDestroyFns.forEach(fn => fn());
|
|
4167
|
-
this._onDestroyFns = [];
|
|
4168
|
-
}
|
|
4169
|
-
_flushDoneFns() {
|
|
4170
|
-
this._onDoneFns.forEach(fn => fn());
|
|
4171
|
-
this._onDoneFns = [];
|
|
4172
|
-
}
|
|
4173
|
-
_flushStartFns() {
|
|
4174
|
-
this._onStartFns.forEach(fn => fn());
|
|
4175
|
-
this._onStartFns = [];
|
|
4176
|
-
}
|
|
4177
|
-
finish() {
|
|
4178
|
-
this.init();
|
|
4179
|
-
if (this._state >= 3 /* FINISHED */)
|
|
4180
|
-
return;
|
|
4181
|
-
this._state = 3 /* FINISHED */;
|
|
4182
|
-
this._styler.finish();
|
|
4183
|
-
this._flushStartFns();
|
|
4184
|
-
if (this._specialStyles) {
|
|
4185
|
-
this._specialStyles.finish();
|
|
4186
|
-
}
|
|
4187
|
-
this._flushDoneFns();
|
|
4188
|
-
}
|
|
4189
|
-
setPosition(value) {
|
|
4190
|
-
this._styler.setPosition(value);
|
|
4191
|
-
}
|
|
4192
|
-
getPosition() {
|
|
4193
|
-
return this._styler.getPosition();
|
|
4194
|
-
}
|
|
4195
|
-
hasStarted() {
|
|
4196
|
-
return this._state >= 2 /* STARTED */;
|
|
4197
|
-
}
|
|
4198
|
-
init() {
|
|
4199
|
-
if (this._state >= 1 /* INITIALIZED */)
|
|
4200
|
-
return;
|
|
4201
|
-
this._state = 1 /* INITIALIZED */;
|
|
4202
|
-
const elm = this.element;
|
|
4203
|
-
this._styler.apply();
|
|
4204
|
-
if (this._delay) {
|
|
4205
|
-
this._styler.pause();
|
|
4206
|
-
}
|
|
4207
|
-
}
|
|
4208
|
-
play() {
|
|
4209
|
-
this.init();
|
|
4210
|
-
if (!this.hasStarted()) {
|
|
4211
|
-
this._flushStartFns();
|
|
4212
|
-
this._state = 2 /* STARTED */;
|
|
4213
|
-
if (this._specialStyles) {
|
|
4214
|
-
this._specialStyles.start();
|
|
4215
|
-
}
|
|
4216
|
-
}
|
|
4217
|
-
this._styler.resume();
|
|
4218
|
-
}
|
|
4219
|
-
pause() {
|
|
4220
|
-
this.init();
|
|
4221
|
-
this._styler.pause();
|
|
4222
|
-
}
|
|
4223
|
-
restart() {
|
|
4224
|
-
this.reset();
|
|
4225
|
-
this.play();
|
|
4226
|
-
}
|
|
4227
|
-
reset() {
|
|
4228
|
-
this._state = 0 /* RESET */;
|
|
4229
|
-
this._styler.destroy();
|
|
4230
|
-
this._buildStyler();
|
|
4231
|
-
this._styler.apply();
|
|
4232
|
-
}
|
|
4233
|
-
_buildStyler() {
|
|
4234
|
-
this._styler = new ElementAnimationStyleHandler(this.element, this.animationName, this._duration, this._delay, this.easing, DEFAULT_FILL_MODE, () => this.finish());
|
|
4235
|
-
}
|
|
4236
|
-
/** @internal */
|
|
4237
|
-
triggerCallback(phaseName) {
|
|
4238
|
-
const methods = phaseName == 'start' ? this._onStartFns : this._onDoneFns;
|
|
4239
|
-
methods.forEach(fn => fn());
|
|
4240
|
-
methods.length = 0;
|
|
4241
|
-
}
|
|
4242
|
-
beforeDestroy() {
|
|
4243
|
-
this.init();
|
|
4244
|
-
const styles = {};
|
|
4245
|
-
if (this.hasStarted()) {
|
|
4246
|
-
const finished = this._state >= 3 /* FINISHED */;
|
|
4247
|
-
Object.keys(this._finalStyles).forEach(prop => {
|
|
4248
|
-
if (prop != 'offset') {
|
|
4249
|
-
styles[prop] = finished ? this._finalStyles[prop] : computeStyle(this.element, prop);
|
|
4250
|
-
}
|
|
4251
|
-
});
|
|
4252
|
-
}
|
|
4253
|
-
this.currentSnapshot = styles;
|
|
4254
|
-
}
|
|
4255
|
-
}
|
|
4256
|
-
|
|
4257
|
-
/**
|
|
4258
|
-
* @license
|
|
4259
|
-
* Copyright Google LLC All Rights Reserved.
|
|
4260
|
-
*
|
|
4261
|
-
* Use of this source code is governed by an MIT-style license that can be
|
|
4262
|
-
* found in the LICENSE file at https://angular.io/license
|
|
4263
|
-
*/
|
|
4264
|
-
class DirectStylePlayer extends NoopAnimationPlayer {
|
|
4265
|
-
constructor(element, styles) {
|
|
4266
|
-
super();
|
|
4267
|
-
this.element = element;
|
|
4268
|
-
this._startingStyles = {};
|
|
4269
|
-
this.__initialized = false;
|
|
4270
|
-
this._styles = hypenatePropsObject(styles);
|
|
4271
|
-
}
|
|
4272
|
-
init() {
|
|
4273
|
-
if (this.__initialized || !this._startingStyles)
|
|
4274
|
-
return;
|
|
4275
|
-
this.__initialized = true;
|
|
4276
|
-
Object.keys(this._styles).forEach(prop => {
|
|
4277
|
-
this._startingStyles[prop] = this.element.style[prop];
|
|
4278
|
-
});
|
|
4279
|
-
super.init();
|
|
4280
|
-
}
|
|
4281
|
-
play() {
|
|
4282
|
-
if (!this._startingStyles)
|
|
4283
|
-
return;
|
|
4284
|
-
this.init();
|
|
4285
|
-
Object.keys(this._styles)
|
|
4286
|
-
.forEach(prop => this.element.style.setProperty(prop, this._styles[prop]));
|
|
4287
|
-
super.play();
|
|
4288
|
-
}
|
|
4289
|
-
destroy() {
|
|
4290
|
-
if (!this._startingStyles)
|
|
4291
|
-
return;
|
|
4292
|
-
Object.keys(this._startingStyles).forEach(prop => {
|
|
4293
|
-
const value = this._startingStyles[prop];
|
|
4294
|
-
if (value) {
|
|
4295
|
-
this.element.style.setProperty(prop, value);
|
|
4296
|
-
}
|
|
4297
|
-
else {
|
|
4298
|
-
this.element.style.removeProperty(prop);
|
|
4299
|
-
}
|
|
4300
|
-
});
|
|
4301
|
-
this._startingStyles = null;
|
|
4302
|
-
super.destroy();
|
|
4303
|
-
}
|
|
4304
|
-
}
|
|
4305
|
-
|
|
4306
|
-
const KEYFRAMES_NAME_PREFIX = 'gen_css_kf_';
|
|
4307
|
-
const TAB_SPACE = ' ';
|
|
4308
|
-
class CssKeyframesDriver {
|
|
4309
|
-
constructor() {
|
|
4310
|
-
this._count = 0;
|
|
4311
|
-
}
|
|
4312
|
-
validateStyleProperty(prop) {
|
|
4313
|
-
return validateStyleProperty(prop);
|
|
4314
|
-
}
|
|
4315
|
-
matchesElement(_element, _selector) {
|
|
4316
|
-
// This method is deprecated and no longer in use so we return false.
|
|
4317
|
-
return false;
|
|
4318
|
-
}
|
|
4319
|
-
containsElement(elm1, elm2) {
|
|
4320
|
-
return containsElement(elm1, elm2);
|
|
4321
|
-
}
|
|
4322
|
-
query(element, selector, multi) {
|
|
4323
|
-
return invokeQuery(element, selector, multi);
|
|
4324
|
-
}
|
|
4325
|
-
computeStyle(element, prop, defaultValue) {
|
|
4326
|
-
return window.getComputedStyle(element)[prop];
|
|
4327
|
-
}
|
|
4328
|
-
buildKeyframeElement(element, name, keyframes) {
|
|
4329
|
-
keyframes = keyframes.map(kf => hypenatePropsObject(kf));
|
|
4330
|
-
let keyframeStr = `@keyframes ${name} {\n`;
|
|
4331
|
-
let tab = '';
|
|
4332
|
-
keyframes.forEach(kf => {
|
|
4333
|
-
tab = TAB_SPACE;
|
|
4334
|
-
const offset = parseFloat(kf['offset']);
|
|
4335
|
-
keyframeStr += `${tab}${offset * 100}% {\n`;
|
|
4336
|
-
tab += TAB_SPACE;
|
|
4337
|
-
Object.keys(kf).forEach(prop => {
|
|
4338
|
-
const value = kf[prop];
|
|
4339
|
-
switch (prop) {
|
|
4340
|
-
case 'offset':
|
|
4341
|
-
return;
|
|
4342
|
-
case 'easing':
|
|
4343
|
-
if (value) {
|
|
4344
|
-
keyframeStr += `${tab}animation-timing-function: ${value};\n`;
|
|
4345
|
-
}
|
|
4346
|
-
return;
|
|
4347
|
-
default:
|
|
4348
|
-
keyframeStr += `${tab}${prop}: ${value};\n`;
|
|
4349
|
-
return;
|
|
4350
|
-
}
|
|
4351
|
-
});
|
|
4352
|
-
keyframeStr += `${tab}}\n`;
|
|
4353
|
-
});
|
|
4354
|
-
keyframeStr += `}\n`;
|
|
4355
|
-
const kfElm = document.createElement('style');
|
|
4356
|
-
kfElm.textContent = keyframeStr;
|
|
4357
|
-
return kfElm;
|
|
4358
|
-
}
|
|
4359
|
-
animate(element, keyframes, duration, delay, easing, previousPlayers = [], scrubberAccessRequested) {
|
|
4360
|
-
if ((typeof ngDevMode === 'undefined' || ngDevMode) && scrubberAccessRequested) {
|
|
4361
|
-
notifyFaultyScrubber();
|
|
4362
|
-
}
|
|
4363
|
-
const previousCssKeyframePlayers = previousPlayers.filter(player => player instanceof CssKeyframesPlayer);
|
|
4364
|
-
const previousStyles = {};
|
|
4365
|
-
if (allowPreviousPlayerStylesMerge(duration, delay)) {
|
|
4366
|
-
previousCssKeyframePlayers.forEach(player => {
|
|
4367
|
-
let styles = player.currentSnapshot;
|
|
4368
|
-
Object.keys(styles).forEach(prop => previousStyles[prop] = styles[prop]);
|
|
4369
|
-
});
|
|
4370
|
-
}
|
|
4371
|
-
keyframes = balancePreviousStylesIntoKeyframes(element, keyframes, previousStyles);
|
|
4372
|
-
const finalStyles = flattenKeyframesIntoStyles(keyframes);
|
|
4373
|
-
// if there is no animation then there is no point in applying
|
|
4374
|
-
// styles and waiting for an event to get fired. This causes lag.
|
|
4375
|
-
// It's better to just directly apply the styles to the element
|
|
4376
|
-
// via the direct styling animation player.
|
|
4377
|
-
if (duration == 0) {
|
|
4378
|
-
return new DirectStylePlayer(element, finalStyles);
|
|
4379
|
-
}
|
|
4380
|
-
const animationName = `${KEYFRAMES_NAME_PREFIX}${this._count++}`;
|
|
4381
|
-
const kfElm = this.buildKeyframeElement(element, animationName, keyframes);
|
|
4382
|
-
const nodeToAppendKfElm = findNodeToAppendKeyframeElement(element);
|
|
4383
|
-
nodeToAppendKfElm.appendChild(kfElm);
|
|
4384
|
-
const specialStyles = packageNonAnimatableStyles(element, keyframes);
|
|
4385
|
-
const player = new CssKeyframesPlayer(element, keyframes, animationName, duration, delay, easing, finalStyles, specialStyles);
|
|
4386
|
-
player.onDestroy(() => removeElement(kfElm));
|
|
4387
|
-
return player;
|
|
4388
|
-
}
|
|
4389
|
-
}
|
|
4390
|
-
function findNodeToAppendKeyframeElement(element) {
|
|
4391
|
-
var _a;
|
|
4392
|
-
const rootNode = (_a = element.getRootNode) === null || _a === void 0 ? void 0 : _a.call(element);
|
|
4393
|
-
if (typeof ShadowRoot !== 'undefined' && rootNode instanceof ShadowRoot) {
|
|
4394
|
-
return rootNode;
|
|
4395
|
-
}
|
|
4396
|
-
return document.head;
|
|
4397
|
-
}
|
|
4398
|
-
function flattenKeyframesIntoStyles(keyframes) {
|
|
4399
|
-
let flatKeyframes = {};
|
|
4400
|
-
if (keyframes) {
|
|
4401
|
-
const kfs = Array.isArray(keyframes) ? keyframes : [keyframes];
|
|
4402
|
-
kfs.forEach(kf => {
|
|
4403
|
-
Object.keys(kf).forEach(prop => {
|
|
4404
|
-
if (prop == 'offset' || prop == 'easing')
|
|
4405
|
-
return;
|
|
4406
|
-
flatKeyframes[prop] = kf[prop];
|
|
4407
|
-
});
|
|
4408
|
-
});
|
|
4409
|
-
}
|
|
4410
|
-
return flatKeyframes;
|
|
4411
|
-
}
|
|
4412
|
-
function removeElement(node) {
|
|
4413
|
-
node.parentNode.removeChild(node);
|
|
4414
|
-
}
|
|
4415
|
-
let warningIssued = false;
|
|
4416
|
-
function notifyFaultyScrubber() {
|
|
4417
|
-
if (warningIssued)
|
|
4418
|
-
return;
|
|
4419
|
-
console.warn('@angular/animations: please load the web-animations.js polyfill to allow programmatic access...\n', ' visit https://bit.ly/IWukam to learn more about using the web-animation-js polyfill.');
|
|
4420
|
-
warningIssued = true;
|
|
4421
|
-
}
|
|
4422
|
-
|
|
4423
3972
|
class WebAnimationsPlayer {
|
|
4424
3973
|
constructor(element, keyframes, options, _specialStyles) {
|
|
4425
3974
|
this.element = element;
|
|
@@ -4435,7 +3984,7 @@ class WebAnimationsPlayer {
|
|
|
4435
3984
|
this._destroyed = false;
|
|
4436
3985
|
this.time = 0;
|
|
4437
3986
|
this.parentPlayer = null;
|
|
4438
|
-
this.currentSnapshot =
|
|
3987
|
+
this.currentSnapshot = new Map();
|
|
4439
3988
|
this._duration = options['duration'];
|
|
4440
3989
|
this._delay = options['delay'] || 0;
|
|
4441
3990
|
this.time = this._duration + this._delay;
|
|
@@ -4458,7 +4007,7 @@ class WebAnimationsPlayer {
|
|
|
4458
4007
|
const keyframes = this.keyframes;
|
|
4459
4008
|
this.domPlayer =
|
|
4460
4009
|
this._triggerWebAnimation(this.element, keyframes, this.options);
|
|
4461
|
-
this._finalKeyframe = keyframes.length ? keyframes[keyframes.length - 1] :
|
|
4010
|
+
this._finalKeyframe = keyframes.length ? keyframes[keyframes.length - 1] : new Map();
|
|
4462
4011
|
this.domPlayer.addEventListener('finish', () => this._onFinish());
|
|
4463
4012
|
}
|
|
4464
4013
|
_preparePlayerBeforeStart() {
|
|
@@ -4470,11 +4019,18 @@ class WebAnimationsPlayer {
|
|
|
4470
4019
|
this.domPlayer.pause();
|
|
4471
4020
|
}
|
|
4472
4021
|
}
|
|
4022
|
+
_convertKeyframesToObject(keyframes) {
|
|
4023
|
+
const kfs = [];
|
|
4024
|
+
keyframes.forEach(frame => {
|
|
4025
|
+
kfs.push(Object.fromEntries(frame));
|
|
4026
|
+
});
|
|
4027
|
+
return kfs;
|
|
4028
|
+
}
|
|
4473
4029
|
/** @internal */
|
|
4474
4030
|
_triggerWebAnimation(element, keyframes, options) {
|
|
4475
4031
|
// jscompiler doesn't seem to know animate is a native property because it's not fully
|
|
4476
4032
|
// supported yet across common browsers (we polyfill it for Edge/Safari) [CL #143630929]
|
|
4477
|
-
return element['animate'](keyframes, options);
|
|
4033
|
+
return element['animate'](this._convertKeyframesToObject(keyframes), options);
|
|
4478
4034
|
}
|
|
4479
4035
|
onStart(fn) {
|
|
4480
4036
|
this._onStartFns.push(fn);
|
|
@@ -4552,15 +4108,15 @@ class WebAnimationsPlayer {
|
|
|
4552
4108
|
return this._delay + this._duration;
|
|
4553
4109
|
}
|
|
4554
4110
|
beforeDestroy() {
|
|
4555
|
-
const styles =
|
|
4111
|
+
const styles = new Map();
|
|
4556
4112
|
if (this.hasStarted()) {
|
|
4557
4113
|
// note: this code is invoked only when the `play` function was called prior to this
|
|
4558
4114
|
// (thus `hasStarted` returns true), this implies that the code that initializes
|
|
4559
4115
|
// `_finalKeyframe` has also been executed and the non-null assertion can be safely used here
|
|
4560
4116
|
const finalKeyframe = this._finalKeyframe;
|
|
4561
|
-
|
|
4562
|
-
if (prop
|
|
4563
|
-
styles
|
|
4117
|
+
finalKeyframe.forEach((val, prop) => {
|
|
4118
|
+
if (prop !== 'offset') {
|
|
4119
|
+
styles.set(prop, this._finished ? val : computeStyle(this.element, prop));
|
|
4564
4120
|
}
|
|
4565
4121
|
});
|
|
4566
4122
|
}
|
|
@@ -4568,17 +4124,13 @@ class WebAnimationsPlayer {
|
|
|
4568
4124
|
}
|
|
4569
4125
|
/** @internal */
|
|
4570
4126
|
triggerCallback(phaseName) {
|
|
4571
|
-
const methods = phaseName
|
|
4127
|
+
const methods = phaseName === 'start' ? this._onStartFns : this._onDoneFns;
|
|
4572
4128
|
methods.forEach(fn => fn());
|
|
4573
4129
|
methods.length = 0;
|
|
4574
4130
|
}
|
|
4575
4131
|
}
|
|
4576
4132
|
|
|
4577
4133
|
class WebAnimationsDriver {
|
|
4578
|
-
constructor() {
|
|
4579
|
-
this._isNativeImpl = /\{\s*\[native\s+code\]\s*\}/.test(getElementAnimateFn().toString());
|
|
4580
|
-
this._cssKeyframesDriver = new CssKeyframesDriver();
|
|
4581
|
-
}
|
|
4582
4134
|
validateStyleProperty(prop) {
|
|
4583
4135
|
return validateStyleProperty(prop);
|
|
4584
4136
|
}
|
|
@@ -4595,14 +4147,7 @@ class WebAnimationsDriver {
|
|
|
4595
4147
|
computeStyle(element, prop, defaultValue) {
|
|
4596
4148
|
return window.getComputedStyle(element)[prop];
|
|
4597
4149
|
}
|
|
4598
|
-
|
|
4599
|
-
this._isNativeImpl = supported;
|
|
4600
|
-
}
|
|
4601
|
-
animate(element, keyframes, duration, delay, easing, previousPlayers = [], scrubberAccessRequested) {
|
|
4602
|
-
const useKeyframes = !scrubberAccessRequested && !this._isNativeImpl;
|
|
4603
|
-
if (useKeyframes) {
|
|
4604
|
-
return this._cssKeyframesDriver.animate(element, keyframes, duration, delay, easing, previousPlayers);
|
|
4605
|
-
}
|
|
4150
|
+
animate(element, keyframes, duration, delay, easing, previousPlayers = []) {
|
|
4606
4151
|
const fill = delay == 0 ? 'both' : 'forwards';
|
|
4607
4152
|
const playerOptions = { duration, delay, fill };
|
|
4608
4153
|
// we check for this to avoid having a null|undefined value be present
|
|
@@ -4610,26 +4155,19 @@ class WebAnimationsDriver {
|
|
|
4610
4155
|
if (easing) {
|
|
4611
4156
|
playerOptions['easing'] = easing;
|
|
4612
4157
|
}
|
|
4613
|
-
const previousStyles =
|
|
4158
|
+
const previousStyles = new Map();
|
|
4614
4159
|
const previousWebAnimationPlayers = previousPlayers.filter(player => player instanceof WebAnimationsPlayer);
|
|
4615
4160
|
if (allowPreviousPlayerStylesMerge(duration, delay)) {
|
|
4616
4161
|
previousWebAnimationPlayers.forEach(player => {
|
|
4617
|
-
|
|
4618
|
-
Object.keys(styles).forEach(prop => previousStyles[prop] = styles[prop]);
|
|
4162
|
+
player.currentSnapshot.forEach((val, prop) => previousStyles.set(prop, val));
|
|
4619
4163
|
});
|
|
4620
4164
|
}
|
|
4621
|
-
|
|
4622
|
-
|
|
4623
|
-
const specialStyles = packageNonAnimatableStyles(element,
|
|
4624
|
-
return new WebAnimationsPlayer(element,
|
|
4165
|
+
let _keyframes = normalizeKeyframes(keyframes).map(styles => copyStyles(styles));
|
|
4166
|
+
_keyframes = balancePreviousStylesIntoKeyframes(element, _keyframes, previousStyles);
|
|
4167
|
+
const specialStyles = packageNonAnimatableStyles(element, _keyframes);
|
|
4168
|
+
return new WebAnimationsPlayer(element, _keyframes, playerOptions, specialStyles);
|
|
4625
4169
|
}
|
|
4626
4170
|
}
|
|
4627
|
-
function supportsWebAnimations() {
|
|
4628
|
-
return typeof getElementAnimateFn() === 'function';
|
|
4629
|
-
}
|
|
4630
|
-
function getElementAnimateFn() {
|
|
4631
|
-
return (isBrowser() && Element.prototype['animate']) || {};
|
|
4632
|
-
}
|
|
4633
4171
|
|
|
4634
4172
|
/**
|
|
4635
4173
|
* @license
|
|
@@ -4667,5 +4205,5 @@ function getElementAnimateFn() {
|
|
|
4667
4205
|
* Generated bundle index. Do not edit.
|
|
4668
4206
|
*/
|
|
4669
4207
|
|
|
4670
|
-
export { AnimationDriver, Animation as ɵAnimation, AnimationEngine as ɵAnimationEngine, AnimationStyleNormalizer as ɵAnimationStyleNormalizer,
|
|
4208
|
+
export { AnimationDriver, Animation as ɵAnimation, AnimationEngine as ɵAnimationEngine, AnimationStyleNormalizer as ɵAnimationStyleNormalizer, NoopAnimationDriver as ɵNoopAnimationDriver, NoopAnimationStyleNormalizer as ɵNoopAnimationStyleNormalizer, WebAnimationsDriver as ɵWebAnimationsDriver, WebAnimationsPlayer as ɵWebAnimationsPlayer, WebAnimationsStyleNormalizer as ɵWebAnimationsStyleNormalizer, allowPreviousPlayerStylesMerge as ɵallowPreviousPlayerStylesMerge, containsElement as ɵcontainsElement, invokeQuery as ɵinvokeQuery, normalizeKeyframes as ɵnormalizeKeyframes, validateStyleProperty as ɵvalidateStyleProperty };
|
|
4671
4209
|
//# sourceMappingURL=browser.mjs.map
|