Upstream version 10.39.225.0
[platform/framework/web/crosswalk.git] / src / chrome / browser / ui / cocoa / infobars / infobar_controller.mm
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.
4
5 #import "chrome/browser/ui/cocoa/infobars/infobar_controller.h"
6
7 #include "base/logging.h"
8 #include "base/mac/bundle_locations.h"
9 #include "base/mac/mac_util.h"
10 #include "chrome/browser/infobars/infobar_service.h"
11 #import "chrome/browser/ui/cocoa/animatable_view.h"
12 #import "chrome/browser/ui/cocoa/browser_window_controller.h"
13 #import "chrome/browser/ui/cocoa/image_button_cell.h"
14 #include "chrome/browser/ui/cocoa/infobars/infobar_cocoa.h"
15 #import "chrome/browser/ui/cocoa/infobars/infobar_container_cocoa.h"
16 #import "chrome/browser/ui/cocoa/infobars/infobar_container_controller.h"
17 #import "chrome/browser/ui/cocoa/infobars/infobar_gradient_view.h"
18 #import "chrome/browser/ui/cocoa/location_bar/location_bar_view_mac.h"
19 #include "grit/theme_resources.h"
20 #import "ui/base/cocoa/controls/hyperlink_text_view.h"
21 #include "ui/gfx/image/image.h"
22 #include "ui/resources/grit/ui_resources.h"
23
24 @interface InfoBarController ()
25 // Sets |label_| based on |labelPlaceholder_|, sets |labelPlaceholder_| to nil.
26 - (void)initializeLabel;
27 @end
28
29 @implementation InfoBarController
30
31 @synthesize containerController = containerController_;
32
33 - (id)initWithInfoBar:(InfoBarCocoa*)infobar {
34   if ((self = [super initWithNibName:@"InfoBar"
35                               bundle:base::mac::FrameworkBundle()])) {
36     DCHECK(infobar);
37     infobar_ = infobar->GetWeakPtr();
38   }
39   return self;
40 }
41
42 // All infobars have an icon, so we set up the icon in the base class
43 // awakeFromNib.
44 - (void)awakeFromNib {
45   [[closeButton_ cell] setImageID:IDR_CLOSE_1
46                    forButtonState:image_button_cell::kDefaultState];
47   [[closeButton_ cell] setImageID:IDR_CLOSE_1_H
48                    forButtonState:image_button_cell::kHoverState];
49   [[closeButton_ cell] setImageID:IDR_CLOSE_1_P
50                    forButtonState:image_button_cell::kPressedState];
51   [[closeButton_ cell] setImageID:IDR_CLOSE_1
52                    forButtonState:image_button_cell::kDisabledState];
53
54   if (![self delegate]->GetIcon().IsEmpty()) {
55     [image_ setImage:[self delegate]->GetIcon().ToNSImage()];
56   } else {
57     // No icon, remove it from the view and grow the textfield to include the
58     // space.
59     NSRect imageFrame = [image_ frame];
60     NSRect labelFrame = [labelPlaceholder_ frame];
61     labelFrame.size.width += NSMinX(imageFrame) - NSMinX(labelFrame);
62     labelFrame.origin.x = imageFrame.origin.x;
63     [image_ removeFromSuperview];
64     image_ = nil;
65     [labelPlaceholder_ setFrame:labelFrame];
66   }
67   [self initializeLabel];
68
69   [self addAdditionalControls];
70
71   [infoBarView_ setInfobarType:[self delegate]->GetInfoBarType()];
72   [infoBarView_ setAutoresizingMask:NSViewWidthSizable | NSViewHeightSizable];
73 }
74
75 - (void)dealloc {
76   [okButton_ setTarget:nil];
77   [cancelButton_ setTarget:nil];
78   [closeButton_ setTarget:nil];
79   [super dealloc];
80 }
81
82 - (InfoBarCocoa*)infobar {
83   return infobar_.get();
84 }
85
86 // Called when someone clicks on the embedded link.
87 - (BOOL)textView:(NSTextView*)textView
88    clickedOnLink:(id)link
89          atIndex:(NSUInteger)charIndex {
90   if ([self respondsToSelector:@selector(linkClicked)])
91     [self performSelector:@selector(linkClicked)];
92   return YES;
93 }
94
95 - (BOOL)isOwned {
96   return infobar_ && infobar_->OwnerCocoa() != NULL;
97 }
98
99 // Called when someone clicks on the ok button.
100 - (void)ok:(id)sender {
101   // Subclasses must override this method if they do not hide the ok button.
102   NOTREACHED();
103 }
104
105 // Called when someone clicks on the cancel button.
106 - (void)cancel:(id)sender {
107   // Subclasses must override this method if they do not hide the cancel button.
108   NOTREACHED();
109 }
110
111 // Called when someone clicks on the close button.
112 - (void)dismiss:(id)sender {
113   if (![self isOwned])
114     return;
115   [self delegate]->InfoBarDismissed();
116   [self removeSelf];
117 }
118
119 - (void)removeSelf {
120   infobar_->RemoveSelf();
121 }
122
123 - (void)addAdditionalControls {
124   // Default implementation does nothing.
125 }
126
127 - (void)infobarWillHide {
128 }
129
130 - (void)infobarWillClose {
131 }
132
133 - (void)removeButtons {
134   // Extend the label all the way across.
135   NSRect labelFrame = [label_.get() frame];
136   labelFrame.size.width = NSMaxX([cancelButton_ frame]) - NSMinX(labelFrame);
137   [okButton_ removeFromSuperview];
138   okButton_ = nil;
139   [cancelButton_ removeFromSuperview];
140   cancelButton_ = nil;
141   [label_.get() setFrame:labelFrame];
142 }
143
144 - (void)layoutArrow {
145   [infoBarView_ setArrowHeight:infobar_->arrow_height()];
146   [infoBarView_ setArrowHalfWidth:infobar_->arrow_half_width()];
147   [infoBarView_ setHasTip:![containerController_ shouldSuppressTopInfoBarTip]];
148
149   // Convert from window to view coordinates.
150   NSPoint point = NSMakePoint([containerController_ infobarArrowX], 0);
151   point = [infoBarView_ convertPoint:point fromView:nil];
152   [infoBarView_ setArrowX:point.x];
153 }
154
155 - (void)disablePopUpMenu:(NSMenu*)menu {
156   // If the menu is re-opened, prevent queries to update items.
157   [menu setDelegate:nil];
158
159   // Prevent target/action messages to the controller.
160   for (NSMenuItem* item in [menu itemArray]) {
161     [item setEnabled:NO];
162     [item setTarget:nil];
163   }
164 }
165
166 - (infobars::InfoBarDelegate*)delegate {
167   return infobar_->delegate();
168 }
169
170 - (void)initializeLabel {
171   // Replace the label placeholder NSTextField with the real label NSTextView.
172   // The former doesn't show links in a nice way, but the latter can't be added
173   // in IB without a containing scroll view, so create the NSTextView
174   // programmatically.
175   base::scoped_nsobject<HyperlinkTextView> newLabel(
176     [[HyperlinkTextView alloc] initWithFrame:[labelPlaceholder_ frame]]);
177   [newLabel setDrawsBackgroundUsingSuperview:YES];
178   [newLabel setAutoresizingMask:[labelPlaceholder_ autoresizingMask]];
179   [[labelPlaceholder_ superview]
180       replaceSubview:labelPlaceholder_ with:newLabel];
181   labelPlaceholder_ = nil;  // Now released.
182   [newLabel setDelegate:self];
183
184   label_.reset(newLabel.release());
185 }
186
187 @end