Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(376)

Side by Side Diff: chrome/browser/resources/settings/settings_page/main_page_behavior.js

Issue 2259163002: MD Settings: Fix scrolling bugs and hacks caused by undefined load behavior (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@TransitionsNoTestsFakeRebase
Patch Set: bug fixes Created 4 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 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 * Calls |readyTest| repeatedly until it returns true, then calls
7 * |readyCallback|.
8 * @param {function():boolean} readyTest
9 * @param {!Function} readyCallback
10 */
11 function doWhenReady(readyTest, readyCallback) {
12 // TODO(dschuyler): Determine whether this hack can be removed.
13 // See also: https://github.com/Polymer/polymer/issues/3629
14 var intervalId = setInterval(function() {
15 if (readyTest()) {
16 clearInterval(intervalId);
17 readyCallback();
18 }
19 }, 10);
20 }
21
22 /**
23 * Responds to route changes by expanding, collapsing, or scrolling to sections 6 * Responds to route changes by expanding, collapsing, or scrolling to sections
24 * on the page. Expanded sections take up the full height of the container. At 7 * on the page. Expanded sections take up the full height of the container. At
25 * most one section should be expanded at any given time. 8 * most one section should be expanded at any given time.
26 * @polymerBehavior MainPageBehavior 9 * @polymerBehavior MainPageBehavior
27 */ 10 */
28 var MainPageBehaviorImpl = { 11 var MainPageBehaviorImpl = {
29 /** @type {?HTMLElement} The scrolling container. */ 12 /** @type {?HTMLElement} The scrolling container. */
30 scroller: null, 13 scroller: null,
31 14
32 /** @override */ 15 /** @override */
33 attached: function() { 16 attached: function() {
34 if (this.domHost && this.domHost.parentNode.tagName == 'PAPER-HEADER-PANEL') 17 if (this.domHost && this.domHost.parentNode.tagName == 'PAPER-HEADER-PANEL')
35 this.scroller = this.domHost.parentNode.scroller; 18 this.scroller = this.domHost.parentNode.scroller;
36 else 19 else
37 this.scroller = document.body; // Used in unit tests. 20 this.scroller = document.body; // Used in unit tests.
38 }, 21 },
39 22
40 /** 23 /**
41 * @param {!settings.Route} newRoute 24 * @param {!settings.Route} newRoute
42 * @param {settings.Route} oldRoute 25 * @param {settings.Route} oldRoute
43 */ 26 */
44 currentRouteChanged: function(newRoute, oldRoute) { 27 currentRouteChanged: function(newRoute, oldRoute) {
45 if (oldRoute || !newRoute.section) { 28 // Allow the page to load before expanding the section.
29 if (!oldRoute)
30 setTimeout(this.tryTransitionToSection_.bind(this));
31 else
46 this.tryTransitionToSection_(); 32 this.tryTransitionToSection_();
47 return;
48 }
49
50 // Wait for the page to really be ready before expanding or scrolling to the
51 // section. TODO(michaelpg): Remove this workaround with a global workaround
52 // for crbug.com/638074.
53 doWhenReady(function() {
54 if (newRoute != settings.getCurrentRoute())
55 return;
56 var section = this.getSection(newRoute.section);
57 return section && (!newRoute.isSubpage() || section.canAnimateExpand());
58 }.bind(this), this.tryTransitionToSection_.bind(this));
59 }, 33 },
60 34
61 /** 35 /**
62 * If possible, transitions to the current route's section (by expanding or 36 * If possible, transitions to the current route's section (by expanding or
63 * scrolling to it). If another transition is running, finishes or cancels 37 * scrolling to it). If another transition is running, finishes or cancels
64 * that one, then schedules this function again. This ensures the current 38 * that one, then schedules this function again. This ensures the current
65 * section is quickly shown, without getting the page into a broken state -- 39 * section is quickly shown, without getting the page into a broken state --
66 * if currentRoute changes in between calls, just transition to the new route. 40 * if currentRoute changes in between calls, just transition to the new route.
67 * @private 41 * @private
68 */ 42 */
(...skipping 15 matching lines...) Expand all
84 if (expandedSection) { 58 if (expandedSection) {
85 // If the section shouldn't be expanded, collapse it. 59 // If the section shouldn't be expanded, collapse it.
86 if (!currentRoute.isSubpage() || expandedSection != currentSection) { 60 if (!currentRoute.isSubpage() || expandedSection != currentSection) {
87 promise = this.collapseSection_(expandedSection); 61 promise = this.collapseSection_(expandedSection);
88 // Scroll to the collapsed section. 62 // Scroll to the collapsed section.
89 if (currentSection) 63 if (currentSection)
90 this.scrollToSection_(); 64 this.scrollToSection_();
91 } 65 }
92 } else if (currentSection) { 66 } else if (currentSection) {
93 // Expand the section into a subpage or scroll to it on the main page. 67 // Expand the section into a subpage or scroll to it on the main page.
68 if (!currentSection.clientHeight) {
69 setTimeout(this.tryTransitionToSection_.bind(this));
70 return;
71 }
94 if (currentRoute.isSubpage()) 72 if (currentRoute.isSubpage())
95 promise = this.expandSection_(currentSection); 73 promise = this.expandSection_(currentSection);
96 else 74 else
97 this.scrollToSection_(); 75 this.scrollToSection_();
98 } 76 }
99 77
100 // When this animation ends, another may be necessary. Call this function 78 // When this animation ends, another may be necessary. Call this function
101 // again after the promise resolves. 79 // again after the promise resolves.
102 if (promise) 80 if (promise)
103 promise.then(this.tryTransitionToSection_.bind(this)); 81 promise.then(this.tryTransitionToSection_.bind(this));
(...skipping 101 matching lines...) Expand 10 before | Expand all | Expand 10 after
205 if (!canAnimateCollapse) { 183 if (!canAnimateCollapse) {
206 // Finish by restoring the section into the page. 184 // Finish by restoring the section into the page.
207 section.setFrozen(false); 185 section.setFrozen(false);
208 return Promise.resolve(); 186 return Promise.resolve();
209 } 187 }
210 188
211 // Play the actual collapse animation. 189 // Play the actual collapse animation.
212 return new Promise(function(resolve, reject) { 190 return new Promise(function(resolve, reject) {
213 // Wait for the other sections to show up so we can scroll properly. 191 // Wait for the other sections to show up so we can scroll properly.
214 setTimeout(function() { 192 setTimeout(function() {
215 var newSection = settings.getCurrentRoute().section && 193 var currentRoute = settings.getCurrentRoute();
216 this.getSection(settings.getCurrentRoute().section); 194 var newSection =
195 currentRoute.section && this.getSection(currentRoute.section);
217 196
218 // Scroll to the section if indicated by the route. TODO(michaelpg): Is 197 // Scroll to the new section if it's on this page. If the route has no
219 // this the right behavior, or should we return to the previous scroll 198 // section (e.g., a root page), return to the original position.
220 // position?
221 if (newSection) 199 if (newSection)
222 newSection.scrollIntoView(); 200 newSection.scrollIntoView();
223 else 201 else if (!currentRoute.section)
224 this.scroller.scrollTop = this.origScrollTop_; 202 this.scroller.scrollTop = this.origScrollTop_;
225 203
226 this.currentAnimation_ = section.animateCollapse( 204 this.currentAnimation_ = section.animateCollapse(
227 /** @type {!HTMLElement} */(this.scroller)); 205 /** @type {!HTMLElement} */(this.scroller));
228 206
229 this.currentAnimation_.finished.catch(function() { 207 this.currentAnimation_.finished.catch(function() {
230 // The collapse was canceled, so the page is showing a subpage still. 208 // The collapse was canceled, so the page is showing a subpage still.
231 this.fire('subpage-expand'); 209 this.fire('subpage-expand');
232 }.bind(this)).then(function() { 210 }.bind(this)).then(function() {
233 // Clean up after the animation succeeds or cancels. 211 // Clean up after the animation succeeds or cancels.
234 section.setFrozen(false); 212 section.setFrozen(false);
235 section.classList.remove('collapsing'); 213 section.classList.remove('collapsing');
236 this.toggleScrolling_(true); 214 this.toggleScrolling_(true);
237 this.currentAnimation_ = null; 215 this.currentAnimation_ = null;
238 resolve(); 216 resolve();
239 }.bind(this)); 217 }.bind(this));
240 }.bind(this)); 218 }.bind(this));
241 }.bind(this)); 219 }.bind(this));
242 }, 220 },
243 221
244 /** @private */ 222 /** @private */
245 scrollToSection_: function() { 223 scrollToSection_: function() {
246 doWhenReady( 224 assert(this.scrollHeight > 0);
247 function() { 225 var section = this.getSection(settings.getCurrentRoute().section);
248 return this.scrollHeight > 0; 226 assert(section);
249 }.bind(this), 227 section.scrollIntoView();
250 function() {
251 // If the current section changes while we are waiting for the page to
252 // be ready, scroll to the newest requested section.
253 var section = this.getSection(settings.getCurrentRoute().section);
254 if (section)
255 section.scrollIntoView();
256 }.bind(this));
257 }, 228 },
258 229
259 /** 230 /**
260 /** 231 /**
261 * Hides or unhides the sections not being expanded. 232 * Hides or unhides the sections not being expanded.
262 * @param {string} sectionName The section to keep visible. 233 * @param {string} sectionName The section to keep visible.
263 * @param {boolean} hidden Whether the sections should be hidden. 234 * @param {boolean} hidden Whether the sections should be hidden.
264 * @private 235 * @private
265 */ 236 */
266 toggleOtherSectionsHidden_: function(sectionName, hidden) { 237 toggleOtherSectionsHidden_: function(sectionName, hidden) {
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
300 this.scroller.style.width = 'calc(100% - ' + scrollbarWidth + 'px)'; 271 this.scroller.style.width = 'calc(100% - ' + scrollbarWidth + 'px)';
301 } 272 }
302 } 273 }
303 }; 274 };
304 275
305 /** @polymerBehavior */ 276 /** @polymerBehavior */
306 var MainPageBehavior = [ 277 var MainPageBehavior = [
307 settings.RouteObserverBehavior, 278 settings.RouteObserverBehavior,
308 MainPageBehaviorImpl, 279 MainPageBehaviorImpl,
309 ]; 280 ];
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698