Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2012 The Chromium Authors. All rights reserved. | 1 // Copyright 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 #include "components/omnibox/browser/omnibox_edit_model.h" | 5 #include "components/omnibox/browser/omnibox_edit_model.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 #include <string> | 8 #include <string> |
| 9 #include <utility> | 9 #include <utility> |
| 10 | 10 |
| (...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 81 // Histogram name which counts the number of milliseconds a user takes | 81 // Histogram name which counts the number of milliseconds a user takes |
| 82 // between focusing and opening an omnibox match. | 82 // between focusing and opening an omnibox match. |
| 83 const char kFocusToOpenTimeHistogram[] = "Omnibox.FocusToOpenTimeAnyPopupState"; | 83 const char kFocusToOpenTimeHistogram[] = "Omnibox.FocusToOpenTimeAnyPopupState"; |
| 84 | 84 |
| 85 // Split the percentage match histograms into buckets based on the width of the | 85 // Split the percentage match histograms into buckets based on the width of the |
| 86 // omnibox. | 86 // omnibox. |
| 87 const int kPercentageMatchHistogramWidthBuckets[] = { 400, 700, 1200 }; | 87 const int kPercentageMatchHistogramWidthBuckets[] = { 400, 700, 1200 }; |
| 88 | 88 |
| 89 void RecordPercentageMatchHistogram(const base::string16& old_text, | 89 void RecordPercentageMatchHistogram(const base::string16& old_text, |
| 90 const base::string16& new_text, | 90 const base::string16& new_text, |
| 91 bool url_replacement_active, | |
| 92 ui::PageTransition transition, | 91 ui::PageTransition transition, |
| 93 int omnibox_width) { | 92 int omnibox_width) { |
| 94 size_t avg_length = (old_text.length() + new_text.length()) / 2; | 93 size_t avg_length = (old_text.length() + new_text.length()) / 2; |
| 95 | 94 |
| 96 int percent = 0; | 95 int percent = 0; |
| 97 if (!old_text.empty() && !new_text.empty()) { | 96 if (!old_text.empty() && !new_text.empty()) { |
| 98 size_t shorter_length = std::min(old_text.length(), new_text.length()); | 97 size_t shorter_length = std::min(old_text.length(), new_text.length()); |
| 99 base::string16::const_iterator end(old_text.begin() + shorter_length); | 98 base::string16::const_iterator end(old_text.begin() + shorter_length); |
| 100 base::string16::const_iterator mismatch( | 99 base::string16::const_iterator mismatch( |
| 101 std::mismatch(old_text.begin(), end, new_text.begin()).first); | 100 std::mismatch(old_text.begin(), end, new_text.begin()).first); |
| 102 size_t matching_characters = mismatch - old_text.begin(); | 101 size_t matching_characters = mismatch - old_text.begin(); |
| 103 percent = static_cast<float>(matching_characters) / avg_length * 100; | 102 percent = static_cast<float>(matching_characters) / avg_length * 100; |
| 104 } | 103 } |
| 105 | 104 |
| 106 std::string histogram_name; | 105 std::string histogram_name; |
| 107 if (url_replacement_active) { | 106 if (ui::PageTransitionTypeIncludingQualifiersIs( |
| 108 if (ui::PageTransitionTypeIncludingQualifiersIs( | 107 transition, ui::PAGE_TRANSITION_TYPED)) { |
|
Peter Kasting
2016/08/13 05:03:44
You should check with mpearson as to whether we wa
Marc Treib
2016/08/16 12:00:18
Added a TODO for now.
| |
| 109 transition, ui::PAGE_TRANSITION_TYPED)) { | 108 histogram_name = "InstantExtended.PercentageMatchV2_URLtoURL"; |
| 110 histogram_name = "InstantExtended.PercentageMatchV2_QuerytoURL"; | 109 UMA_HISTOGRAM_PERCENTAGE(histogram_name, percent); |
| 111 UMA_HISTOGRAM_PERCENTAGE(histogram_name, percent); | |
| 112 } else { | |
| 113 histogram_name = "InstantExtended.PercentageMatchV2_QuerytoQuery"; | |
| 114 UMA_HISTOGRAM_PERCENTAGE(histogram_name, percent); | |
| 115 } | |
| 116 } else { | 110 } else { |
| 117 if (ui::PageTransitionTypeIncludingQualifiersIs( | 111 histogram_name = "InstantExtended.PercentageMatchV2_URLtoQuery"; |
| 118 transition, ui::PAGE_TRANSITION_TYPED)) { | 112 UMA_HISTOGRAM_PERCENTAGE(histogram_name, percent); |
| 119 histogram_name = "InstantExtended.PercentageMatchV2_URLtoURL"; | |
| 120 UMA_HISTOGRAM_PERCENTAGE(histogram_name, percent); | |
| 121 } else { | |
| 122 histogram_name = "InstantExtended.PercentageMatchV2_URLtoQuery"; | |
| 123 UMA_HISTOGRAM_PERCENTAGE(histogram_name, percent); | |
| 124 } | |
| 125 } | 113 } |
| 126 | 114 |
| 127 std::string suffix = "large"; | 115 std::string suffix = "large"; |
| 128 for (size_t i = 0; i < arraysize(kPercentageMatchHistogramWidthBuckets); | 116 for (size_t i = 0; i < arraysize(kPercentageMatchHistogramWidthBuckets); |
| 129 ++i) { | 117 ++i) { |
| 130 if (omnibox_width < kPercentageMatchHistogramWidthBuckets[i]) { | 118 if (omnibox_width < kPercentageMatchHistogramWidthBuckets[i]) { |
| 131 suffix = base::IntToString(kPercentageMatchHistogramWidthBuckets[i]); | 119 suffix = base::IntToString(kPercentageMatchHistogramWidthBuckets[i]); |
| 132 break; | 120 break; |
| 133 } | 121 } |
| 134 } | 122 } |
| (...skipping 216 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 351 base::string16* title, | 339 base::string16* title, |
| 352 gfx::Image* favicon) { | 340 gfx::Image* favicon) { |
| 353 *url = CurrentMatch(nullptr).destination_url; | 341 *url = CurrentMatch(nullptr).destination_url; |
| 354 if (*url == client_->GetURL()) { | 342 if (*url == client_->GetURL()) { |
| 355 *title = client_->GetTitle(); | 343 *title = client_->GetTitle(); |
| 356 *favicon = client_->GetFavicon(); | 344 *favicon = client_->GetFavicon(); |
| 357 } | 345 } |
| 358 } | 346 } |
| 359 | 347 |
| 360 bool OmniboxEditModel::CurrentTextIsURL() const { | 348 bool OmniboxEditModel::CurrentTextIsURL() const { |
| 361 if (controller_->GetToolbarModel()->WouldReplaceURL()) | |
| 362 return false; | |
| 363 | |
| 364 // If current text is not composed of replaced search terms and | 349 // If current text is not composed of replaced search terms and |
|
Peter Kasting
2016/08/13 05:03:44
Nit: Remove everything in this line but the first
Marc Treib
2016/08/16 12:00:17
Done.
| |
| 365 // !user_input_in_progress_, then permanent text is showing and should be a | 350 // !user_input_in_progress_, then permanent text is showing and should be a |
| 366 // URL, so no further checking is needed. By avoiding checking in this case, | 351 // URL, so no further checking is needed. By avoiding checking in this case, |
| 367 // we avoid calling into the autocomplete providers, and thus initializing the | 352 // we avoid calling into the autocomplete providers, and thus initializing the |
| 368 // history system, as long as possible, which speeds startup. | 353 // history system, as long as possible, which speeds startup. |
| 369 if (!user_input_in_progress_) | 354 if (!user_input_in_progress_) |
| 370 return true; | 355 return true; |
| 371 | 356 |
| 372 return !AutocompleteMatch::IsSearchType(CurrentMatch(nullptr).type); | 357 return !AutocompleteMatch::IsSearchType(CurrentMatch(nullptr).type); |
| 373 } | 358 } |
| 374 | 359 |
| 375 AutocompleteMatch::Type OmniboxEditModel::CurrentTextType() const { | 360 AutocompleteMatch::Type OmniboxEditModel::CurrentTextType() const { |
| 376 return CurrentMatch(nullptr).type; | 361 return CurrentMatch(nullptr).type; |
| 377 } | 362 } |
| 378 | 363 |
| 379 void OmniboxEditModel::AdjustTextForCopy(int sel_min, | 364 void OmniboxEditModel::AdjustTextForCopy(int sel_min, |
| 380 bool is_all_selected, | 365 bool is_all_selected, |
| 381 base::string16* text, | 366 base::string16* text, |
| 382 GURL* url, | 367 GURL* url, |
| 383 bool* write_url) { | 368 bool* write_url) { |
| 384 *write_url = false; | 369 *write_url = false; |
| 385 | 370 |
| 386 // Do not adjust if selection did not start at the beginning of the field, or | 371 // Do not adjust if selection did not start at the beginning of the field. |
| 387 // if the URL was omitted. | 372 if ((sel_min != 0)) |
|
Peter Kasting
2016/08/13 05:03:44
Nit: Extra ()
Marc Treib
2016/08/16 12:00:17
Done.
| |
| 388 if ((sel_min != 0) || controller_->GetToolbarModel()->WouldReplaceURL()) | |
| 389 return; | 373 return; |
| 390 | 374 |
| 391 // Check whether the user is trying to copy the current page's URL by | 375 // Check whether the user is trying to copy the current page's URL by |
| 392 // selecting the whole thing without editing it. | 376 // selecting the whole thing without editing it. |
| 393 // | 377 // |
| 394 // This is complicated by ZeroSuggest. When ZeroSuggest is active, the user | 378 // This is complicated by ZeroSuggest. When ZeroSuggest is active, the user |
| 395 // may be selecting different items and thus changing the address bar text, | 379 // may be selecting different items and thus changing the address bar text, |
| 396 // even though !user_input_in_progress_; and the permanent URL may change | 380 // even though !user_input_in_progress_; and the permanent URL may change |
| 397 // without updating the visible text, just like when user input is in | 381 // without updating the visible text, just like when user input is in |
| 398 // progress. In these cases, we don't want to copy the underlying URL, we | 382 // progress. In these cases, we don't want to copy the underlying URL, we |
| (...skipping 371 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 770 | 754 |
| 771 // Get the current text before we call RevertAll() which will clear it. | 755 // Get the current text before we call RevertAll() which will clear it. |
| 772 base::string16 current_text = view_->GetText(); | 756 base::string16 current_text = view_->GetText(); |
| 773 | 757 |
| 774 if (disposition != NEW_BACKGROUND_TAB) { | 758 if (disposition != NEW_BACKGROUND_TAB) { |
| 775 base::AutoReset<bool> tmp(&in_revert_, true); | 759 base::AutoReset<bool> tmp(&in_revert_, true); |
| 776 view_->RevertAll(); // Revert the box to its unedited state. | 760 view_->RevertAll(); // Revert the box to its unedited state. |
| 777 } | 761 } |
| 778 | 762 |
| 779 RecordPercentageMatchHistogram( | 763 RecordPercentageMatchHistogram( |
| 780 permanent_text_, current_text, | 764 permanent_text_, current_text, match.transition, view_->GetWidth()); |
| 781 controller_->GetToolbarModel()->WouldReplaceURL(), | |
| 782 match.transition, view_->GetWidth()); | |
| 783 | 765 |
| 784 // Track whether the destination URL sends us to a search results page | 766 // Track whether the destination URL sends us to a search results page |
| 785 // using the default search provider. | 767 // using the default search provider. |
| 786 TemplateURLService* template_url_service = client_->GetTemplateURLService(); | 768 TemplateURLService* template_url_service = client_->GetTemplateURLService(); |
| 787 if (template_url_service && | 769 if (template_url_service && |
| 788 template_url_service->IsSearchResultsPageFromDefaultSearchProvider( | 770 template_url_service->IsSearchResultsPageFromDefaultSearchProvider( |
| 789 match.destination_url)) { | 771 match.destination_url)) { |
| 790 base::RecordAction( | 772 base::RecordAction( |
| 791 base::UserMetricsAction("OmniboxDestinationURLIsSearchOnDSP")); | 773 base::UserMetricsAction("OmniboxDestinationURLIsSearchOnDSP")); |
| 792 } | 774 } |
| (...skipping 581 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1374 | 1356 |
| 1375 base::string16 OmniboxEditModel::MaybePrependKeyword( | 1357 base::string16 OmniboxEditModel::MaybePrependKeyword( |
| 1376 const base::string16& text) const { | 1358 const base::string16& text) const { |
| 1377 return is_keyword_selected() ? (keyword_ + base::char16(' ') + text) : text; | 1359 return is_keyword_selected() ? (keyword_ + base::char16(' ') + text) : text; |
| 1378 } | 1360 } |
| 1379 | 1361 |
| 1380 void OmniboxEditModel::GetInfoForCurrentText(AutocompleteMatch* match, | 1362 void OmniboxEditModel::GetInfoForCurrentText(AutocompleteMatch* match, |
| 1381 GURL* alternate_nav_url) const { | 1363 GURL* alternate_nav_url) const { |
| 1382 DCHECK(match); | 1364 DCHECK(match); |
| 1383 | 1365 |
| 1384 if (controller_->GetToolbarModel()->WouldPerformSearchTermReplacement( | 1366 if (query_in_progress() || PopupIsOpen()) { |
| 1385 false)) { | |
| 1386 // Any time the user hits enter on the unchanged omnibox, we should reload. | |
| 1387 // When we're not extracting search terms, AcceptInput() will take care of | |
| 1388 // this (see code referring to PAGE_TRANSITION_RELOAD there), but when we're | |
| 1389 // extracting search terms, the conditionals there won't fire, so we | |
| 1390 // explicitly set up a match that will reload here. | |
| 1391 | |
| 1392 // It's important that we fetch the current visible URL to reload instead of | |
| 1393 // just getting a "search what you typed" URL from | |
| 1394 // SearchProvider::CreateSearchSuggestion(), since the user may be in a | |
| 1395 // non-default search mode such as image search. | |
| 1396 match->type = AutocompleteMatchType::SEARCH_WHAT_YOU_TYPED; | |
| 1397 match->provider = autocomplete_controller()->search_provider(); | |
| 1398 match->destination_url = client_->GetURL(); | |
| 1399 match->transition = ui::PAGE_TRANSITION_RELOAD; | |
| 1400 } else if (query_in_progress() || PopupIsOpen()) { | |
| 1401 if (query_in_progress()) { | 1367 if (query_in_progress()) { |
| 1402 // It's technically possible for |result| to be empty if no provider | 1368 // It's technically possible for |result| to be empty if no provider |
| 1403 // returns a synchronous result but the query has not completed | 1369 // returns a synchronous result but the query has not completed |
| 1404 // synchronously; pratically, however, that should never actually happen. | 1370 // synchronously; pratically, however, that should never actually happen. |
| 1405 if (result().empty()) | 1371 if (result().empty()) |
| 1406 return; | 1372 return; |
| 1407 // The user cannot have manually selected a match, or the query would have | 1373 // The user cannot have manually selected a match, or the query would have |
| 1408 // stopped. So the default match must be the desired selection. | 1374 // stopped. So the default match must be the desired selection. |
| 1409 *match = *result().default_match(); | 1375 *match = *result().default_match(); |
| 1410 } else { | 1376 } else { |
| (...skipping 91 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1502 const GURL& gurl = client_->GetURL(); | 1468 const GURL& gurl = client_->GetURL(); |
| 1503 if (!gurl.is_valid()) | 1469 if (!gurl.is_valid()) |
| 1504 return OmniboxEventProto::INVALID_SPEC; | 1470 return OmniboxEventProto::INVALID_SPEC; |
| 1505 const std::string& url = gurl.spec(); | 1471 const std::string& url = gurl.spec(); |
| 1506 if (client_->IsNewTabPage(url)) | 1472 if (client_->IsNewTabPage(url)) |
| 1507 return OmniboxEventProto::NTP; | 1473 return OmniboxEventProto::NTP; |
| 1508 if (url == url::kAboutBlankURL) | 1474 if (url == url::kAboutBlankURL) |
| 1509 return OmniboxEventProto::BLANK; | 1475 return OmniboxEventProto::BLANK; |
| 1510 if (client_->IsHomePage(url)) | 1476 if (client_->IsHomePage(url)) |
| 1511 return OmniboxEventProto::HOME_PAGE; | 1477 return OmniboxEventProto::HOME_PAGE; |
| 1512 if (controller_->GetToolbarModel()->WouldPerformSearchTermReplacement(true)) | |
| 1513 return OmniboxEventProto::SEARCH_RESULT_PAGE_DOING_SEARCH_TERM_REPLACEMENT; | |
|
Peter Kasting
2016/08/13 05:03:44
This value should be changed to OBSOLETE in the pr
Marc Treib
2016/08/16 12:00:17
Done.
| |
| 1514 if (client_->IsSearchResultsPage()) | 1478 if (client_->IsSearchResultsPage()) |
| 1515 return OmniboxEventProto::SEARCH_RESULT_PAGE_NO_SEARCH_TERM_REPLACEMENT; | 1479 return OmniboxEventProto::SEARCH_RESULT_PAGE_NO_SEARCH_TERM_REPLACEMENT; |
| 1516 return OmniboxEventProto::OTHER; | 1480 return OmniboxEventProto::OTHER; |
| 1517 } | 1481 } |
| 1518 | 1482 |
| 1519 void OmniboxEditModel::ClassifyStringForPasteAndGo( | 1483 void OmniboxEditModel::ClassifyStringForPasteAndGo( |
| 1520 const base::string16& text, | 1484 const base::string16& text, |
| 1521 AutocompleteMatch* match, | 1485 AutocompleteMatch* match, |
| 1522 GURL* alternate_nav_url) const { | 1486 GURL* alternate_nav_url) const { |
| 1523 DCHECK(match); | 1487 DCHECK(match); |
| 1524 client_->GetAutocompleteClassifier()->Classify( | 1488 client_->GetAutocompleteClassifier()->Classify( |
| 1525 text, false, false, ClassifyPage(), match, alternate_nav_url); | 1489 text, false, false, ClassifyPage(), match, alternate_nav_url); |
| 1526 } | 1490 } |
| 1527 | 1491 |
| 1528 void OmniboxEditModel::SetFocusState(OmniboxFocusState state, | 1492 void OmniboxEditModel::SetFocusState(OmniboxFocusState state, |
| 1529 OmniboxFocusChangeReason reason) { | 1493 OmniboxFocusChangeReason reason) { |
| 1530 if (state == focus_state_) | 1494 if (state == focus_state_) |
| 1531 return; | 1495 return; |
| 1532 | 1496 |
| 1533 // Update state and notify view if the omnibox has focus and the caret | 1497 // Update state and notify view if the omnibox has focus and the caret |
| 1534 // visibility changed. | 1498 // visibility changed. |
| 1535 const bool was_caret_visible = is_caret_visible(); | 1499 const bool was_caret_visible = is_caret_visible(); |
| 1536 focus_state_ = state; | 1500 focus_state_ = state; |
| 1537 if (focus_state_ != OMNIBOX_FOCUS_NONE && | 1501 if (focus_state_ != OMNIBOX_FOCUS_NONE && |
| 1538 is_caret_visible() != was_caret_visible) | 1502 is_caret_visible() != was_caret_visible) |
| 1539 view_->ApplyCaretVisibility(); | 1503 view_->ApplyCaretVisibility(); |
| 1540 | 1504 |
| 1541 client_->OnFocusChanged(focus_state_, reason); | 1505 client_->OnFocusChanged(focus_state_, reason); |
| 1542 } | 1506 } |
| OLD | NEW |