OLD | NEW |
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 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 OptionsPage = options.OptionsPage; | 6 const OptionsPage = options.OptionsPage; |
7 | 7 |
8 /** | 8 /** |
9 * Encapsulated handling of a search bubble. | 9 * Encapsulated handling of a search bubble. |
10 * @constructor | 10 * @constructor |
(...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
98 } | 98 } |
99 } | 99 } |
100 | 100 |
101 /** | 101 /** |
102 * Encapsulated handling of the search page. | 102 * Encapsulated handling of the search page. |
103 * @constructor | 103 * @constructor |
104 */ | 104 */ |
105 function SearchPage() { | 105 function SearchPage() { |
106 OptionsPage.call(this, 'search', templateData.searchPageTabTitle, | 106 OptionsPage.call(this, 'search', templateData.searchPageTabTitle, |
107 'searchPage'); | 107 'searchPage'); |
108 this.searchActive = false; | |
109 } | 108 } |
110 | 109 |
111 cr.addSingletonGetter(SearchPage); | 110 cr.addSingletonGetter(SearchPage); |
112 | 111 |
113 SearchPage.prototype = { | 112 SearchPage.prototype = { |
114 // Inherit SearchPage from OptionsPage. | 113 // Inherit SearchPage from OptionsPage. |
115 __proto__: OptionsPage.prototype, | 114 __proto__: OptionsPage.prototype, |
116 | 115 |
117 /** | 116 /** |
| 117 * A boolean to prevent recursion. Used by setSearchText_(). |
| 118 * @type {Boolean} |
| 119 * @private |
| 120 */ |
| 121 insideSetSearchText_: false, |
| 122 |
| 123 /** |
118 * Initialize the page. | 124 * Initialize the page. |
119 */ | 125 */ |
120 initializePage: function() { | 126 initializePage: function() { |
121 // Call base class implementation to start preference initialization. | 127 // Call base class implementation to start preference initialization. |
122 OptionsPage.prototype.initializePage.call(this); | 128 OptionsPage.prototype.initializePage.call(this); |
123 | 129 |
124 var self = this; | 130 var self = this; |
125 | 131 |
126 // Create a search field element. | 132 // Create a search field element. |
127 var searchField = document.createElement('input'); | 133 var searchField = document.createElement('input'); |
(...skipping 10 matching lines...) Expand all Loading... |
138 self.tab.onclick = self.tab.onkeydown = self.tab.onkeypress = undefined; | 144 self.tab.onclick = self.tab.onkeydown = self.tab.onkeypress = undefined; |
139 self.tab.tabIndex = -1; | 145 self.tab.tabIndex = -1; |
140 self.tab.setAttribute('role', ''); | 146 self.tab.setAttribute('role', ''); |
141 | 147 |
142 // Don't allow the focus on the search navbar. http://crbug.com/77989 | 148 // Don't allow the focus on the search navbar. http://crbug.com/77989 |
143 self.tab.onfocus = self.tab.blur; | 149 self.tab.onfocus = self.tab.blur; |
144 | 150 |
145 // Handle search events. (No need to throttle, WebKit's search field | 151 // Handle search events. (No need to throttle, WebKit's search field |
146 // will do that automatically.) | 152 // will do that automatically.) |
147 searchField.onsearch = function(e) { | 153 searchField.onsearch = function(e) { |
148 self.setSearchText_(SearchPage.canonicalizeQuery(this.value)); | 154 self.setSearchText_(this.value); |
149 }; | 155 }; |
150 | 156 |
151 // We update the history stack every time the search field blurs. This way | 157 // We update the history stack every time the search field blurs. This way |
152 // we get a history entry for each search, roughly, but not each letter | 158 // we get a history entry for each search, roughly, but not each letter |
153 // typed. | 159 // typed. |
154 searchField.onblur = function(e) { | 160 searchField.onblur = function(e) { |
155 var query = SearchPage.canonicalizeQuery(searchField.value); | 161 var query = SearchPage.canonicalizeQuery(searchField.value); |
156 if (!query) | 162 if (!query) |
157 return; | 163 return; |
158 | 164 |
(...skipping 118 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
277 this.removeSearchBubbles_(); | 283 this.removeSearchBubbles_(); |
278 } | 284 } |
279 }, | 285 }, |
280 | 286 |
281 /** | 287 /** |
282 * Set the current search criteria. | 288 * Set the current search criteria. |
283 * @param {string} text Search text. | 289 * @param {string} text Search text. |
284 * @private | 290 * @private |
285 */ | 291 */ |
286 setSearchText_: function(text) { | 292 setSearchText_: function(text) { |
| 293 // Prevent recursive execution of this method. |
| 294 if (this.insideSetSearchText_) return; |
| 295 this.insideSetSearchText_ = true; |
| 296 |
| 297 // Cleanup the search query string. |
| 298 text = SearchPage.canonicalizeQuery(text); |
| 299 |
| 300 // Notify listeners about the new search query, some pages may wish to |
| 301 // show/hide elements based on the query. |
| 302 var event = new cr.Event('searchChanged'); |
| 303 event.searchText = text; |
| 304 this.dispatchEvent(event); |
| 305 |
287 // Toggle the search page if necessary. | 306 // Toggle the search page if necessary. |
288 if (text.length) { | 307 if (text.length) { |
289 if (!this.searchActive_) | 308 if (!this.searchActive_) |
290 OptionsPage.navigateToPage(this.name); | 309 OptionsPage.navigateToPage(this.name); |
291 } else { | 310 } else { |
292 if (this.searchActive_) | 311 if (this.searchActive_) |
293 OptionsPage.showDefaultPage(); | 312 OptionsPage.showDefaultPage(); |
| 313 |
| 314 this.insideSetSearchText_ = false; |
294 return; | 315 return; |
295 } | 316 } |
296 | 317 |
297 var foundMatches = false; | 318 var foundMatches = false; |
298 var bubbleControls = []; | 319 var bubbleControls = []; |
299 | 320 |
300 // Remove any prior search results. | 321 // Remove any prior search results. |
301 this.unhighlightMatches_(); | 322 this.unhighlightMatches_(); |
302 this.removeSearchBubbles_(); | 323 this.removeSearchBubbles_(); |
303 | 324 |
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
374 // Configure elements on the search results page based on search results. | 395 // Configure elements on the search results page based on search results. |
375 if (foundMatches) | 396 if (foundMatches) |
376 $('searchPageNoMatches').classList.add('search-hidden'); | 397 $('searchPageNoMatches').classList.add('search-hidden'); |
377 else | 398 else |
378 $('searchPageNoMatches').classList.remove('search-hidden'); | 399 $('searchPageNoMatches').classList.remove('search-hidden'); |
379 | 400 |
380 // Create search balloons for sub-page results. | 401 // Create search balloons for sub-page results. |
381 length = bubbleControls.length; | 402 length = bubbleControls.length; |
382 for (var i = 0; i < length; i++) | 403 for (var i = 0; i < length; i++) |
383 this.createSearchBubble_(bubbleControls[i], text); | 404 this.createSearchBubble_(bubbleControls[i], text); |
| 405 |
| 406 // Cleanup the recursion-prevention variable. |
| 407 this.insideSetSearchText_ = false; |
384 }, | 408 }, |
385 | 409 |
386 /** | 410 /** |
387 * Performs a string replacement based on a regex and replace string. | 411 * Performs a string replacement based on a regex and replace string. |
388 * @param {RegEx} regex A regular expression for finding search matches. | 412 * @param {RegEx} regex A regular expression for finding search matches. |
389 * @param {String} replace A string to apply the replace operation. | 413 * @param {String} replace A string to apply the replace operation. |
390 * @param {Element} element An HTML container element. | 414 * @param {Element} element An HTML container element. |
391 * @returns {Boolean} true if the element was changed. | 415 * @returns {Boolean} true if the element was changed. |
392 * @private | 416 * @private |
393 */ | 417 */ |
(...skipping 171 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
565 // Trim beginning and ending whitespace. | 589 // Trim beginning and ending whitespace. |
566 return text.replace(/^\s+|\s+$/g, ''); | 590 return text.replace(/^\s+|\s+$/g, ''); |
567 }; | 591 }; |
568 | 592 |
569 // Export | 593 // Export |
570 return { | 594 return { |
571 SearchPage: SearchPage | 595 SearchPage: SearchPage |
572 }; | 596 }; |
573 | 597 |
574 }); | 598 }); |
OLD | NEW |