Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 1 | // Copyright 2013 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. |
| 4 | |
| 5 | #include "chrome/browser/ui/views/autofill/autocheckout_bubble_views.h" |
| 6 | |
| 7 | #include "chrome/browser/ui/autofill/autocheckout_bubble.h" |
| 8 | #include "chrome/browser/ui/autofill/autocheckout_bubble_controller.h" |
Torne (Richard Coles) | 7d4cd47 | 2013-06-19 11:58:07 +0100 | [diff] [blame] | 9 | #include "ui/gfx/image/image.h" |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 10 | #include "ui/gfx/rect.h" |
Torne (Richard Coles) | c2e0dbd | 2013-05-09 18:35:53 +0100 | [diff] [blame] | 11 | #include "ui/views/bubble/bubble_border.h" |
Torne (Richard Coles) | 7d4cd47 | 2013-06-19 11:58:07 +0100 | [diff] [blame] | 12 | #include "ui/views/controls/button/image_button.h" |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 13 | #include "ui/views/controls/button/label_button.h" |
| 14 | #include "ui/views/controls/label.h" |
| 15 | #include "ui/views/layout/grid_layout.h" |
| 16 | #include "ui/views/layout/layout_constants.h" |
| 17 | #include "ui/views/widget/widget.h" |
| 18 | |
Ben Murdoch | bb1529c | 2013-08-08 10:24:53 +0100 | [diff] [blame^] | 19 | #if defined(USE_AURA) |
| 20 | #include "ui/aura/window.h" |
| 21 | #endif |
| 22 | |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 23 | namespace autofill { |
| 24 | |
| 25 | AutocheckoutBubbleViews::AutocheckoutBubbleViews( |
Torne (Richard Coles) | c2e0dbd | 2013-05-09 18:35:53 +0100 | [diff] [blame] | 26 | scoped_ptr<AutocheckoutBubbleController> controller, |
| 27 | views::View* anchor_view) |
| 28 | : views::BubbleDelegateView(anchor_view, views::BubbleBorder::TOP_LEFT), |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 29 | controller_(controller.Pass()), |
| 30 | ok_button_(NULL), |
| 31 | cancel_button_(NULL) { |
Torne (Richard Coles) | c2e0dbd | 2013-05-09 18:35:53 +0100 | [diff] [blame] | 32 | set_parent_window(controller_->native_window()); |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 33 | controller_->BubbleCreated(); |
| 34 | } |
| 35 | |
| 36 | AutocheckoutBubbleViews::~AutocheckoutBubbleViews() { |
| 37 | controller_->BubbleDestroyed(); |
| 38 | } |
| 39 | |
| 40 | void AutocheckoutBubbleViews::ShowBubble() { |
| 41 | StartFade(true); |
| 42 | } |
| 43 | |
| 44 | void AutocheckoutBubbleViews::HideBubble() { |
| 45 | StartFade(false); |
| 46 | } |
| 47 | |
| 48 | void AutocheckoutBubbleViews::Init() { |
| 49 | views::GridLayout* layout = new views::GridLayout(this); |
| 50 | SetLayoutManager(layout); |
| 51 | |
| 52 | // Add the message label to the first row. |
| 53 | views::ColumnSet* cs = layout->AddColumnSet(1); |
Torne (Richard Coles) | 7d4cd47 | 2013-06-19 11:58:07 +0100 | [diff] [blame] | 54 | views::Label* message_label = new views::Label(controller_->PromptText()); |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 55 | |
| 56 | // Maximum width for the message field in pixels. The message text will be |
| 57 | // wrapped when its width is wider than this. |
Torne (Richard Coles) | c2e0dbd | 2013-05-09 18:35:53 +0100 | [diff] [blame] | 58 | const int kMaxMessageWidth = 300; |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 59 | |
| 60 | int message_width = |
| 61 | std::min(kMaxMessageWidth, message_label->GetPreferredSize().width()); |
| 62 | cs->AddColumn(views::GridLayout::LEADING, |
| 63 | views::GridLayout::CENTER, |
| 64 | 0, |
| 65 | views::GridLayout::FIXED, |
| 66 | message_width, |
| 67 | false); |
| 68 | message_label->SetBounds(0, 0, message_width, 0); |
| 69 | message_label->SetHorizontalAlignment(gfx::ALIGN_LEFT); |
| 70 | message_label->SetMultiLine(true); |
| 71 | layout->StartRow(0, 1); |
| 72 | layout->AddView(message_label); |
| 73 | |
| 74 | // Padding between message and buttons. |
| 75 | layout->AddPaddingRow(0, views::kRelatedControlVerticalSpacing); |
| 76 | |
| 77 | cs = layout->AddColumnSet(2); |
| 78 | cs->AddPaddingColumn(1, views::kRelatedControlHorizontalSpacing); |
| 79 | cs->AddColumn(views::GridLayout::CENTER, |
| 80 | views::GridLayout::CENTER, |
| 81 | 0, |
| 82 | views::GridLayout::USE_PREF, |
| 83 | 0, |
| 84 | 0); |
| 85 | cs->AddPaddingColumn(0, views::kRelatedButtonHSpacing); |
| 86 | cs->AddColumn(views::GridLayout::CENTER, |
| 87 | views::GridLayout::CENTER, |
| 88 | 0, |
| 89 | views::GridLayout::USE_PREF, |
| 90 | 0, |
| 91 | 0); |
| 92 | layout->StartRow(0, 2); |
Torne (Richard Coles) | 7d4cd47 | 2013-06-19 11:58:07 +0100 | [diff] [blame] | 93 | |
| 94 | if (!controller_->NormalImage().IsEmpty()) { |
| 95 | views::ImageButton* image_button = new views::ImageButton(this); |
| 96 | image_button->SetImage(views::Button::STATE_NORMAL, |
| 97 | controller_->NormalImage().ToImageSkia()); |
| 98 | image_button->SetImage(views::Button::STATE_HOVERED, |
| 99 | controller_->HoverImage().ToImageSkia()); |
| 100 | image_button->SetImage(views::Button::STATE_PRESSED, |
| 101 | controller_->PressedImage().ToImageSkia()); |
| 102 | ok_button_ = image_button; |
| 103 | } else { |
| 104 | views::LabelButton* label_button = new views::LabelButton( |
| 105 | this, AutocheckoutBubbleController::AcceptText()); |
| 106 | label_button->SetStyle(views::Button::STYLE_NATIVE_TEXTBUTTON); |
| 107 | ok_button_ = label_button; |
| 108 | } |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 109 | layout->AddView(ok_button_); |
Torne (Richard Coles) | 7d4cd47 | 2013-06-19 11:58:07 +0100 | [diff] [blame] | 110 | |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 111 | cancel_button_ = |
Torne (Richard Coles) | 7d4cd47 | 2013-06-19 11:58:07 +0100 | [diff] [blame] | 112 | new views::LabelButton(this, AutocheckoutBubbleController::CancelText()); |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 113 | cancel_button_->SetStyle(views::Button::STYLE_NATIVE_TEXTBUTTON); |
| 114 | layout->AddView(cancel_button_); |
| 115 | } |
| 116 | |
| 117 | gfx::Rect AutocheckoutBubbleViews::GetAnchorRect() { |
| 118 | return controller_->anchor_rect(); |
| 119 | } |
| 120 | |
Torne (Richard Coles) | c2e0dbd | 2013-05-09 18:35:53 +0100 | [diff] [blame] | 121 | void AutocheckoutBubbleViews::OnWidgetBoundsChanged( |
| 122 | views::Widget* widget, |
| 123 | const gfx::Rect& new_bounds) { |
| 124 | if (anchor_widget() == widget) |
| 125 | HideBubble(); |
| 126 | } |
| 127 | |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 128 | void AutocheckoutBubbleViews::ButtonPressed(views::Button* sender, |
| 129 | const ui::Event& event) { |
| 130 | if (sender == ok_button_) { |
| 131 | controller_->BubbleAccepted(); |
| 132 | } else if (sender == cancel_button_) { |
| 133 | controller_->BubbleCanceled(); |
| 134 | } else { |
| 135 | NOTREACHED(); |
| 136 | } |
| 137 | GetWidget()->Close(); |
| 138 | } |
| 139 | |
| 140 | // static |
| 141 | base::WeakPtr<AutocheckoutBubble> AutocheckoutBubble::Create( |
| 142 | scoped_ptr<AutocheckoutBubbleController> controller) { |
Ben Murdoch | bb1529c | 2013-08-08 10:24:53 +0100 | [diff] [blame^] | 143 | #if defined(USE_AURA) |
| 144 | // If the page hasn't yet been attached to a RootWindow, |
| 145 | // Aura code for creating the bubble will fail. |
| 146 | if (!controller->native_window()->GetRootWindow()) |
| 147 | return base::WeakPtr<AutocheckoutBubble>(); |
| 148 | #endif // defined(USE_AURA) |
| 149 | |
Torne (Richard Coles) | c2e0dbd | 2013-05-09 18:35:53 +0100 | [diff] [blame] | 150 | views::Widget* widget = views::Widget::GetTopLevelWidgetForNativeView( |
| 151 | controller->native_window()); |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 152 | // The bubble owns itself. |
| 153 | AutocheckoutBubbleViews* delegate = |
Torne (Richard Coles) | c2e0dbd | 2013-05-09 18:35:53 +0100 | [diff] [blame] | 154 | new AutocheckoutBubbleViews(controller.Pass(), |
| 155 | widget ? widget->GetContentsView() : NULL); |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 156 | views::BubbleDelegateView::CreateBubble(delegate); |
| 157 | delegate->SetAlignment(views::BubbleBorder::ALIGN_EDGE_TO_ANCHOR_EDGE); |
| 158 | return delegate->AsWeakPtr(); |
| 159 | } |
| 160 | |
| 161 | } // namespace autofill |