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
3 // found in the LICENSE file.
5 #include "chrome/browser/ui/views/autofill/autofill_popup_view_views.h"
7 #include "chrome/browser/ui/autofill/autofill_popup_controller.h"
8 #include "components/autofill/core/browser/popup_item_ids.h"
9 #include "components/autofill/core/browser/suggestion.h"
10 #include "ui/base/resource/resource_bundle.h"
11 #include "ui/events/keycodes/keyboard_codes.h"
12 #include "ui/gfx/canvas.h"
13 #include "ui/gfx/geometry/point.h"
14 #include "ui/gfx/geometry/rect.h"
15 #include "ui/gfx/image/image.h"
16 #include "ui/gfx/native_widget_types.h"
17 #include "ui/gfx/text_utils.h"
18 #include "ui/views/border.h"
19 #include "ui/views/widget/widget.h"
23 AutofillPopupViewViews::AutofillPopupViewViews(
24 AutofillPopupController
* controller
, views::FocusManager
* focus_manager
)
25 : AutofillPopupBaseView(controller
, focus_manager
),
26 controller_(controller
) {}
28 AutofillPopupViewViews::~AutofillPopupViewViews() {}
30 void AutofillPopupViewViews::Show() {
34 void AutofillPopupViewViews::Hide() {
35 // The controller is no longer valid after it hides us.
41 void AutofillPopupViewViews::UpdateBoundsAndRedrawPopup() {
42 DoUpdateBoundsAndRedrawPopup();
45 void AutofillPopupViewViews::OnPaint(gfx::Canvas
* canvas
) {
49 canvas
->DrawColor(kPopupBackground
);
50 OnPaintBorder(canvas
);
52 for (size_t i
= 0; i
< controller_
->GetLineCount(); ++i
) {
53 gfx::Rect line_rect
= controller_
->GetRowBounds(i
);
55 if (controller_
->GetSuggestionAt(i
).frontend_id
==
56 POPUP_ITEM_ID_SEPARATOR
) {
57 canvas
->FillRect(line_rect
, kItemTextColor
);
59 DrawAutofillEntry(canvas
, i
, line_rect
);
64 void AutofillPopupViewViews::InvalidateRow(size_t row
) {
65 SchedulePaintInRect(controller_
->GetRowBounds(row
));
68 void AutofillPopupViewViews::DrawAutofillEntry(gfx::Canvas
* canvas
,
70 const gfx::Rect
& entry_rect
) {
71 if (controller_
->selected_line() == index
)
72 canvas
->FillRect(entry_rect
, kHoveredBackgroundColor
);
74 const bool is_rtl
= controller_
->IsRTL();
75 const int value_text_width
=
76 gfx::GetStringWidth(controller_
->GetElidedValueAt(index
),
77 controller_
->GetValueFontListForRow(index
));
78 const int value_content_x
= is_rtl
?
79 entry_rect
.width() - value_text_width
- kEndPadding
: kEndPadding
;
81 canvas
->DrawStringRectWithFlags(
82 controller_
->GetElidedValueAt(index
),
83 controller_
->GetValueFontListForRow(index
),
84 controller_
->IsWarning(index
) ? kWarningTextColor
: kValueTextColor
,
85 gfx::Rect(value_content_x
,
89 gfx::Canvas::TEXT_ALIGN_CENTER
);
91 // Use this to figure out where all the other Autofill items should be placed.
92 int x_align_left
= is_rtl
? kEndPadding
: entry_rect
.width() - kEndPadding
;
94 // Draw the Autofill icon, if one exists
95 ui::ResourceBundle
& rb
= ui::ResourceBundle::GetSharedInstance();
96 int row_height
= controller_
->GetRowBounds(index
).height();
97 if (!controller_
->GetSuggestionAt(index
).icon
.empty()) {
98 int icon
= controller_
->GetIconResourceID(
99 controller_
->GetSuggestionAt(index
).icon
);
101 const gfx::ImageSkia
* image
= rb
.GetImageSkiaNamed(icon
);
102 int icon_y
= entry_rect
.y() + (row_height
- image
->height()) / 2;
104 x_align_left
+= is_rtl
? 0 : -image
->width();
106 canvas
->DrawImageInt(*image
, x_align_left
, icon_y
);
108 x_align_left
+= is_rtl
? image
->width() + kIconPadding
: -kIconPadding
;
111 // Draw the label text.
112 const int label_width
=
113 gfx::GetStringWidth(controller_
->GetElidedLabelAt(index
),
114 controller_
->GetLabelFontList());
116 x_align_left
-= label_width
;
118 canvas
->DrawStringRectWithFlags(
119 controller_
->GetElidedLabelAt(index
),
120 controller_
->GetLabelFontList(),
122 gfx::Rect(x_align_left
,
125 entry_rect
.height()),
126 gfx::Canvas::TEXT_ALIGN_CENTER
);
129 AutofillPopupView
* AutofillPopupView::Create(
130 AutofillPopupController
* controller
) {
131 views::Widget
* observing_widget
=
132 views::Widget::GetTopLevelWidgetForNativeView(
133 controller
->container_view());
135 // If the top level widget can't be found, cancel the popup since we can't
137 if (!observing_widget
)
140 return new AutofillPopupViewViews(controller
,
141 observing_widget
->GetFocusManager());
144 } // namespace autofill