Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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 cr.define('options', function() { | 5 cr.define('options', function() { |
| 6 /** @const */ var FocusOutlineManager = cr.ui.FocusOutlineManager; | 6 /** @const */ var FocusOutlineManager = cr.ui.FocusOutlineManager; |
| 7 | 7 |
| 8 ///////////////////////////////////////////////////////////////////////////// | 8 ///////////////////////////////////////////////////////////////////////////// |
| 9 // OptionsPage class: | 9 // OptionsPage class: |
| 10 | 10 |
| (...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 64 | 64 |
| 65 /** | 65 /** |
| 66 * Gets the default page (to be shown on initial load). | 66 * Gets the default page (to be shown on initial load). |
| 67 */ | 67 */ |
| 68 OptionsPage.getDefaultPage = function() { | 68 OptionsPage.getDefaultPage = function() { |
| 69 return BrowserOptions.getInstance(); | 69 return BrowserOptions.getInstance(); |
| 70 }; | 70 }; |
| 71 | 71 |
| 72 /** | 72 /** |
| 73 * Shows the default page. | 73 * Shows the default page. |
| 74 * @param {Object=} opt_propertyBag An optional bag of properties including | |
| 75 * replaceState (if history state should be replaced instead of pushed). | |
| 74 */ | 76 */ |
| 75 OptionsPage.showDefaultPage = function() { | 77 OptionsPage.showDefaultPage = function(opt_propertyBag) { |
| 76 this.navigateToPage(this.getDefaultPage().name); | 78 opt_propertyBag = opt_propertyBag || {}; |
| 79 this.navigateToPage(this.getDefaultPage().name, | |
| 80 {replaceState: opt_propertyBag.replaceState}); | |
| 77 }; | 81 }; |
| 78 | 82 |
| 79 /** | 83 /** |
| 80 * "Navigates" to a page, meaning that the page will be shown and the | 84 * "Navigates" to a page, meaning that the page will be shown and the |
| 81 * appropriate entry is placed in the history. | 85 * appropriate entry is placed in the history. |
| 82 * @param {string} pageName Page name. | 86 * @param {string} pageName Page name. |
| 87 * @param {Object=} opt_propertyBag An optional bag of properties including | |
| 88 * replaceState (if history state should be replaced instead of pushed). | |
| 83 */ | 89 */ |
| 84 OptionsPage.navigateToPage = function(pageName) { | 90 OptionsPage.navigateToPage = function(pageName, opt_propertyBag) { |
| 85 this.showPageByName(pageName, true); | 91 opt_propertyBag = opt_propertyBag || {}; |
| 92 this.showPageByName(pageName, true, | |
| 93 {replaceState: opt_propertyBag.replaceState}); | |
| 86 }; | 94 }; |
| 87 | 95 |
| 88 /** | 96 /** |
| 89 * Shows a registered page. This handles both top-level and overlay pages. | 97 * Shows a registered page. This handles both top-level and overlay pages. |
| 90 * @param {string} pageName Page name. | 98 * @param {string} pageName Page name. |
| 91 * @param {boolean} updateHistory True if we should update the history after | 99 * @param {boolean} updateHistory True if we should update the history after |
| 92 * showing the page. | 100 * showing the page. |
| 93 * @param {Object=} opt_propertyBag An optional bag of properties including | 101 * @param {Object=} opt_propertyBag An optional bag of properties including |
| 94 * replaceState (if history state should be replaced instead of pushed). | 102 * replaceState (if history state should be replaced instead of pushed). |
| 95 * @private | 103 * @private |
| (...skipping 17 matching lines...) Expand all Loading... | |
| 113 } | 121 } |
| 114 } | 122 } |
| 115 | 123 |
| 116 // Find the target page. | 124 // Find the target page. |
| 117 var targetPage = this.registeredPages[pageName.toLowerCase()]; | 125 var targetPage = this.registeredPages[pageName.toLowerCase()]; |
| 118 if (!targetPage || !targetPage.canShowPage()) { | 126 if (!targetPage || !targetPage.canShowPage()) { |
| 119 // If it's not a page, try it as an overlay. | 127 // If it's not a page, try it as an overlay. |
| 120 if (!targetPage && this.showOverlay_(pageName, rootPage)) { | 128 if (!targetPage && this.showOverlay_(pageName, rootPage)) { |
| 121 if (updateHistory) | 129 if (updateHistory) |
| 122 this.updateHistoryState_(!!opt_propertyBag.replaceState); | 130 this.updateHistoryState_(!!opt_propertyBag.replaceState); |
| 131 this.updateTitle_(); | |
| 123 return; | 132 return; |
| 124 } else { | 133 } else { |
| 125 targetPage = this.getDefaultPage(); | 134 targetPage = this.getDefaultPage(); |
| 126 } | 135 } |
| 127 } | 136 } |
| 128 | 137 |
| 129 pageName = targetPage.name.toLowerCase(); | 138 pageName = targetPage.name.toLowerCase(); |
| 130 var targetPageWasVisible = targetPage.visible; | 139 var targetPageWasVisible = targetPage.visible; |
| 131 | 140 |
| 132 // Determine if the root page is 'sticky', meaning that it | 141 // Determine if the root page is 'sticky', meaning that it |
| (...skipping 26 matching lines...) Expand all Loading... | |
| 159 this.registeredOverlayPages[name]; | 168 this.registeredOverlayPages[name]; |
| 160 if (!page.parentPage && isRootPageLocked) | 169 if (!page.parentPage && isRootPageLocked) |
| 161 continue; | 170 continue; |
| 162 page.visible = name == pageName || page.isAncestorOfPage(targetPage); | 171 page.visible = name == pageName || page.isAncestorOfPage(targetPage); |
| 163 } | 172 } |
| 164 | 173 |
| 165 // Update the history and current location. | 174 // Update the history and current location. |
| 166 if (updateHistory) | 175 if (updateHistory) |
| 167 this.updateHistoryState_(!!opt_propertyBag.replaceState); | 176 this.updateHistoryState_(!!opt_propertyBag.replaceState); |
| 168 | 177 |
| 169 // Update tab title. | |
| 170 this.setTitle_(targetPage.title); | |
| 171 | |
| 172 // Update focus if any other control was focused on the previous page, | 178 // Update focus if any other control was focused on the previous page, |
| 173 // or the previous page is not known. | 179 // or the previous page is not known. |
| 174 if (document.activeElement != document.body && | 180 if (document.activeElement != document.body && |
| 175 (!rootPage || rootPage.pageDiv.contains(document.activeElement))) { | 181 (!rootPage || rootPage.pageDiv.contains(document.activeElement))) { |
| 176 targetPage.focus(); | 182 targetPage.focus(); |
| 177 } | 183 } |
| 178 | 184 |
| 179 // Notify pages if they were shown. | 185 // Notify pages if they were shown. |
| 180 for (var i = 0; i < allPageNames.length; ++i) { | 186 for (var i = 0; i < allPageNames.length; ++i) { |
| 181 var name = allPageNames[i]; | 187 var name = allPageNames[i]; |
| 182 var page = this.registeredPages[name] || | 188 var page = this.registeredPages[name] || |
| 183 this.registeredOverlayPages[name]; | 189 this.registeredOverlayPages[name]; |
| 184 if (!page.parentPage && isRootPageLocked) | 190 if (!page.parentPage && isRootPageLocked) |
| 185 continue; | 191 continue; |
| 186 if (!targetPageWasVisible && page.didShowPage && | 192 if (!targetPageWasVisible && page.didShowPage && |
| 187 (name == pageName || page.isAncestorOfPage(targetPage))) { | 193 (name == pageName || page.isAncestorOfPage(targetPage))) { |
| 188 page.didShowPage(); | 194 page.didShowPage(); |
| 189 } | 195 } |
| 190 } | 196 } |
| 197 | |
| 198 // Update the document title. Do this after didShowPage was called, in case | |
| 199 // a page decides to change its title. | |
| 200 this.updateTitle_(); | |
| 191 }; | 201 }; |
| 192 | 202 |
| 193 /** | 203 /** |
| 194 * Sets the title of the page. This is accomplished by calling into the | |
| 195 * parent page API. | |
| 196 * @param {string} title The title string. | |
| 197 * @private | |
| 198 */ | |
| 199 OptionsPage.setTitle_ = function(title) { | |
| 200 uber.invokeMethodOnParent('setTitle', {title: title}); | |
| 201 }; | |
| 202 | |
| 203 /** | |
| 204 * Scrolls the page to the correct position (the top when opening an overlay, | 204 * Scrolls the page to the correct position (the top when opening an overlay, |
| 205 * or the old scroll position a previously hidden overlay becomes visible). | 205 * or the old scroll position a previously hidden overlay becomes visible). |
| 206 * @private | 206 * @private |
| 207 */ | 207 */ |
| 208 OptionsPage.updateScrollPosition_ = function() { | 208 OptionsPage.updateScrollPosition_ = function() { |
| 209 var container = $('page-container'); | 209 var container = $('page-container'); |
| 210 var scrollTop = container.oldScrollTop || 0; | 210 var scrollTop = container.oldScrollTop || 0; |
| 211 container.oldScrollTop = undefined; | 211 container.oldScrollTop = undefined; |
| 212 window.scroll(scrollLeftForDocument(document), scrollTop); | 212 window.scroll(scrollLeftForDocument(document), scrollTop); |
| 213 }; | 213 }; |
| 214 | 214 |
| 215 /** | 215 /** |
| 216 * Pushes the current page onto the history stack, overriding the last page | 216 * Updates the title to title of the current page. |
| 217 * if it is the generic chrome://settings/. | 217 * @private |
| 218 */ | |
| 219 OptionsPage.updateTitle_ = function() { | |
| 220 var page = this.getTopmostVisiblePage(); | |
| 221 uber.setTitle(page.title); | |
| 222 }; | |
| 223 | |
| 224 /** | |
| 225 * Pushes the current page onto the history stack, replacing the current entry | |
| 226 * if appropriate. | |
| 218 * @param {boolean} replace If true, allow no history events to be created. | 227 * @param {boolean} replace If true, allow no history events to be created. |
| 219 * @param {object=} opt_params A bag of optional params, including: | 228 * @param {object=} opt_params A bag of optional params, including: |
| 220 * {boolean} ignoreHash Whether to include the hash or not. | 229 * {boolean} ignoreHash Whether to include the hash or not. |
| 221 * @private | 230 * @private |
| 222 */ | 231 */ |
| 223 OptionsPage.updateHistoryState_ = function(replace, opt_params) { | 232 OptionsPage.updateHistoryState_ = function(replace, opt_params) { |
| 224 if (OptionsPage.isDialog) | 233 if (OptionsPage.isDialog) |
| 225 return; | 234 return; |
| 226 | 235 |
| 227 var page = this.getTopmostVisiblePage(); | 236 var page = this.getTopmostVisiblePage(); |
| 228 var path = window.location.pathname + window.location.hash; | 237 var path = window.location.pathname + window.location.hash; |
| 229 if (path) | 238 if (path) |
| 230 path = path.slice(1).replace(/\/(?:#|$)/, ''); // Remove trailing slash. | 239 path = path.slice(1).replace(/\/(?:#|$)/, ''); // Remove trailing slash. |
| 231 | 240 |
| 232 // Update tab title. | |
| 233 this.setTitle_(page.title); | |
|
davidben
2014/05/19 22:38:33
This is replaced by an explicit updateTitle_ call.
| |
| 234 | |
| 235 // The page is already in history (the user may have clicked the same link | 241 // The page is already in history (the user may have clicked the same link |
| 236 // twice). Do nothing. | 242 // twice). Do nothing. |
| 237 if (path == page.name && !OptionsPage.isLoading()) | 243 if (path == page.name && !OptionsPage.isLoading()) |
| 238 return; | 244 return; |
| 239 | 245 |
| 240 var hash = opt_params && opt_params.ignoreHash ? '' : window.location.hash; | 246 var hash = opt_params && opt_params.ignoreHash ? '' : window.location.hash; |
| 241 | 247 |
| 242 // If settings are embedded, tell the outer page to set its "path" to the | 248 var newPath = (page == this.getDefaultPage() ? '' : page.name) + hash; |
| 243 // inner frame's path. | 249 var historyFunction = replace ? uber.replaceState : uber.pushState; |
| 244 var outerPath = (page == this.getDefaultPage() ? '' : page.name) + hash; | 250 historyFunction.call(uber, {pageName: page.name}, newPath); |
| 245 uber.invokeMethodOnParent('setPath', {path: outerPath}); | |
| 246 | |
| 247 // If there is no path, the current location is chrome://settings/. | |
| 248 // Override this with the new page. | |
|
davidben
2014/05/19 22:38:33
This special-case is replaced with the new replace
| |
| 249 var historyFunction = path && !replace ? window.history.pushState : | |
| 250 window.history.replaceState; | |
| 251 historyFunction.call(window.history, | |
| 252 {pageName: page.name}, | |
| 253 page.title, | |
| 254 '/' + page.name + hash); | |
| 255 }; | 251 }; |
| 256 | 252 |
| 257 /** | 253 /** |
| 258 * Shows a registered Overlay page. Does not update history. | 254 * Shows a registered Overlay page. Does not update history. |
| 259 * @param {string} overlayName Page name. | 255 * @param {string} overlayName Page name. |
| 260 * @param {OptionPage} rootPage The currently visible root-level page. | 256 * @param {OptionPage} rootPage The currently visible root-level page. |
| 261 * @return {boolean} whether we showed an overlay. | 257 * @return {boolean} whether we showed an overlay. |
| 262 */ | 258 */ |
| 263 OptionsPage.showOverlay_ = function(overlayName, rootPage) { | 259 OptionsPage.showOverlay_ = function(overlayName, rootPage) { |
| 264 var overlay = this.registeredOverlayPages[overlayName.toLowerCase()]; | 260 var overlay = this.registeredOverlayPages[overlayName.toLowerCase()]; |
| 265 if (!overlay || !overlay.canShowPage()) | 261 if (!overlay || !overlay.canShowPage()) |
| 266 return false; | 262 return false; |
| 267 | 263 |
| 268 // Save the currently focused element in the page for restoration later. | 264 // Save the currently focused element in the page for restoration later. |
| 269 var currentPage = this.getTopmostVisiblePage(); | 265 var currentPage = this.getTopmostVisiblePage(); |
| 270 if (currentPage) | 266 if (currentPage) |
| 271 currentPage.lastFocusedElement = document.activeElement; | 267 currentPage.lastFocusedElement = document.activeElement; |
| 272 | 268 |
| 273 if ((!rootPage || !rootPage.sticky) && | 269 if ((!rootPage || !rootPage.sticky) && |
| 274 overlay.parentPage && | 270 overlay.parentPage && |
| 275 !overlay.parentPage.visible) { | 271 !overlay.parentPage.visible) { |
| 276 this.showPageByName(overlay.parentPage.name, false); | 272 this.showPageByName(overlay.parentPage.name, false); |
| 277 } | 273 } |
| 278 | 274 |
| 279 if (!overlay.visible) { | 275 if (!overlay.visible) { |
| 280 overlay.visible = true; | 276 overlay.visible = true; |
| 281 if (overlay.didShowPage) overlay.didShowPage(); | 277 if (overlay.didShowPage) overlay.didShowPage(); |
| 282 } | 278 } |
| 283 | 279 |
| 284 // Update tab title. | |
| 285 this.setTitle_(overlay.title); | |
|
davidben
2014/05/19 22:38:33
This is replaced by the updateTitle_ call later. I
| |
| 286 | |
| 287 // Change focus to the overlay if any other control was focused by keyboard | 280 // Change focus to the overlay if any other control was focused by keyboard |
| 288 // before. Otherwise, no one should have focus. | 281 // before. Otherwise, no one should have focus. |
| 289 if (document.activeElement != document.body) { | 282 if (document.activeElement != document.body) { |
| 290 if (FocusOutlineManager.forDocument(document).visible) { | 283 if (FocusOutlineManager.forDocument(document).visible) { |
| 291 overlay.focus(); | 284 overlay.focus(); |
| 292 } else if (!overlay.pageDiv.contains(document.activeElement)) { | 285 } else if (!overlay.pageDiv.contains(document.activeElement)) { |
| 293 document.activeElement.blur(); | 286 document.activeElement.blur(); |
| 294 } | 287 } |
| 295 } | 288 } |
| 296 | 289 |
| (...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 343 */ | 336 */ |
| 344 OptionsPage.closeOverlay = function() { | 337 OptionsPage.closeOverlay = function() { |
| 345 var overlay = this.getVisibleOverlay_(); | 338 var overlay = this.getVisibleOverlay_(); |
| 346 if (!overlay) | 339 if (!overlay) |
| 347 return; | 340 return; |
| 348 | 341 |
| 349 overlay.visible = false; | 342 overlay.visible = false; |
| 350 | 343 |
| 351 if (overlay.didClosePage) overlay.didClosePage(); | 344 if (overlay.didClosePage) overlay.didClosePage(); |
| 352 this.updateHistoryState_(false, {ignoreHash: true}); | 345 this.updateHistoryState_(false, {ignoreHash: true}); |
| 346 this.updateTitle_(); | |
| 353 | 347 |
| 354 this.restoreLastFocusedElement_(); | 348 this.restoreLastFocusedElement_(); |
| 355 }; | 349 }; |
| 356 | 350 |
| 357 /** | 351 /** |
| 358 * Closes all overlays and updates the history after each closed overlay. | 352 * Closes all overlays and updates the history after each closed overlay. |
| 359 */ | 353 */ |
| 360 OptionsPage.closeAllOverlays = function() { | 354 OptionsPage.closeAllOverlays = function() { |
| 361 while (this.isOverlayVisible_()) { | 355 while (this.isOverlayVisible_()) { |
| 362 this.closeOverlay(); | 356 this.closeOverlay(); |
| (...skipping 656 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1019 canShowPage: function() { | 1013 canShowPage: function() { |
| 1020 return true; | 1014 return true; |
| 1021 }, | 1015 }, |
| 1022 }; | 1016 }; |
| 1023 | 1017 |
| 1024 // Export | 1018 // Export |
| 1025 return { | 1019 return { |
| 1026 OptionsPage: OptionsPage | 1020 OptionsPage: OptionsPage |
| 1027 }; | 1021 }; |
| 1028 }); | 1022 }); |
| OLD | NEW |