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

Side by Side Diff: chrome/browser/ui/views/autocomplete/autocomplete_popup_contents_view.cc

Issue 9417032: Enabled pressing TAB to traverse through the Omnibox results (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 8 years, 10 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 | Annotate | Revision Log
OLDNEW
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/autocomplete/autocomplete_popup_contents_view. h" 5 #include "chrome/browser/ui/views/autocomplete/autocomplete_popup_contents_view. h"
6 6
7 #if defined(OS_WIN) 7 #if defined(OS_WIN)
8 #include <commctrl.h> 8 #include <commctrl.h>
9 #include <dwmapi.h> 9 #include <dwmapi.h>
10 #include <objidl.h> 10 #include <objidl.h>
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
46 #endif 46 #endif
47 #endif 47 #endif
48 #if defined(USE_AURA) 48 #if defined(USE_AURA)
49 #include "ash/wm/window_animations.h" 49 #include "ash/wm/window_animations.h"
50 #endif 50 #endif
51 51
52 namespace { 52 namespace {
53 53
54 const SkAlpha kGlassPopupAlpha = 240; 54 const SkAlpha kGlassPopupAlpha = 240;
55 const SkAlpha kOpaquePopupAlpha = 255; 55 const SkAlpha kOpaquePopupAlpha = 255;
56
56 // The size delta between the font used for the edit and the result rows. Passed 57 // The size delta between the font used for the edit and the result rows. Passed
57 // to gfx::Font::DeriveFont. 58 // to gfx::Font::DeriveFont.
58 #if defined(OS_CHROMEOS) 59 #if defined(OS_CHROMEOS)
59 // Don't adjust the size on Chrome OS (http://crbug.com/61433). 60 // Don't adjust the size on Chrome OS (http://crbug.com/61433).
60 const int kEditFontAdjust = 0; 61 const int kEditFontAdjust = 0;
61 #else 62 #else
62 const int kEditFontAdjust = -1; 63 const int kEditFontAdjust = -1;
63 #endif 64 #endif
64 65
65 // Horizontal padding between the buttons on the opt in promo. 66 // Horizontal padding between the buttons on the opt in promo.
(...skipping 164 matching lines...) Expand 10 before | Expand all | Expand 10 after
230 ALLOW_THIS_IN_INITIALIZER_LIST(size_animation_(this)) { 231 ALLOW_THIS_IN_INITIALIZER_LIST(size_animation_(this)) {
231 // The following little dance is required because set_border() requires a 232 // The following little dance is required because set_border() requires a
232 // pointer to a non-const object. 233 // pointer to a non-const object.
233 views::BubbleBorder* bubble_border = 234 views::BubbleBorder* bubble_border =
234 new views::BubbleBorder(views::BubbleBorder::NONE, 235 new views::BubbleBorder(views::BubbleBorder::NONE,
235 views::BubbleBorder::NO_SHADOW); 236 views::BubbleBorder::NO_SHADOW);
236 bubble_border_ = bubble_border; 237 bubble_border_ = bubble_border;
237 set_border(bubble_border); 238 set_border(bubble_border);
238 // The contents is owned by the LocationBarView. 239 // The contents is owned by the LocationBarView.
239 set_parent_owned(false); 240 set_parent_owned(false);
241
242 for (size_t i = 0; i < AutocompleteResult::kMaxMatches; ++i) {
243 AutocompleteResultView* result_view =
244 CreateResultView(this, i, result_font_, result_bold_font_);
245 result_view->SetVisible(false);
246 AddChildViewAt(result_view, static_cast<int>(i));
247 }
240 } 248 }
241 249
242 AutocompletePopupContentsView::~AutocompletePopupContentsView() { 250 AutocompletePopupContentsView::~AutocompletePopupContentsView() {
243 // We don't need to do anything with |popup_| here. The OS either has already 251 // We don't need to do anything with |popup_| here. The OS either has already
244 // closed the window, in which case it's been deleted, or it will soon, in 252 // closed the window, in which case it's been deleted, or it will soon, in
245 // which case there's nothing we need to do. 253 // which case there's nothing we need to do.
246 } 254 }
247 255
248 gfx::Rect AutocompletePopupContentsView::GetPopupBounds() const { 256 gfx::Rect AutocompletePopupContentsView::GetPopupBounds() const {
249 if (!size_animation_.is_animating()) 257 if (!size_animation_.is_animating())
(...skipping 25 matching lines...) Expand all
275 } 283 }
276 284
277 //////////////////////////////////////////////////////////////////////////////// 285 ////////////////////////////////////////////////////////////////////////////////
278 // AutocompletePopupContentsView, AutocompletePopupView overrides: 286 // AutocompletePopupContentsView, AutocompletePopupView overrides:
279 287
280 bool AutocompletePopupContentsView::IsOpen() const { 288 bool AutocompletePopupContentsView::IsOpen() const {
281 return (popup_ != NULL); 289 return (popup_ != NULL);
282 } 290 }
283 291
284 void AutocompletePopupContentsView::InvalidateLine(size_t line) { 292 void AutocompletePopupContentsView::InvalidateLine(size_t line) {
285 child_at(static_cast<int>(line))->SchedulePaint(); 293 AutocompleteResultView* result = static_cast<AutocompleteResultView*>(
294 child_at(static_cast<int>(line)));
295 result->Invalidate();
296
297 if (HasMatchAt(line) && GetMatchAtIndex(line).associated_keyword.get()) {
298 result->ShowKeyword(IsSelectedIndex(line) &&
299 model_->selected_line_state() == AutocompletePopupModel::KEYWORD);
300 }
286 } 301 }
287 302
288 void AutocompletePopupContentsView::UpdatePopupAppearance() { 303 void AutocompletePopupContentsView::UpdatePopupAppearance() {
289 if (model_->result().empty()) { 304 if (model_->result().empty()) {
290 // No matches, close any existing popup. 305 // No matches, close any existing popup.
291 if (popup_ != NULL) { 306 if (popup_ != NULL) {
292 size_animation_.Stop(); 307 size_animation_.Stop();
308
293 // NOTE: Do NOT use CloseNow() here, as we may be deep in a callstack 309 // NOTE: Do NOT use CloseNow() here, as we may be deep in a callstack
294 // triggered by the popup receiving a message (e.g. LBUTTONUP), and 310 // triggered by the popup receiving a message (e.g. LBUTTONUP), and
295 // destroying the popup would cause us to read garbage when we unwind back 311 // destroying the popup would cause us to read garbage when we unwind back
296 // to that level. 312 // to that level.
297 popup_->Close(); // This will eventually delete the popup. 313 popup_->Close(); // This will eventually delete the popup.
298 popup_.reset(); 314 popup_.reset();
299 } 315 }
300 return; 316 return;
301 } 317 }
302 318
303 // Update the match cached by each row, in the process of doing so make sure 319 // Update the match cached by each row, in the process of doing so make sure
304 // we have enough row views. 320 // we have enough row views.
305 size_t child_rv_count = child_count(); 321 size_t child_rv_count = child_count();
306 if (opt_in_view_) { 322 if (opt_in_view_) {
307 DCHECK_GT(child_rv_count, 0u); 323 DCHECK_GT(child_rv_count, 0u);
308 child_rv_count--; 324 child_rv_count--;
309 } 325 }
310 for (size_t i = 0; i < model_->result().size(); ++i) { 326 const size_t result_size = model_->result().size();
311 AutocompleteResultView* result_view; 327 for (size_t i = 0; i < result_size; ++i) {
312 if (i >= child_rv_count) { 328 AutocompleteResultView* view = static_cast<AutocompleteResultView*>(
313 result_view = 329 child_at(i));
314 CreateResultView(this, i, result_font_, result_bold_font_); 330 view->SetMatch(GetMatchAtIndex(i));
315 AddChildViewAt(result_view, static_cast<int>(i)); 331 view->SetVisible(true);
316 } else {
317 result_view = static_cast<AutocompleteResultView*>(child_at(i));
318 result_view->SetVisible(true);
319 }
320 result_view->SetMatch(GetMatchAtIndex(i));
321 } 332 }
322 for (size_t i = model_->result().size(); i < child_rv_count; ++i) 333 for (size_t i = result_size; i < child_rv_count; ++i)
323 child_at(i)->SetVisible(false); 334 child_at(i)->SetVisible(false);
324 335
325 PromoCounter* counter = profile_->GetInstantPromoCounter(); 336 PromoCounter* counter = profile_->GetInstantPromoCounter();
326 if (!opt_in_view_ && counter && counter->ShouldShow(base::Time::Now())) { 337 if (!opt_in_view_ && counter && counter->ShouldShow(base::Time::Now())) {
327 opt_in_view_ = new InstantOptInView(this, result_bold_font_, result_font_); 338 opt_in_view_ = new InstantOptInView(this, result_bold_font_, result_font_);
328 AddChildView(opt_in_view_); 339 AddChildView(opt_in_view_);
329 } else if (opt_in_view_ && (!counter || 340 } else if (opt_in_view_ && (!counter ||
330 !counter->ShouldShow(base::Time::Now()))) { 341 !counter->ShouldShow(base::Time::Now()))) {
331 delete opt_in_view_; 342 delete opt_in_view_;
332 opt_in_view_ = NULL; 343 opt_in_view_ = NULL;
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after
390 } 401 }
391 402
392 void AutocompletePopupContentsView::OnDragCanceled() { 403 void AutocompletePopupContentsView::OnDragCanceled() {
393 ignore_mouse_drag_ = true; 404 ignore_mouse_drag_ = true;
394 } 405 }
395 406
396 //////////////////////////////////////////////////////////////////////////////// 407 ////////////////////////////////////////////////////////////////////////////////
397 // AutocompletePopupContentsView, AutocompleteResultViewModel implementation: 408 // AutocompletePopupContentsView, AutocompleteResultViewModel implementation:
398 409
399 bool AutocompletePopupContentsView::IsSelectedIndex(size_t index) const { 410 bool AutocompletePopupContentsView::IsSelectedIndex(size_t index) const {
400 return HasMatchAt(index) ? index == model_->selected_line() : false; 411 return index == model_->selected_line();
401 } 412 }
402 413
403 bool AutocompletePopupContentsView::IsHoveredIndex(size_t index) const { 414 bool AutocompletePopupContentsView::IsHoveredIndex(size_t index) const {
404 return HasMatchAt(index) ? index == model_->hovered_line() : false; 415 return index == model_->hovered_line();
405 } 416 }
406 417
407 const SkBitmap* AutocompletePopupContentsView::GetIconIfExtensionMatch( 418 const SkBitmap* AutocompletePopupContentsView::GetIconIfExtensionMatch(
408 size_t index) const { 419 size_t index) const {
409 if (!HasMatchAt(index)) 420 if (!HasMatchAt(index))
410 return NULL; 421 return NULL;
411 return model_->GetIconIfExtensionMatch(GetMatchAtIndex(index)); 422 return model_->GetIconIfExtensionMatch(GetMatchAtIndex(index));
412 } 423 }
413 424
414 //////////////////////////////////////////////////////////////////////////////// 425 ////////////////////////////////////////////////////////////////////////////////
(...skipping 15 matching lines...) Expand all
430 // Size our children to the available content area. 441 // Size our children to the available content area.
431 LayoutChildren(); 442 LayoutChildren();
432 443
433 // We need to manually schedule a paint here since we are a layered window and 444 // We need to manually schedule a paint here since we are a layered window and
434 // won't implicitly require painting until we ask for one. 445 // won't implicitly require painting until we ask for one.
435 SchedulePaint(); 446 SchedulePaint();
436 } 447 }
437 448
438 views::View* AutocompletePopupContentsView::GetEventHandlerForPoint( 449 views::View* AutocompletePopupContentsView::GetEventHandlerForPoint(
439 const gfx::Point& point) { 450 const gfx::Point& point) {
440 // If there is no opt in view, then we want all mouse events. Otherwise let 451 // If there is no opt in view then we want all mouse events. Otherwise, let
441 // any descendants of the opt-in view get mouse events. 452 // any descendants of the opt-in view get mouse events.
442 if (!opt_in_view_) 453 if (!opt_in_view_)
443 return this; 454 return this;
444 455
445 views::View* child = views::View::GetEventHandlerForPoint(point); 456 views::View* child = views::View::GetEventHandlerForPoint(point);
446 views::View* ancestor = child; 457 views::View* ancestor = child;
447 while (ancestor && ancestor != opt_in_view_) 458 while (ancestor && ancestor != opt_in_view_)
448 ancestor = ancestor->parent(); 459 ancestor = ancestor->parent();
449 return ancestor ? child : this; 460 return ancestor ? child : this;
450 } 461 }
(...skipping 190 matching lines...) Expand 10 before | Expand all | Expand 10 after
641 void AutocompletePopupContentsView::OpenIndex( 652 void AutocompletePopupContentsView::OpenIndex(
642 size_t index, 653 size_t index,
643 WindowOpenDisposition disposition) { 654 WindowOpenDisposition disposition) {
644 if (!HasMatchAt(index)) 655 if (!HasMatchAt(index))
645 return; 656 return;
646 657
647 // OpenMatch() may close the popup, which will clear the result set and, by 658 // OpenMatch() may close the popup, which will clear the result set and, by
648 // extension, |match| and its contents. So copy the relevant match out to 659 // extension, |match| and its contents. So copy the relevant match out to
649 // make sure it stays alive until the call completes. 660 // make sure it stays alive until the call completes.
650 AutocompleteMatch match = model_->result().match_at(index); 661 AutocompleteMatch match = model_->result().match_at(index);
651 string16 keyword;
652 const bool is_keyword_hint = model_->GetKeywordForMatch(match, &keyword);
653 omnibox_view_->OpenMatch(match, disposition, GURL(), index, 662 omnibox_view_->OpenMatch(match, disposition, GURL(), index,
654 is_keyword_hint ? string16() : keyword); 663 match.keyword);
655 } 664 }
656 665
657 size_t AutocompletePopupContentsView::GetIndexForPoint( 666 size_t AutocompletePopupContentsView::GetIndexForPoint(
658 const gfx::Point& point) { 667 const gfx::Point& point) {
659 if (!HitTest(point)) 668 if (!HitTest(point))
660 return AutocompletePopupModel::kNoMatch; 669 return AutocompletePopupModel::kNoMatch;
661 670
662 int nb_match = model_->result().size(); 671 int nb_match = model_->result().size();
663 DCHECK(nb_match <= child_count()); 672 DCHECK(nb_match <= child_count());
664 for (int i = 0; i < nb_match; ++i) { 673 for (int i = 0; i < nb_match; ++i) {
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
699 opt_in_view_ = NULL; 708 opt_in_view_ = NULL;
700 PromoCounter* counter = profile_->GetInstantPromoCounter(); 709 PromoCounter* counter = profile_->GetInstantPromoCounter();
701 DCHECK(counter); 710 DCHECK(counter);
702 counter->Hide(); 711 counter->Hide();
703 if (opt_in) { 712 if (opt_in) {
704 browser::ShowInstantConfirmDialogIfNecessary( 713 browser::ShowInstantConfirmDialogIfNecessary(
705 location_bar_->GetWidget()->GetNativeWindow(), profile_); 714 location_bar_->GetWidget()->GetNativeWindow(), profile_);
706 } 715 }
707 UpdatePopupAppearance(); 716 UpdatePopupAppearance();
708 } 717 }
OLDNEW
« no previous file with comments | « chrome/browser/ui/omnibox/omnibox_view_browsertest.cc ('k') | chrome/browser/ui/views/autocomplete/autocomplete_result_view.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698