Chromium Code Reviews| 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 #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 611 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 622 bool just_deleted_text, | 622 bool just_deleted_text, |
| 623 bool allow_keyword_ui_change) { | 623 bool allow_keyword_ui_change) { |
| 624 // Update the paste state as appropriate: if we're just finishing a paste | 624 // Update the paste state as appropriate: if we're just finishing a paste |
| 625 // that replaced all the text, preserve that information; otherwise, if we've | 625 // that replaced all the text, preserve that information; otherwise, if we've |
| 626 // made some other edit, clear paste tracking. | 626 // made some other edit, clear paste tracking. |
| 627 if (paste_state_ == PASTING) | 627 if (paste_state_ == PASTING) |
| 628 paste_state_ = PASTED; | 628 paste_state_ = PASTED; |
| 629 else if (text_differs) | 629 else if (text_differs) |
| 630 paste_state_ = NONE; | 630 paste_state_ = NONE; |
| 631 | 631 |
| 632 const bool had_inline_autocomplete = !inline_autocomplete_text_.empty(); | |
|
Peter Kasting
2011/01/25 02:12:22
Nit: You can roll this back into the statement bel
James Su
2011/01/25 02:52:48
Done.
| |
| 633 | |
| 632 // Modifying the selection counts as accepting the autocompleted text. | 634 // Modifying the selection counts as accepting the autocompleted text. |
| 633 const bool user_text_changed = | 635 const bool user_text_changed = |
| 634 text_differs || (selection_differs && !inline_autocomplete_text_.empty()); | 636 text_differs || (selection_differs && had_inline_autocomplete); |
| 635 | 637 |
| 636 // If something has changed while the control key is down, prevent | 638 // If something has changed while the control key is down, prevent |
| 637 // "ctrl-enter" until the control key is released. When we do this, we need | 639 // "ctrl-enter" until the control key is released. When we do this, we need |
| 638 // to update the popup if it's open, since the desired_tld will have changed. | 640 // to update the popup if it's open, since the desired_tld will have changed. |
| 639 if ((text_differs || selection_differs) && | 641 if ((text_differs || selection_differs) && |
| 640 (control_key_state_ == DOWN_WITHOUT_CHANGE)) { | 642 (control_key_state_ == DOWN_WITHOUT_CHANGE)) { |
| 641 control_key_state_ = DOWN_WITH_CHANGE; | 643 control_key_state_ = DOWN_WITH_CHANGE; |
| 642 if (!text_differs && !popup_->IsOpen()) | 644 if (!text_differs && !popup_->IsOpen()) |
| 643 return false; // Don't open the popup for no reason. | 645 return false; // Don't open the popup for no reason. |
| 644 } else if (!user_text_changed) { | 646 } else if (!user_text_changed) { |
| 645 return false; | 647 return false; |
| 646 } | 648 } |
| 647 | 649 |
| 650 const std::wstring old_user_text = user_text_; | |
| 648 // If the user text has not changed, we do not want to change the model's | 651 // If the user text has not changed, we do not want to change the model's |
| 649 // state associated with the text. Otherwise, we can get surprising behavior | 652 // state associated with the text. Otherwise, we can get surprising behavior |
| 650 // where the autocompleted text unexpectedly reappears, e.g. crbug.com/55983 | 653 // where the autocompleted text unexpectedly reappears, e.g. crbug.com/55983 |
| 651 if (user_text_changed) { | 654 if (user_text_changed) { |
| 652 const std::wstring new_user_text = UserTextFromDisplayText(new_text); | 655 InternalSetUserText(UserTextFromDisplayText(new_text)); |
| 653 | |
| 654 // Try to accept the current keyword if the user only typed a space at the | |
| 655 // end of content. Model's state and popup will be updated when the keyword | |
| 656 // is accepted. So we just need to return false here. | |
| 657 if (allow_keyword_ui_change && !selection_differs && | |
| 658 MaybeAcceptKeywordBySpace(new_user_text)) | |
| 659 return false; | |
| 660 | |
| 661 InternalSetUserText(new_user_text); | |
| 662 has_temporary_text_ = false; | 656 has_temporary_text_ = false; |
| 663 | 657 |
| 664 // Track when the user has deleted text so we won't allow inline | 658 // Track when the user has deleted text so we won't allow inline |
| 665 // autocomplete. | 659 // autocomplete. |
| 666 just_deleted_text_ = just_deleted_text; | 660 just_deleted_text_ = just_deleted_text; |
| 667 } | 661 } |
| 668 | 662 |
| 669 view_->UpdatePopup(); | 663 view_->UpdatePopup(); |
| 664 | |
| 665 // Try to accept the current keyword if the user only typed a space at the | |
|
Peter Kasting
2011/01/25 02:12:22
Nit: This comment might now be more accurate as:
James Su
2011/01/25 02:52:48
Done.
| |
| 666 // end of content. Model's state and popup will be updated when the keyword | |
| 667 // is accepted. So we just need to return false here. | |
| 668 if (text_differs && allow_keyword_ui_change && !just_deleted_text && | |
|
Peter Kasting
2011/01/25 02:12:22
Nit: Even more condensed:
return !text_differs
James Su
2011/01/25 02:52:48
I'd prefer to keep the old one, which is more read
Peter Kasting
2011/01/25 04:25:48
Then how about this:
return !(text_differs && a
| |
| 669 MaybeAcceptKeywordBySpace(old_user_text, user_text_)) | |
| 670 return false; | |
| 671 | |
| 670 return true; | 672 return true; |
| 671 } | 673 } |
| 672 | 674 |
| 673 void AutocompleteEditModel::PopupBoundsChangedTo(const gfx::Rect& bounds) { | 675 void AutocompleteEditModel::PopupBoundsChangedTo(const gfx::Rect& bounds) { |
| 674 controller_->OnPopupBoundsChanged(bounds); | 676 controller_->OnPopupBoundsChanged(bounds); |
| 675 } | 677 } |
| 676 | 678 |
| 677 void AutocompleteEditModel::OnPopupClosed() { | 679 void AutocompleteEditModel::OnPopupClosed() { |
| 678 // Accepts the temporary text as the user text, because it makes little | 680 // Accepts the temporary text as the user text, because it makes little |
| 679 // sense to have temporary text when the popup is closed. | 681 // sense to have temporary text when the popup is closed. |
| (...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 775 const AutocompleteInput::Type type = AutocompleteInput::Parse( | 777 const AutocompleteInput::Type type = AutocompleteInput::Parse( |
| 776 UserTextFromDisplayText(text), std::wstring(), NULL, NULL, &parsed_url); | 778 UserTextFromDisplayText(text), std::wstring(), NULL, NULL, &parsed_url); |
| 777 if (type != AutocompleteInput::URL) | 779 if (type != AutocompleteInput::URL) |
| 778 return false; | 780 return false; |
| 779 | 781 |
| 780 *url = parsed_url; | 782 *url = parsed_url; |
| 781 return true; | 783 return true; |
| 782 } | 784 } |
| 783 | 785 |
| 784 bool AutocompleteEditModel::MaybeAcceptKeywordBySpace( | 786 bool AutocompleteEditModel::MaybeAcceptKeywordBySpace( |
| 787 const std::wstring& old_user_text, | |
| 785 const std::wstring& new_user_text) { | 788 const std::wstring& new_user_text) { |
| 786 return (paste_state_ == NONE) && is_keyword_hint_ && !keyword_.empty() && | 789 return (paste_state_ == NONE) && is_keyword_hint_ && !keyword_.empty() && |
| 787 inline_autocomplete_text_.empty() && !user_text_.empty() && | 790 inline_autocomplete_text_.empty() && |
| 788 (new_user_text.length() == user_text_.length() + 1) && | 791 !old_user_text.empty() && new_user_text.length() >= 2 && |
|
Peter Kasting
2011/01/25 02:12:22
Nit: "!old_user_text.empty()" is unnecessary given
James Su
2011/01/25 02:52:48
Done.
| |
| 789 !new_user_text.compare(0, user_text_.length(), user_text_) && | 792 (old_user_text.length() + 1 >= new_user_text.length()) && |
| 790 IsSpaceCharForAcceptingKeyword(new_user_text[user_text_.length()]) && | 793 !new_user_text.compare(0, new_user_text.length() - 1, old_user_text, |
| 791 !IsWhitespace(user_text_[user_text_.length() - 1]) && | 794 0, new_user_text.length() - 1) && |
| 795 IsSpaceCharForAcceptingKeyword(new_user_text[new_user_text.length() - 1]) && | |
|
Peter Kasting
2011/01/25 02:12:22
Nit: 80 columns.
Also, I think it'll be a littler
James Su
2011/01/25 02:52:48
Done.
| |
| 796 !IsWhitespace(new_user_text[new_user_text.length() - 2]) && | |
| 792 AcceptKeyword(); | 797 AcceptKeyword(); |
| 793 } | 798 } |
| 794 | 799 |
| 795 // static | 800 // static |
| 796 bool AutocompleteEditModel::IsSpaceCharForAcceptingKeyword(wchar_t c) { | 801 bool AutocompleteEditModel::IsSpaceCharForAcceptingKeyword(wchar_t c) { |
| 797 switch (c) { | 802 switch (c) { |
| 798 case 0x0020: // Space | 803 case 0x0020: // Space |
| 799 case 0x3000: // Ideographic Space | 804 case 0x3000: // Ideographic Space |
| 800 return true; | 805 return true; |
| 801 default: | 806 default: |
| 802 return false; | 807 return false; |
| 803 } | 808 } |
| 804 } | 809 } |
| OLD | NEW |