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
3 // found in the LICENSE file.
4
5 #include "chrome/browser/ui/views/infobars/confirm_infobar.h"
6
7 #include "chrome/browser/tab_contents/confirm_infobar_delegate.h"
8 #include "chrome/browser/ui/views/event_utils.h"
9 #include "views/controls/button/text_button.h"
10 #include "views/controls/label.h"
11
12 // ConfirmInfoBarDelegate -----------------------------------------------------
13
CreateInfoBar()14 InfoBar* ConfirmInfoBarDelegate::CreateInfoBar() {
15 return new ConfirmInfoBar(this);
16 }
17
18 // ConfirmInfoBar -------------------------------------------------------------
19
ConfirmInfoBar(ConfirmInfoBarDelegate * delegate)20 ConfirmInfoBar::ConfirmInfoBar(ConfirmInfoBarDelegate* delegate)
21 : InfoBarView(delegate),
22 label_(NULL),
23 ok_button_(NULL),
24 cancel_button_(NULL),
25 link_(NULL) {
26 }
27
~ConfirmInfoBar()28 ConfirmInfoBar::~ConfirmInfoBar() {
29 }
30
Layout()31 void ConfirmInfoBar::Layout() {
32 InfoBarView::Layout();
33
34 int available_width = std::max(0, EndX() - StartX() - ContentMinimumWidth());
35 gfx::Size label_size = label_->GetPreferredSize();
36 label_->SetBounds(StartX(), OffsetY(label_size),
37 std::min(label_size.width(), available_width), label_size.height());
38 available_width = std::max(0, available_width - label_size.width());
39
40 int button_x = label_->bounds().right() + kEndOfLabelSpacing;
41 if (ok_button_ != NULL) {
42 gfx::Size ok_size = ok_button_->GetPreferredSize();
43 ok_button_->SetBounds(button_x, OffsetY(ok_size), ok_size.width(),
44 ok_size.height());
45 button_x += ok_size.width() + kButtonButtonSpacing;
46 }
47
48 if (cancel_button_ != NULL) {
49 gfx::Size cancel_size = cancel_button_->GetPreferredSize();
50 cancel_button_->SetBounds(button_x, OffsetY(cancel_size),
51 cancel_size.width(), cancel_size.height());
52 }
53
54 if (link_ != NULL) {
55 gfx::Size link_size = link_->GetPreferredSize();
56 int link_width = std::min(link_size.width(), available_width);
57 link_->SetBounds(EndX() - link_width, OffsetY(link_size), link_width,
58 link_size.height());
59 }
60 }
61
ViewHierarchyChanged(bool is_add,View * parent,View * child)62 void ConfirmInfoBar::ViewHierarchyChanged(bool is_add,
63 View* parent,
64 View* child) {
65 if (is_add && child == this && (label_ == NULL)) {
66 ConfirmInfoBarDelegate* delegate = GetDelegate();
67 label_ = CreateLabel(delegate->GetMessageText());
68 AddChildView(label_);
69
70 if (delegate->GetButtons() & ConfirmInfoBarDelegate::BUTTON_OK) {
71 ok_button_ = CreateTextButton(this,
72 delegate->GetButtonLabel(ConfirmInfoBarDelegate::BUTTON_OK),
73 delegate->NeedElevation(ConfirmInfoBarDelegate::BUTTON_OK));
74 AddChildView(ok_button_);
75 }
76
77 if (delegate->GetButtons() & ConfirmInfoBarDelegate::BUTTON_CANCEL) {
78 cancel_button_ = CreateTextButton(this,
79 delegate->GetButtonLabel(ConfirmInfoBarDelegate::BUTTON_CANCEL),
80 delegate->NeedElevation(ConfirmInfoBarDelegate::BUTTON_CANCEL));
81 AddChildView(cancel_button_);
82 }
83
84 string16 link_text(delegate->GetLinkText());
85 if (!link_text.empty()) {
86 link_ = CreateLink(link_text, this, background()->get_color());
87 AddChildView(link_);
88 }
89 }
90
91 // This must happen after adding all other children so InfoBarView can ensure
92 // the close button is the last child.
93 InfoBarView::ViewHierarchyChanged(is_add, parent, child);
94 }
95
ButtonPressed(views::Button * sender,const views::Event & event)96 void ConfirmInfoBar::ButtonPressed(views::Button* sender,
97 const views::Event& event) {
98 ConfirmInfoBarDelegate* delegate = GetDelegate();
99 if ((ok_button_ != NULL) && sender == ok_button_) {
100 if (delegate->Accept())
101 RemoveInfoBar();
102 } else if ((cancel_button_ != NULL) && (sender == cancel_button_)) {
103 if (delegate->Cancel())
104 RemoveInfoBar();
105 } else {
106 InfoBarView::ButtonPressed(sender, event);
107 }
108 }
109
ContentMinimumWidth() const110 int ConfirmInfoBar::ContentMinimumWidth() const {
111 int width = (link_ == NULL) ? 0 : kEndOfLabelSpacing; // Space before link
112 int before_cancel_spacing = kEndOfLabelSpacing;
113 if (ok_button_ != NULL) {
114 width += kEndOfLabelSpacing + ok_button_->GetPreferredSize().width();
115 before_cancel_spacing = kButtonButtonSpacing;
116 }
117 return width + ((cancel_button_ == NULL) ? 0 :
118 (before_cancel_spacing + cancel_button_->GetPreferredSize().width()));
119 }
120
LinkActivated(views::Link * source,int event_flags)121 void ConfirmInfoBar::LinkActivated(views::Link* source, int event_flags) {
122 DCHECK(link_ != NULL);
123 DCHECK_EQ(link_, source);
124 if (GetDelegate()->LinkClicked(
125 event_utils::DispositionFromEventFlags(event_flags)))
126 RemoveInfoBar();
127 }
128
GetDelegate()129 ConfirmInfoBarDelegate* ConfirmInfoBar::GetDelegate() {
130 return delegate()->AsConfirmInfoBarDelegate();
131 }
132