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/ui/views/omnibox/omnibox_view_views.h" | 5 #include "chrome/browser/ui/views/omnibox/omnibox_view_views.h" |
6 | 6 |
7 #include <set> | 7 #include <set> |
8 | 8 |
9 #include "base/command_line.h" | 9 #include "base/command_line.h" |
10 #include "base/logging.h" | 10 #include "base/logging.h" |
(...skipping 259 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
270 return text(); | 270 return text(); |
271 } | 271 } |
272 | 272 |
273 void OmniboxViewViews::SetUserText(const base::string16& text, | 273 void OmniboxViewViews::SetUserText(const base::string16& text, |
274 const base::string16& display_text, | 274 const base::string16& display_text, |
275 bool update_popup) { | 275 bool update_popup) { |
276 saved_selection_for_focus_change_ = gfx::Range::InvalidRange(); | 276 saved_selection_for_focus_change_ = gfx::Range::InvalidRange(); |
277 OmniboxView::SetUserText(text, display_text, update_popup); | 277 OmniboxView::SetUserText(text, display_text, update_popup); |
278 } | 278 } |
279 | 279 |
280 void OmniboxViewViews::SetForcedQuery() { | 280 void OmniboxViewViews::EnterKeywordModeForDefaultSearchProvider() { |
281 const base::string16 current_text(text()); | 281 // Transition the user into keyword mode using their default search provider. |
282 const size_t start = current_text.find_first_not_of(base::kWhitespaceUTF16); | 282 // Select their query if they typed one. |
283 if (start == base::string16::npos || (current_text[start] != '?')) | 283 model()->EnterKeywordModeForDefaultSearchProvider( |
284 OmniboxView::SetUserText(base::ASCIIToUTF16("?")); | 284 KeywordModeEntryMethod::KEYBOARD_SHORTCUT); |
285 else | 285 SelectRange(gfx::Range(text().size(), 0)); |
286 SelectRange(gfx::Range(current_text.size(), start + 1)); | |
287 } | 286 } |
288 | 287 |
289 void OmniboxViewViews::GetSelectionBounds( | 288 void OmniboxViewViews::GetSelectionBounds( |
290 base::string16::size_type* start, | 289 base::string16::size_type* start, |
291 base::string16::size_type* end) const { | 290 base::string16::size_type* end) const { |
292 const gfx::Range range = GetSelectedRange(); | 291 const gfx::Range range = GetSelectedRange(); |
293 *start = static_cast<size_t>(range.start()); | 292 *start = static_cast<size_t>(range.start()); |
294 *end = static_cast<size_t>(range.end()); | 293 *end = static_cast<size_t>(range.end()); |
295 } | 294 } |
296 | 295 |
(...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
412 } | 411 } |
413 } | 412 } |
414 | 413 |
415 bool OmniboxViewViews::HandleEarlyTabActions(const ui::KeyEvent& event) { | 414 bool OmniboxViewViews::HandleEarlyTabActions(const ui::KeyEvent& event) { |
416 // This must run before accelerator handling invokes a focus change on tab. | 415 // This must run before accelerator handling invokes a focus change on tab. |
417 // Note the parallel with SkipDefaultKeyEventProcessing above. | 416 // Note the parallel with SkipDefaultKeyEventProcessing above. |
418 if (!views::FocusManager::IsTabTraversalKeyEvent(event)) | 417 if (!views::FocusManager::IsTabTraversalKeyEvent(event)) |
419 return false; | 418 return false; |
420 | 419 |
421 if (model()->is_keyword_hint() && !event.IsShiftDown()) | 420 if (model()->is_keyword_hint() && !event.IsShiftDown()) |
422 return model()->AcceptKeyword(ENTERED_KEYWORD_MODE_VIA_TAB); | 421 return model()->AcceptKeyword(KeywordModeEntryMethod::TAB); |
423 | 422 |
424 if (!model()->popup_model()->IsOpen()) | 423 if (!model()->popup_model()->IsOpen()) |
425 return false; | 424 return false; |
426 | 425 |
427 if (event.IsShiftDown() && | 426 if (event.IsShiftDown() && |
428 (model()->popup_model()->selected_line_state() == | 427 (model()->popup_model()->selected_line_state() == |
429 OmniboxPopupModel::KEYWORD)) | 428 OmniboxPopupModel::KEYWORD)) |
430 model()->ClearKeyword(); | 429 model()->ClearKeyword(); |
431 else | 430 else |
432 model()->OnUpOrDownKeyPressed(event.IsShiftDown() ? -1 : 1); | 431 model()->OnUpOrDownKeyPressed(event.IsShiftDown() ? -1 : 1); |
(...skipping 16 matching lines...) Expand all Loading... |
449 const gfx::Range range(caret_pos, caret_pos); | 448 const gfx::Range range(caret_pos, caret_pos); |
450 SetTextAndSelectedRange(text, range); | 449 SetTextAndSelectedRange(text, range); |
451 | 450 |
452 if (update_popup) | 451 if (update_popup) |
453 UpdatePopup(); | 452 UpdatePopup(); |
454 | 453 |
455 if (notify_text_changed) | 454 if (notify_text_changed) |
456 TextChanged(); | 455 TextChanged(); |
457 } | 456 } |
458 | 457 |
| 458 void OmniboxViewViews::SetCaretPos(size_t caret_pos) { |
| 459 SelectRange(gfx::Range(caret_pos, caret_pos)); |
| 460 } |
| 461 |
459 bool OmniboxViewViews::IsSelectAll() const { | 462 bool OmniboxViewViews::IsSelectAll() const { |
460 // TODO(oshima): IME support. | 463 // TODO(oshima): IME support. |
461 return text() == GetSelectedText(); | 464 return text() == GetSelectedText(); |
462 } | 465 } |
463 | 466 |
464 bool OmniboxViewViews::DeleteAtEndPressed() { | 467 bool OmniboxViewViews::DeleteAtEndPressed() { |
465 return delete_at_end_pressed_; | 468 return delete_at_end_pressed_; |
466 } | 469 } |
467 | 470 |
468 void OmniboxViewViews::UpdatePopup() { | 471 void OmniboxViewViews::UpdatePopup() { |
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
518 SelectRange(saved_temporary_selection_); | 521 SelectRange(saved_temporary_selection_); |
519 // We got here because the user hit the Escape key. We explicitly don't call | 522 // We got here because the user hit the Escape key. We explicitly don't call |
520 // TextChanged(), since OmniboxPopupModel::ResetToDefaultMatch() has already | 523 // TextChanged(), since OmniboxPopupModel::ResetToDefaultMatch() has already |
521 // been called by now, and it would've called TextChanged() if it was | 524 // been called by now, and it would've called TextChanged() if it was |
522 // warranted. | 525 // warranted. |
523 } | 526 } |
524 | 527 |
525 void OmniboxViewViews::OnBeforePossibleChange() { | 528 void OmniboxViewViews::OnBeforePossibleChange() { |
526 // Record our state. | 529 // Record our state. |
527 text_before_change_ = text(); | 530 text_before_change_ = text(); |
| 531 keyword_before_change_ = model()->keyword(); |
| 532 is_keyword_selected_before_change_ = model()->is_keyword_selected(); |
528 sel_before_change_ = GetSelectedRange(); | 533 sel_before_change_ = GetSelectedRange(); |
529 ime_composing_before_change_ = IsIMEComposing(); | 534 ime_composing_before_change_ = IsIMEComposing(); |
530 } | 535 } |
531 | 536 |
532 bool OmniboxViewViews::OnAfterPossibleChange(bool allow_keyword_ui_change) { | 537 bool OmniboxViewViews::OnAfterPossibleChange(bool allow_keyword_ui_change) { |
533 // See if the text or selection have changed since OnBeforePossibleChange(). | 538 // See if the text or selection have changed since OnBeforePossibleChange(). |
534 const base::string16 new_text = text(); | 539 const base::string16 new_text = text(); |
| 540 const base::string16 new_keyword = model()->keyword(); |
| 541 const bool new_is_keyword_selected = model()->is_keyword_selected(); |
535 const gfx::Range new_sel = GetSelectedRange(); | 542 const gfx::Range new_sel = GetSelectedRange(); |
536 const bool text_changed = (new_text != text_before_change_) || | 543 const bool text_changed = (new_text != text_before_change_) || |
537 (ime_composing_before_change_ != IsIMEComposing()); | 544 (ime_composing_before_change_ != IsIMEComposing()); |
| 545 const bool keyword_changed = |
| 546 (new_is_keyword_selected != is_keyword_selected_before_change_) || |
| 547 (new_is_keyword_selected && is_keyword_selected_before_change_ && |
| 548 new_keyword != keyword_before_change_); |
538 const bool selection_differs = | 549 const bool selection_differs = |
539 !((sel_before_change_.is_empty() && new_sel.is_empty()) || | 550 !((sel_before_change_.is_empty() && new_sel.is_empty()) || |
540 sel_before_change_.EqualsIgnoringDirection(new_sel)); | 551 sel_before_change_.EqualsIgnoringDirection(new_sel)); |
541 | 552 |
542 // When the user has deleted text, we don't allow inline autocomplete. Make | 553 // When the user has deleted text, we don't allow inline autocomplete. Make |
543 // sure to not flag cases like selecting part of the text and then pasting | 554 // sure to not flag cases like selecting part of the text and then pasting |
544 // (or typing) the prefix of that selection. (We detect these by making | 555 // (or typing) the prefix of that selection. (We detect these by making |
545 // sure the caret, which should be after any insertion, hasn't moved | 556 // sure the caret, which should be after any insertion, hasn't moved |
546 // forward of the old selection start.) | 557 // forward of the old selection start.) |
547 const bool just_deleted_text = | 558 const bool just_deleted_text = |
548 (text_before_change_.length() > new_text.length()) && | 559 (text_before_change_.length() > new_text.length()) && |
549 (new_sel.start() <= sel_before_change_.GetMin()); | 560 (new_sel.start() <= sel_before_change_.GetMin()); |
550 | 561 |
551 const bool something_changed = model()->OnAfterPossibleChange( | 562 const bool something_changed = model()->OnAfterPossibleChange( |
552 text_before_change_, new_text, new_sel.start(), new_sel.end(), | 563 text_before_change_, new_text, new_sel.start(), new_sel.end(), |
553 selection_differs, text_changed, just_deleted_text, | 564 selection_differs, text_changed, keyword_changed, just_deleted_text, |
554 allow_keyword_ui_change && !IsIMEComposing()); | 565 allow_keyword_ui_change && !IsIMEComposing()); |
555 | 566 |
556 // If only selection was changed, we don't need to call model()'s | 567 // If only selection was changed, we don't need to call model()'s |
557 // OnChanged() method, which is called in TextChanged(). | 568 // OnChanged() method, which is called in TextChanged(). |
558 // But we still need to call EmphasizeURLComponents() to make sure the text | 569 // But we still need to call EmphasizeURLComponents() to make sure the text |
559 // attributes are updated correctly. | 570 // attributes are updated correctly. |
560 if (something_changed && text_changed) | 571 if (something_changed && (text_changed || keyword_changed)) |
561 TextChanged(); | 572 TextChanged(); |
562 else if (selection_differs) | 573 else if (selection_differs) |
563 EmphasizeURLComponents(); | 574 EmphasizeURLComponents(); |
564 else if (delete_at_end_pressed_) | 575 else if (delete_at_end_pressed_) |
565 model()->OnChanged(); | 576 model()->OnChanged(); |
566 | 577 |
567 return something_changed; | 578 return something_changed; |
568 } | 579 } |
569 | 580 |
570 gfx::NativeView OmniboxViewViews::GetNativeView() const { | 581 gfx::NativeView OmniboxViewViews::GetNativeView() const { |
(...skipping 504 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1075 menu_contents->InsertItemWithStringIdAt( | 1086 menu_contents->InsertItemWithStringIdAt( |
1076 select_all_position + 1, IDS_SHOW_URL, IDS_SHOW_URL); | 1087 select_all_position + 1, IDS_SHOW_URL, IDS_SHOW_URL); |
1077 } | 1088 } |
1078 | 1089 |
1079 // Minor note: We use IDC_ for command id here while the underlying textfield | 1090 // Minor note: We use IDC_ for command id here while the underlying textfield |
1080 // is using IDS_ for all its command ids. This is because views cannot depend | 1091 // is using IDS_ for all its command ids. This is because views cannot depend |
1081 // on IDC_ for now. | 1092 // on IDC_ for now. |
1082 menu_contents->AddItemWithStringId(IDC_EDIT_SEARCH_ENGINES, | 1093 menu_contents->AddItemWithStringId(IDC_EDIT_SEARCH_ENGINES, |
1083 IDS_EDIT_SEARCH_ENGINES); | 1094 IDS_EDIT_SEARCH_ENGINES); |
1084 } | 1095 } |
OLD | NEW |