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

Side by Side Diff: Source/devtools/front_end/components/SearchableView.js

Issue 632573002: Adding regex support to search bar in dev tools console (Closed) Base URL: https://chromium.googlesource.com/chromium/blink@master
Patch Set: Implement regex search similar to Sublime Text Created 6 years, 2 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
« no previous file with comments | « no previous file | Source/devtools/front_end/console/ConsoleView.js » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved. 2 * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved.
3 * Copyright (C) 2007 Matt Lilek (pewtermoose@gmail.com). 3 * Copyright (C) 2007 Matt Lilek (pewtermoose@gmail.com).
4 * Copyright (C) 2009 Joseph Pecoraro 4 * Copyright (C) 2009 Joseph Pecoraro
5 * Copyright (C) 2011 Google Inc. All rights reserved. 5 * Copyright (C) 2011 Google Inc. All rights reserved.
6 * 6 *
7 * Redistribution and use in source and binary forms, with or without 7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions 8 * modification, are permitted provided that the following conditions
9 * are met: 9 * are met:
10 * 10 *
(...skipping 15 matching lines...) Expand all
26 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 26 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
27 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 27 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 28 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
29 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 29 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 */ 30 */
31 31
32 /** 32 /**
33 * @constructor 33 * @constructor
34 * @extends {WebInspector.VBox} 34 * @extends {WebInspector.VBox}
35 * @param {!WebInspector.Searchable} searchable 35 * @param {!WebInspector.Searchable} searchable
36 * @param {?boolean=} supportRegex
36 */ 37 */
37 WebInspector.SearchableView = function(searchable) 38 WebInspector.SearchableView = function(searchable, supportRegex)
38 { 39 {
39 WebInspector.VBox.call(this); 40 WebInspector.VBox.call(this);
41 this.registerRequiredCSS("searchable.css");
40 42
41 this._searchProvider = searchable; 43 this._searchProvider = searchable;
42 this.element.addEventListener("keydown", this._onKeyDown.bind(this), false); 44 this.element.addEventListener("keydown", this._onKeyDown.bind(this), false);
43 45
44 this._footerElementContainer = this.element.createChild("div", "search-bar s tatus-bar hidden"); 46 this._footerElementContainer = this.element.createChild("div", "search-bar s tatus-bar hidden");
45 this._footerElementContainer.style.order = 100; 47 this._footerElementContainer.style.order = 100;
46 48
47 this._footerElement = this._footerElementContainer.createChild("table", "too lbar-search"); 49 this._footerElement = this._footerElementContainer.createChild("table", "too lbar-search");
48 this._footerElement.cellSpacing = 0; 50 this._footerElement.cellSpacing = 0;
49 51
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after
95 this._prevButtonElement.textContent = WebInspector.UIString("Previous"); 97 this._prevButtonElement.textContent = WebInspector.UIString("Previous");
96 this._prevButtonElement.tabIndex = -1; 98 this._prevButtonElement.tabIndex = -1;
97 this._prevButtonElement.addEventListener("click", this._onPreviousClick.bind (this), false); 99 this._prevButtonElement.addEventListener("click", this._onPreviousClick.bind (this), false);
98 100
99 this._replaceAllButtonElement = this._secondRowElement.createChild("td").cre ateChild("button"); 101 this._replaceAllButtonElement = this._secondRowElement.createChild("td").cre ateChild("button");
100 this._replaceAllButtonElement.textContent = WebInspector.UIString("Replace A ll"); 102 this._replaceAllButtonElement.textContent = WebInspector.UIString("Replace A ll");
101 this._replaceAllButtonElement.addEventListener("click", this._replaceAll.bin d(this), false); 103 this._replaceAllButtonElement.addEventListener("click", this._replaceAll.bin d(this), false);
102 104
103 // Column 4 105 // Column 4
104 this._replaceElement = this._firstRowElement.createChild("td").createChild(" span"); 106 this._replaceElement = this._firstRowElement.createChild("td").createChild(" span");
107 this._uniqueId = ++WebInspector.SearchableView._lastUniqueId;
108 var replaceChildElements = this._createCheckbox(this._replaceElement, "searc h-replace",
109 this._updateSecondRowVisibility, "Replace");
110 this._replaceCheckboxElement = replaceChildElements[0];
111 this._replaceLabelElement = replaceChildElements[1];
105 112
106 this._replaceCheckboxElement = this._replaceElement.createChild("input"); 113 if (supportRegex) {
107 this._replaceCheckboxElement.type = "checkbox"; 114 this.enableRegex = false;
108 this._uniqueId = ++WebInspector.SearchableView._lastUniqueId; 115 this._regexElement = this._firstRowElement.createChild("td").createChild ("span");
109 var replaceCheckboxId = "search-replace-trigger" + this._uniqueId; 116 var regexChildElements = this._createCheckbox(this._regexElement, "searc h-regex", this._onRegexToggle,
110 this._replaceCheckboxElement.id = replaceCheckboxId; 117 "Regex");
111 this._replaceCheckboxElement.addEventListener("change", this._updateSecondRo wVisibility.bind(this), false); 118 this._regexCheckboxElement = regexChildElements[0];
112 119 this._regexLabelElement = regexChildElements[1];
113 this._replaceLabelElement = this._replaceElement.createChild("label"); 120 }
114 this._replaceLabelElement.textContent = WebInspector.UIString("Replace");
115 this._replaceLabelElement.setAttribute("for", replaceCheckboxId);
116 121
117 // Column 5 122 // Column 5
118 var cancelButtonElement = this._firstRowElement.createChild("td").createChil d("button"); 123 var cancelButtonElement = this._firstRowElement.createChild("td").createChil d("button");
119 cancelButtonElement.textContent = WebInspector.UIString("Cancel"); 124 cancelButtonElement.textContent = WebInspector.UIString("Cancel");
120 cancelButtonElement.tabIndex = -1; 125 cancelButtonElement.tabIndex = -1;
121 cancelButtonElement.addEventListener("click", this.closeSearch.bind(this), f alse); 126 cancelButtonElement.addEventListener("click", this.closeSearch.bind(this), f alse);
122 this._minimalSearchQuerySize = 3; 127 this._minimalSearchQuerySize = 3;
123 128
124 this._registerShortcuts(); 129 this._registerShortcuts();
125 } 130 }
(...skipping 352 matching lines...) Expand 10 before | Expand all | Expand 10 after
478 }, 483 },
479 484
480 _clearSearch: function() 485 _clearSearch: function()
481 { 486 {
482 delete this._currentQuery; 487 delete this._currentQuery;
483 if (!!this._searchProvider.currentQuery) { 488 if (!!this._searchProvider.currentQuery) {
484 delete this._searchProvider.currentQuery; 489 delete this._searchProvider.currentQuery;
485 this._searchProvider.searchCanceled(); 490 this._searchProvider.searchCanceled();
486 } 491 }
487 this._updateSearchMatchesCountAndCurrentMatchIndex(0, -1); 492 this._updateSearchMatchesCountAndCurrentMatchIndex(0, -1);
493 this.setQueryInvalid(false);
488 }, 494 },
489 495
490 /** 496 /**
491 * @param {boolean} forceSearch 497 * @param {boolean} forceSearch
492 * @param {boolean} shouldJump 498 * @param {boolean} shouldJump
493 * @param {boolean=} jumpBackwards 499 * @param {boolean=} jumpBackwards
494 */ 500 */
495 _performSearch: function(forceSearch, shouldJump, jumpBackwards) 501 _performSearch: function(forceSearch, shouldJump, jumpBackwards)
496 { 502 {
497 var query = this._searchInputElement.value; 503 var query = this._searchInputElement.value;
498 if (!query || (!forceSearch && query.length < this._minimalSearchQuerySi ze && !this._currentQuery)) { 504 if (!query || (!forceSearch && query.length < this._minimalSearchQuerySi ze && !this._currentQuery)) {
499 this._clearSearch(); 505 this._clearSearch();
500 return; 506 return;
501 } 507 }
502 508
509 this.setQueryInvalid(false);
503 this._currentQuery = query; 510 this._currentQuery = query;
504 this._searchProvider.currentQuery = query; 511 this._searchProvider.currentQuery = query;
505 this._searchProvider.performSearch(query, shouldJump, jumpBackwards); 512 if (!this.enableRegex) {
513 this._searchProvider.performSearch(query, shouldJump, jumpBackwards) ;
514 } else {
515 this._searchProvider.performRegexSearch(query, shouldJump, jumpBackw ards);
516 }
506 }, 517 },
507 518
508 _updateSecondRowVisibility: function() 519 _updateSecondRowVisibility: function()
509 { 520 {
510 var secondRowVisible = this._replaceCheckboxElement.checked; 521 var secondRowVisible = this._replaceCheckboxElement.checked;
511 this._footerElementContainer.classList.toggle("replaceable", secondRowVi sible); 522 this._footerElementContainer.classList.toggle("replaceable", secondRowVi sible);
512 this._footerElement.classList.toggle("toolbar-search-replace", secondRow Visible); 523 this._footerElement.classList.toggle("toolbar-search-replace", secondRow Visible);
513 this._secondRowElement.classList.toggle("hidden", !secondRowVisible); 524 this._secondRowElement.classList.toggle("hidden", !secondRowVisible);
514 this._prevButtonElement.classList.toggle("hidden", !secondRowVisible); 525 this._prevButtonElement.classList.toggle("hidden", !secondRowVisible);
515 this._findButtonElement.classList.toggle("hidden", !secondRowVisible); 526 this._findButtonElement.classList.toggle("hidden", !secondRowVisible);
(...skipping 21 matching lines...) Expand all
537 _onInput: function(event) 548 _onInput: function(event)
538 { 549 {
539 this._onValueChanged(); 550 this._onValueChanged();
540 }, 551 },
541 552
542 _onValueChanged: function() 553 _onValueChanged: function()
543 { 554 {
544 this._performSearch(false, true); 555 this._performSearch(false, true);
545 }, 556 },
546 557
558 _onRegexToggle: function (event)
559 {
560 this._searchProvider.searchCanceled();
561 this.enableRegex = event.target.checked;
562 this._performSearch(true, true, true);
563 },
564
565 setQueryInvalid: function (invalid) {
566 var cls = "search-query-invalid";
567 if (invalid) {
568 this._searchInputElement.classList.add(cls);
569 } else {
570 this._searchInputElement.classList.remove(cls);
571 }
572 },
573
574 _createCheckbox: function(parentElement, idPrefix, toggleCallback, label)
575 {
576 var checkboxElement = parentElement.createChild("input");
577 checkboxElement.type = "checkbox";
578 var checkboxId = idPrefix + "-trigger" + this._uniqueId;
579 checkboxElement.id = checkboxId;
580 checkboxElement.addEventListener("change", toggleCallback.bind(this), fa lse);
581
582 var labelElement = parentElement.createChild("label");
583 labelElement.textContent = WebInspector.UIString(label);
584 labelElement.setAttribute("for", checkboxId);
585
586 return [checkboxElement, labelElement];
587 },
588
547 __proto__: WebInspector.VBox.prototype 589 __proto__: WebInspector.VBox.prototype
548 } 590 }
549 591
550 /** 592 /**
551 * @interface 593 * @interface
552 */ 594 */
553 WebInspector.Searchable = function() 595 WebInspector.Searchable = function()
554 { 596 {
555 } 597 }
556 598
557 WebInspector.Searchable.prototype = { 599 WebInspector.Searchable.prototype = {
558 searchCanceled: function() { }, 600 searchCanceled: function() { },
559 601
560 /** 602 /**
561 * @param {string} query 603 * @param {string} query
562 * @param {boolean} shouldJump 604 * @param {boolean} shouldJump
563 * @param {boolean=} jumpBackwards 605 * @param {boolean=} jumpBackwards
564 */ 606 */
565 performSearch: function(query, shouldJump, jumpBackwards) { }, 607 performSearch: function(query, shouldJump, jumpBackwards) { },
566 608
609 performRegexSearch: function(query, shouldJump, jumpBackwards) { },
610
567 jumpToNextSearchResult: function() { }, 611 jumpToNextSearchResult: function() { },
568 612
569 jumpToPreviousSearchResult: function() { } 613 jumpToPreviousSearchResult: function() { }
570 } 614 }
571 615
572 /** 616 /**
573 * @interface 617 * @interface
574 */ 618 */
575 WebInspector.Replaceable = function() 619 WebInspector.Replaceable = function()
576 { 620 {
577 } 621 }
578 622
579 WebInspector.Replaceable.prototype = { 623 WebInspector.Replaceable.prototype = {
580 /** 624 /**
581 * @param {string} text 625 * @param {string} text
582 */ 626 */
583 replaceSelectionWith: function(text) { }, 627 replaceSelectionWith: function(text) { },
584 628
585 /** 629 /**
586 * @param {string} query 630 * @param {string} query
587 * @param {string} replacement 631 * @param {string} replacement
588 */ 632 */
589 replaceAllWith: function(query, replacement) { } 633 replaceAllWith: function(query, replacement) { }
590 } 634 }
OLDNEW
« no previous file with comments | « no previous file | Source/devtools/front_end/console/ConsoleView.js » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698