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 #include "chrome/browser/autocomplete/autocomplete_edit.h" | 5 #include "chrome/browser/autocomplete/autocomplete_edit.h" |
6 | 6 |
7 #include <string> | 7 #include <string> |
8 | 8 |
9 #include "base/basictypes.h" | 9 #include "base/basictypes.h" |
10 #include "base/metrics/histogram.h" | 10 #include "base/metrics/histogram.h" |
(...skipping 395 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
406 has_focus_ ? permanent_text_.length() : 0); | 406 has_focus_ ? permanent_text_.length() : 0); |
407 NetworkActionPredictor* network_action_predictor = | 407 NetworkActionPredictor* network_action_predictor = |
408 NetworkActionPredictorFactory::GetForProfile(profile_); | 408 NetworkActionPredictorFactory::GetForProfile(profile_); |
409 if (network_action_predictor) | 409 if (network_action_predictor) |
410 network_action_predictor->ClearTransitionalMatches(); | 410 network_action_predictor->ClearTransitionalMatches(); |
411 } | 411 } |
412 | 412 |
413 void AutocompleteEditModel::StartAutocomplete( | 413 void AutocompleteEditModel::StartAutocomplete( |
414 bool has_selected_text, | 414 bool has_selected_text, |
415 bool prevent_inline_autocomplete) const { | 415 bool prevent_inline_autocomplete) const { |
| 416 ClearPopupKeywordMode(); |
| 417 |
416 bool keyword_is_selected = KeywordIsSelected(); | 418 bool keyword_is_selected = KeywordIsSelected(); |
417 popup_->SetHoveredLine(AutocompletePopupModel::kNoMatch); | 419 popup_->SetHoveredLine(AutocompletePopupModel::kNoMatch); |
418 // We don't explicitly clear AutocompletePopupModel::manually_selected_match, | 420 // We don't explicitly clear AutocompletePopupModel::manually_selected_match, |
419 // as Start ends up invoking AutocompletePopupModel::OnResultChanged which | 421 // as Start ends up invoking AutocompletePopupModel::OnResultChanged which |
420 // clears it. | 422 // clears it. |
421 autocomplete_controller_->Start( | 423 autocomplete_controller_->Start( |
422 user_text_, GetDesiredTLD(), | 424 user_text_, GetDesiredTLD(), |
423 prevent_inline_autocomplete || just_deleted_text_ || | 425 prevent_inline_autocomplete || just_deleted_text_ || |
424 (has_selected_text && inline_autocomplete_text_.empty()) || | 426 (has_selected_text && inline_autocomplete_text_.empty()) || |
425 (paste_state_ != NONE), keyword_is_selected, | 427 (paste_state_ != NONE), keyword_is_selected, |
(...skipping 177 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
603 | 605 |
604 InstantController* instant = controller_->GetInstant(); | 606 InstantController* instant = controller_->GetInstant(); |
605 if (instant && !popup_->IsOpen()) | 607 if (instant && !popup_->IsOpen()) |
606 instant->DestroyPreviewContents(); | 608 instant->DestroyPreviewContents(); |
607 in_revert_ = false; | 609 in_revert_ = false; |
608 } | 610 } |
609 | 611 |
610 bool AutocompleteEditModel::AcceptKeyword() { | 612 bool AutocompleteEditModel::AcceptKeyword() { |
611 DCHECK(is_keyword_hint_ && !keyword_.empty()); | 613 DCHECK(is_keyword_hint_ && !keyword_.empty()); |
612 | 614 |
613 view_->OnBeforePossibleChange(); | 615 autocomplete_controller_->Stop(false); |
614 view_->SetWindowTextAndCaretPos(string16(), 0); | |
615 is_keyword_hint_ = false; | 616 is_keyword_hint_ = false; |
616 view_->OnAfterPossibleChange(); | 617 |
617 just_deleted_text_ = false; // OnAfterPossibleChange() erroneously sets this | 618 if (popup_->IsOpen()) |
618 // since the edit contents have disappeared. It | 619 popup_->SetSelectedLineState(AutocompletePopupModel::KEYWORD); |
619 // doesn't really matter, but we clear it to be | 620 |
620 // consistent. | 621 string16 display_text = autocomplete_controller_->keyword_provider()-> |
| 622 SplitReplacementStringFromInput(user_text_, true); |
| 623 view_->SetUserText(string16(), display_text, false); |
| 624 |
621 content::RecordAction(UserMetricsAction("AcceptedKeywordHint")); | 625 content::RecordAction(UserMetricsAction("AcceptedKeywordHint")); |
622 return true; | 626 return true; |
623 } | 627 } |
624 | 628 |
625 void AutocompleteEditModel::ClearKeyword(const string16& visible_text) { | 629 void AutocompleteEditModel::ClearKeyword(const string16& visible_text) { |
626 view_->OnBeforePossibleChange(); | 630 autocomplete_controller_->Stop(false); |
| 631 ClearPopupKeywordMode(); |
| 632 |
627 const string16 window_text(keyword_ + visible_text); | 633 const string16 window_text(keyword_ + visible_text); |
628 view_->SetWindowTextAndCaretPos(window_text.c_str(), keyword_.length()); | 634 |
629 keyword_.clear(); | 635 // Only reset the result if the edit text has changed since the |
630 is_keyword_hint_ = false; | 636 // keyword was accepted. |
631 view_->OnAfterPossibleChange(); | 637 if (just_deleted_text_ || !visible_text.empty()) { |
632 just_deleted_text_ = true; // OnAfterPossibleChange() fails to clear this | 638 view_->OnBeforePossibleChange(); |
633 // since the edit contents have actually grown | 639 view_->SetWindowTextAndCaretPos(window_text.c_str(), keyword_.length()); |
634 // longer. | 640 keyword_.clear(); |
| 641 is_keyword_hint_ = false; |
| 642 view_->OnAfterPossibleChange(); |
| 643 just_deleted_text_ = true; // OnAfterPossibleChange() fails to clear this |
| 644 // since the edit contents have actually grown |
| 645 // longer. |
| 646 } else { |
| 647 view_->SetUserText(window_text, window_text, false); |
| 648 is_keyword_hint_ = true; |
| 649 OnChanged(); |
| 650 } |
635 } | 651 } |
636 | 652 |
637 const AutocompleteResult& AutocompleteEditModel::result() const { | 653 const AutocompleteResult& AutocompleteEditModel::result() const { |
638 return autocomplete_controller_->result(); | 654 return autocomplete_controller_->result(); |
639 } | 655 } |
640 | 656 |
641 void AutocompleteEditModel::OnSetFocus(bool control_down) { | 657 void AutocompleteEditModel::OnSetFocus(bool control_down) { |
642 has_focus_ = true; | 658 has_focus_ = true; |
643 control_key_state_ = control_down ? DOWN_WITHOUT_CHANGE : UP; | 659 control_key_state_ = control_down ? DOWN_WITHOUT_CHANGE : UP; |
644 | 660 |
(...skipping 242 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
887 match->fill_into_edit.substr(match->inline_autocomplete_offset); | 903 match->fill_into_edit.substr(match->inline_autocomplete_offset); |
888 } | 904 } |
889 | 905 |
890 if (!prerender::IsOmniboxEnabled(profile_)) | 906 if (!prerender::IsOmniboxEnabled(profile_)) |
891 DoPreconnect(*match); | 907 DoPreconnect(*match); |
892 | 908 |
893 // We could prefetch the alternate nav URL, if any, but because there | 909 // We could prefetch the alternate nav URL, if any, but because there |
894 // can be many of these as a user types an initial series of characters, | 910 // can be many of these as a user types an initial series of characters, |
895 // the OS DNS cache could suffer eviction problems for minimal gain. | 911 // the OS DNS cache could suffer eviction problems for minimal gain. |
896 | 912 |
897 is_keyword_hint = popup_->GetKeywordForMatch(*match, &keyword); | 913 is_keyword_hint = match->GetKeyword(&keyword); |
898 } | 914 } |
| 915 |
899 popup_->OnResultChanged(); | 916 popup_->OnResultChanged(); |
900 OnPopupDataChanged(inline_autocomplete_text, NULL, keyword, | 917 OnPopupDataChanged(inline_autocomplete_text, NULL, keyword, |
901 is_keyword_hint); | 918 is_keyword_hint); |
902 } else { | 919 } else { |
903 popup_->OnResultChanged(); | 920 popup_->OnResultChanged(); |
904 } | 921 } |
905 | 922 |
906 if (popup_->IsOpen()) { | 923 if (popup_->IsOpen()) { |
907 PopupBoundsChangedTo(popup_->view()->GetTargetBounds()); | 924 PopupBoundsChangedTo(popup_->view()->GetTargetBounds()); |
908 } else if (was_open) { | 925 } else if (was_open) { |
(...skipping 12 matching lines...) Expand all Loading... |
921 void AutocompleteEditModel::InternalSetUserText(const string16& text) { | 938 void AutocompleteEditModel::InternalSetUserText(const string16& text) { |
922 user_text_ = text; | 939 user_text_ = text; |
923 just_deleted_text_ = false; | 940 just_deleted_text_ = false; |
924 inline_autocomplete_text_.clear(); | 941 inline_autocomplete_text_.clear(); |
925 } | 942 } |
926 | 943 |
927 bool AutocompleteEditModel::KeywordIsSelected() const { | 944 bool AutocompleteEditModel::KeywordIsSelected() const { |
928 return !is_keyword_hint_ && !keyword_.empty(); | 945 return !is_keyword_hint_ && !keyword_.empty(); |
929 } | 946 } |
930 | 947 |
| 948 void AutocompleteEditModel::ClearPopupKeywordMode() const { |
| 949 if (popup_->IsOpen() && |
| 950 popup_->selected_line_state() == AutocompletePopupModel::KEYWORD) |
| 951 popup_->SetSelectedLineState(AutocompletePopupModel::NORMAL); |
| 952 } |
| 953 |
931 string16 AutocompleteEditModel::DisplayTextFromUserText( | 954 string16 AutocompleteEditModel::DisplayTextFromUserText( |
932 const string16& text) const { | 955 const string16& text) const { |
933 return KeywordIsSelected() ? | 956 return KeywordIsSelected() ? |
934 KeywordProvider::SplitReplacementStringFromInput(text, false) : text; | 957 KeywordProvider::SplitReplacementStringFromInput(text, false) : text; |
935 } | 958 } |
936 | 959 |
937 string16 AutocompleteEditModel::UserTextFromDisplayText( | 960 string16 AutocompleteEditModel::UserTextFromDisplayText( |
938 const string16& text) const { | 961 const string16& text) const { |
939 return KeywordIsSelected() ? (keyword_ + char16(' ') + text) : text; | 962 return KeywordIsSelected() ? (keyword_ + char16(' ') + text) : text; |
940 } | 963 } |
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1020 old_user_text.length() - caret_position + 1)) { | 1043 old_user_text.length() - caret_position + 1)) { |
1021 return false; | 1044 return false; |
1022 } | 1045 } |
1023 | 1046 |
1024 // Then check if the text before the inserted space matches a keyword. | 1047 // Then check if the text before the inserted space matches a keyword. |
1025 string16 keyword; | 1048 string16 keyword; |
1026 TrimWhitespace(new_user_text.substr(0, caret_position - 1), | 1049 TrimWhitespace(new_user_text.substr(0, caret_position - 1), |
1027 TRIM_LEADING, &keyword); | 1050 TRIM_LEADING, &keyword); |
1028 | 1051 |
1029 // Only allow exact keyword match if |keyword| represents a keyword hint. | 1052 // Only allow exact keyword match if |keyword| represents a keyword hint. |
1030 return keyword.length() && popup_->GetKeywordForText(keyword, &keyword); | 1053 return keyword.length() && |
| 1054 !autocomplete_controller_->keyword_provider()-> |
| 1055 GetKeywordForText(keyword).empty(); |
1031 } | 1056 } |
1032 | 1057 |
1033 bool AutocompleteEditModel::DoInstant(const AutocompleteMatch& match, | 1058 bool AutocompleteEditModel::DoInstant(const AutocompleteMatch& match, |
1034 string16* suggested_text) { | 1059 string16* suggested_text) { |
1035 DCHECK(suggested_text); | 1060 DCHECK(suggested_text); |
1036 | 1061 |
1037 if (in_revert_) | 1062 if (in_revert_) |
1038 return false; | 1063 return false; |
1039 | 1064 |
1040 InstantController* instant = controller_->GetInstant(); | 1065 InstantController* instant = controller_->GetInstant(); |
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1096 // static | 1121 // static |
1097 bool AutocompleteEditModel::IsSpaceCharForAcceptingKeyword(wchar_t c) { | 1122 bool AutocompleteEditModel::IsSpaceCharForAcceptingKeyword(wchar_t c) { |
1098 switch (c) { | 1123 switch (c) { |
1099 case 0x0020: // Space | 1124 case 0x0020: // Space |
1100 case 0x3000: // Ideographic Space | 1125 case 0x3000: // Ideographic Space |
1101 return true; | 1126 return true; |
1102 default: | 1127 default: |
1103 return false; | 1128 return false; |
1104 } | 1129 } |
1105 } | 1130 } |
OLD | NEW |