OLD | NEW |
1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 /* | 5 /* |
6 Exported function: | 6 Exported function: |
7 assertResponsive | 7 assertResponsive |
8 | 8 |
9 Call signature: | 9 Call signature: |
10 assertResponsive({ | 10 assertResponsive({ |
(...skipping 17 matching lines...) Expand all Loading... |
28 configuration. | 28 configuration. |
29 It starts the interpolation in every configuration, changes the | 29 It starts the interpolation in every configuration, changes the |
30 state to every other configuration (n * (n - 1) complexity) and asserts that | 30 state to every other configuration (n * (n - 1) complexity) and asserts that |
31 each destination configuration's expectations are met. | 31 each destination configuration's expectations are met. |
32 Each animation target can be assigned custom styles via the ".target" selector. | 32 Each animation target can be assigned custom styles via the ".target" selector. |
33 This test is designed to catch stale interpolation caches. | 33 This test is designed to catch stale interpolation caches. |
34 */ | 34 */ |
35 | 35 |
36 (function() { | 36 (function() { |
37 'use strict'; | 37 'use strict'; |
38 var sharedStyle = null; | |
39 var animationCount = 0; | |
40 var pendingResponsiveTests = []; | 38 var pendingResponsiveTests = []; |
41 | 39 |
42 function assertResponsive(options) { | 40 function assertResponsive(options) { |
43 pendingResponsiveTests.push(options); | 41 pendingResponsiveTests.push(options); |
44 } | 42 } |
45 | 43 |
46 function createStateTransitions(configurations) { | 44 function createStateTransitions(configurations) { |
47 var stateTransitions = []; | 45 var stateTransitions = []; |
48 for (var i = 0; i < configurations.length; i++) { | 46 for (var i = 0; i < configurations.length; i++) { |
49 var beforeConfiguration = configurations[i]; | 47 var beforeConfiguration = configurations[i]; |
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
85 console.assert(targets.every(function(target) { return target.parentElement
=== parent; })); | 83 console.assert(targets.every(function(target) { return target.parentElement
=== parent; })); |
86 parent.style[property] = state.inherited; | 84 parent.style[property] = state.inherited; |
87 } | 85 } |
88 if (state.underlying) { | 86 if (state.underlying) { |
89 for (var target of targets) { | 87 for (var target of targets) { |
90 target.style[property] = state.underlying; | 88 target.style[property] = state.underlying; |
91 } | 89 } |
92 } | 90 } |
93 } | 91 } |
94 | 92 |
95 function createAnimationName() { | 93 function createKeyframes(property, from, to) { |
96 return 'anim' + (animationCount++); | 94 return [ |
| 95 {[property]: from}, |
| 96 {[property]: to}, |
| 97 ]; |
97 } | 98 } |
98 | 99 |
99 function createKeyframes(animationName, property, from, to) { | 100 function startPausedAnimations(targets, keyframes, fractions) { |
100 return ` | |
101 @keyframes ${animationName} { | |
102 from { ${property}: ${from}; } | |
103 to { ${property}: ${to}; } | |
104 }`; | |
105 } | |
106 | |
107 function addGlobalStyle(styleText) { | |
108 if (!sharedStyle) { | |
109 sharedStyle = createElement('style', document.documentElement); | |
110 } | |
111 sharedStyle.textContent += styleText; | |
112 } | |
113 | |
114 function startPausedAnimations(targets, animationName, fractions) { | |
115 console.assert(targets.length == fractions.length); | 101 console.assert(targets.length == fractions.length); |
116 for (var i = 0; i < targets.length; i++) { | 102 for (var i = 0; i < targets.length; i++) { |
117 var target = targets[i]; | 103 var target = targets[i]; |
118 var fraction = fractions[i]; | 104 var fraction = fractions[i]; |
119 console.assert(fraction >= 0 && fraction <= 1); | 105 console.assert(fraction >= 0 && fraction < 1); |
120 target.style.animation = `${animationName} 1s linear both paused`; | 106 var animation = target.animate(keyframes, 1); |
121 target.style.animationDelay = `${-fraction}s`; | 107 animation.currentTime = fraction; |
| 108 animation.pause(); |
122 } | 109 } |
123 } | 110 } |
124 | 111 |
125 function runPendingResponsiveTests() { | 112 function runPendingResponsiveTests() { |
126 var stateTransitionTests = []; | 113 var stateTransitionTests = []; |
127 pendingResponsiveTests.forEach(function(options) { | 114 pendingResponsiveTests.forEach(function(options) { |
128 var property = options.property; | 115 var property = options.property; |
129 var from = options.from; | 116 var from = options.from; |
130 var to = options.to; | 117 var to = options.to; |
131 var animationName = createAnimationName(); | 118 var keyframes = createKeyframes(property, from, to); |
132 addGlobalStyle(createKeyframes(animationName, property, from, to)); | |
133 | 119 |
134 var stateTransitions = createStateTransitions(options.configurations); | 120 var stateTransitions = createStateTransitions(options.configurations); |
135 stateTransitions.forEach(function(stateTransition) { | 121 stateTransitions.forEach(function(stateTransition) { |
136 var before = stateTransition.before; | 122 var before = stateTransition.before; |
137 var after = stateTransition.after; | 123 var after = stateTransition.after; |
138 var container = createElement('div', document.body); | 124 var container = createElement('div', document.body); |
139 var targets = createTargets(after.expect.length, container); | 125 var targets = createTargets(after.expect.length, container); |
140 | 126 |
141 setState(targets, property, before.state); | 127 setState(targets, property, before.state); |
142 startPausedAnimations(targets, animationName, after.expect.map(function(ex
pectation) { return expectation.at; })); | 128 startPausedAnimations(targets, keyframes, after.expect.map(function(expect
ation) { return expectation.at; })); |
143 stateTransitionTests.push({ | 129 stateTransitionTests.push({ |
144 applyStateTransition() { | 130 applyStateTransition() { |
145 setState(targets, property, after.state); | 131 setState(targets, property, after.state); |
146 }, | 132 }, |
147 assert() { | 133 assert() { |
148 for (var i = 0; i < targets.length; i++) { | 134 for (var i = 0; i < targets.length; i++) { |
149 var target = targets[i]; | 135 var target = targets[i]; |
150 var expectation = after.expect[i]; | 136 var expectation = after.expect[i]; |
151 var actual = getComputedStyle(target)[property]; | 137 var actual = getComputedStyle(target)[property]; |
152 test(function() { | 138 test(function() { |
153 assert_equals(actual, expectation.is); | 139 assert_equals(actual, expectation.is); |
154 }, `Animation on property <${property}> from [${from}] to [${to}] wi
th ${JSON.stringify(before.state)} changed to ${JSON.stringify(after.state)} at
(${expectation.at}) is [${expectation.is}]`); | 140 }, `Animation on property <${property}> from [${from}] to [${to}] wi
th ${JSON.stringify(before.state)} changed to ${JSON.stringify(after.state)} at
(${expectation.at}) is [${expectation.is}]`); |
155 } | 141 } |
156 }, | 142 }, |
157 }); | 143 }); |
158 }); | 144 }); |
159 }); | 145 }); |
160 | 146 |
161 // Force style recalc to instantiate animations internally. | |
162 getComputedStyle(document.body).color; | |
163 | |
164 // Separate style modification from measurement as different phases to avoid a
style recalc storm. | 147 // Separate style modification from measurement as different phases to avoid a
style recalc storm. |
165 for (var stateTransitionTest of stateTransitionTests) { | 148 for (var stateTransitionTest of stateTransitionTests) { |
166 stateTransitionTest.applyStateTransition(); | 149 stateTransitionTest.applyStateTransition(); |
167 } | 150 } |
168 for (var stateTransitionTest of stateTransitionTests) { | 151 for (var stateTransitionTest of stateTransitionTests) { |
169 stateTransitionTest.assert(); | 152 stateTransitionTest.assert(); |
170 } | 153 } |
171 } | 154 } |
172 | 155 |
173 function loadScript(url) { | 156 function loadScript(url) { |
(...skipping 12 matching lines...) Expand all Loading... |
186 requestAnimationFrame(function() { | 169 requestAnimationFrame(function() { |
187 runPendingResponsiveTests(); | 170 runPendingResponsiveTests(); |
188 asyncHandle.done() | 171 asyncHandle.done() |
189 }); | 172 }); |
190 }); | 173 }); |
191 | 174 |
192 | 175 |
193 window.assertResponsive = assertResponsive; | 176 window.assertResponsive = assertResponsive; |
194 | 177 |
195 })(); | 178 })(); |
OLD | NEW |