This repository has been archived by the owner on Apr 20, 2023. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 235
/
TransitionStyleInfo.js
119 lines (104 loc) · 4.85 KB
/
TransitionStyleInfo.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
/**
* Handles parsing, caching, and detecting changes to the 'transition' CSS property
* @constructor
* @param {Element} el the target element
*/
PIE.TransitionStyleInfo = PIE.StyleInfoBase.newStyleInfo( {
cssProperty: 'transition',
styleProperty: 'transition',
parseCss: function( css ) {
var props,
Type = PIE.Tokenizer.Type,
tokenizer, token, tokenType, tokenValue, currentTransition,
a, b, c, d;
function tokenIsChar( token, ch ) {
return token && token.tokenValue === ch;
}
function tokenToNumber( token ) {
return ( token && ( token.tokenType & Type.NUMBER ) ) ? parseFloat( token.tokenValue, 10 ) : NaN;
}
function flushCurrentTransition() {
// Fill in defaults
if (!currentTransition.property) {
currentTransition.property = 'all';
}
if (!currentTransition.timingFunction) {
currentTransition.timingFunction = 'ease';
}
if (!currentTransition.delay) {
currentTransition.delay = '0';
}
props.push(currentTransition);
currentTransition = 0;
}
if( css ) {
tokenizer = new PIE.Tokenizer( css );
props = [];
while( token = tokenizer.next() ) {
tokenType = token.tokenType;
tokenValue = token.tokenValue;
if (!currentTransition) {
currentTransition = {
// property: 'all',
// duration: '0ms',
// timingFunction: <PIE.TransitionTimingFunction.*>,
// delay: '0ms'
};
}
// Time values: first one is duration and second one is delay
if (tokenType & Type.TIME && !currentTransition.duration) {
currentTransition.duration = tokenValue;
}
else if (tokenType & Type.TIME && !currentTransition.delay) {
currentTransition.delay = tokenValue;
}
// Timing function
else if (tokenType & Type.IDENT && !currentTransition.timingFunction && tokenValue in PIE.TransitionTimingFunction.namedEasings) {
currentTransition.timingFunction = PIE.TransitionTimingFunction.namedEasings[tokenValue];
}
else if (tokenType & Type.FUNCTION && !currentTransition.timingFunction) {
if ( tokenValue === 'step' &&
!isNaN( a = tokenToNumber( tokenizer.next() ) ) && a > 0 && Math.floor( a ) === a &&
tokenIsChar( tokenizer.next(), ',' ) &&
( b = tokenizer.next() ) && ( b.tokenType & Type.IDENT ) && ( b.tokenValue === 'start' || b.tokenValue === 'end' ) &&
tokenIsChar( tokenizer.next(), ')' )
) {
currentTransition.timingFunction = PIE.TransitionTimingFunction.getStepsTimingFunction( a, b );
}
else if (tokenValue === 'cubic-bezier' &&
!isNaN( a = tokenToNumber( tokenizer.next() ) ) && a >= 0 && a <= 1 &&
tokenIsChar( tokenizer.next(), ',' ) &&
!isNaN( b = tokenToNumber( tokenizer.next() ) ) &&
tokenIsChar( tokenizer.next(), ',' ) &&
!isNaN( c = tokenToNumber( tokenizer.next() ) ) && c >= 0 && c <= 1 &&
tokenIsChar( tokenizer.next(), ',' ) &&
!isNaN( d = tokenToNumber( tokenizer.next() ) ) &&
tokenIsChar( tokenizer.next(), ')' )
) {
currentTransition.timingFunction = PIE.TransitionTimingFunction.getCubicBezierTimingFunction( a, b, c, d );
}
else {
return null;
}
}
// Property name
else if (tokenType & Type.IDENT && !currentTransition.property) {
currentTransition.property = tokenValue;
}
// Comma: start a new value. Only duration is required so fail if it wasn't found.
else if (tokenType & Type.OPERATOR && tokenValue === ',' && currentTransition.duration) {
flushCurrentTransition();
}
// Something unrecognized - fail!
else {
return null;
}
}
// leftovers
if( currentTransition && currentTransition.duration ) {
flushCurrentTransition();
}
}
return props && props.length ? props : null;
}
} );