OLD | NEW |
---|---|
1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. Use of this | 1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. Use of this |
2 // source code is governed by a BSD-style license that can be found in the | 2 // source code is governed by a BSD-style license that can be found in the |
3 // LICENSE file. | 3 // LICENSE file. |
4 | 4 |
5 #import "chrome/browser/cocoa/blocked_popup_container_controller.h" | 5 #import "chrome/browser/cocoa/blocked_popup_container_controller.h" |
6 | 6 |
7 #include "app/l10n_util.h" | 7 #include "app/l10n_util.h" |
8 #include "base/sys_string_conversions.h" | 8 #include "base/sys_string_conversions.h" |
9 #import "chrome/browser/cocoa/bubble_view.h" | |
9 #include "chrome/browser/cocoa/nsimage_cache.h" | 10 #include "chrome/browser/cocoa/nsimage_cache.h" |
10 #include "chrome/browser/tab_contents/tab_contents.h" | 11 #include "chrome/browser/tab_contents/tab_contents.h" |
11 #include "chrome/browser/tab_contents/tab_contents_view.h" | 12 #include "chrome/browser/tab_contents/tab_contents_view.h" |
12 #include "grit/generated_resources.h" | 13 #include "grit/generated_resources.h" |
13 | 14 |
14 #import "chrome/browser/cocoa/background_gradient_view.h" | |
15 | |
16 // A C++ bridge class that manages the interaction between the C++ interface | 15 // A C++ bridge class that manages the interaction between the C++ interface |
17 // and the Objective-C view controller that implements the popup blocker. | 16 // and the Objective-C view controller that implements the popup blocker. |
18 class BlockedPopupContainerViewBridge : public BlockedPopupContainerView { | 17 class BlockedPopupContainerViewBridge : public BlockedPopupContainerView { |
19 public: | 18 public: |
20 BlockedPopupContainerViewBridge(BlockedPopupContainerController* controller); | 19 BlockedPopupContainerViewBridge(BlockedPopupContainerController* controller); |
21 virtual ~BlockedPopupContainerViewBridge(); | 20 virtual ~BlockedPopupContainerViewBridge(); |
22 | 21 |
23 // Overrides from BlockedPopupContainerView | 22 // Overrides from BlockedPopupContainerView |
24 virtual void SetPosition(); | 23 virtual void SetPosition(); |
25 virtual void ShowView(); | 24 virtual void ShowView(); |
(...skipping 17 matching lines...) Expand all Loading... | |
43 - (id)initWithContainer:(BlockedPopupContainer*)container { | 42 - (id)initWithContainer:(BlockedPopupContainer*)container { |
44 if ((self = [super init])) { | 43 if ((self = [super init])) { |
45 container_ = container; | 44 container_ = container; |
46 bridge_.reset(new BlockedPopupContainerViewBridge(self)); | 45 bridge_.reset(new BlockedPopupContainerViewBridge(self)); |
47 [self initPopupView]; | 46 [self initPopupView]; |
48 } | 47 } |
49 return self; | 48 return self; |
50 } | 49 } |
51 | 50 |
52 - (void)dealloc { | 51 - (void)dealloc { |
52 [closeButton_ removeTrackingArea:closeTrackingArea_.get()]; | |
53 [view_ removeFromSuperview]; | 53 [view_ removeFromSuperview]; |
54 [[NSNotificationCenter defaultCenter] removeObserver:self]; | 54 [[NSNotificationCenter defaultCenter] removeObserver:self]; |
55 [super dealloc]; | 55 [super dealloc]; |
56 } | 56 } |
57 | 57 |
58 - (IBAction)closePopup:(id)sender { | 58 - (IBAction)closePopup:(id)sender { |
59 container_->set_dismissed(); | 59 container_->set_dismissed(); |
60 container_->CloseAll(); | 60 container_->CloseAll(); |
61 } | 61 } |
62 | 62 |
63 // Create and initialize the popup view and its label, close box, etc. | 63 // Create and initialize the popup view and its label, close box, etc. |
64 - (void)initPopupView { | 64 - (void)initPopupView { |
65 static const float kWidth = 200.0; | 65 static const float kWidth = 200.0; |
66 static const float kHeight = 20.0; | 66 static const float kHeight = 20.0; |
67 static const float kCloseBoxSize = 16.0; | 67 static const float kCloseBoxSize = 16.0; |
68 static const float kCloseBoxPaddingY = 2.0; | 68 static const float kCloseBoxPaddingY = 2.0; |
69 static const float kLabelPaddingX = 5.0; | 69 static const float kLabelPaddingX = 5.0; |
70 | 70 |
71 NSWindow* window = [[self containingView] window]; | |
72 | |
71 // Create it below the parent's bottom edge so we can animate it into place. | 73 // Create it below the parent's bottom edge so we can animate it into place. |
72 NSRect startFrame = NSMakeRect(0.0, -kHeight, kWidth, kHeight); | 74 NSRect startFrame = NSMakeRect(0.0, -kHeight, kWidth, kHeight); |
73 view_.reset([[BackgroundGradientView alloc] initWithFrame:startFrame]); | 75 view_.reset([[BubbleView alloc] initWithFrame:startFrame |
76 themeProvider:window]); | |
74 [view_ setAutoresizingMask:NSViewMinXMargin | NSViewMaxYMargin]; | 77 [view_ setAutoresizingMask:NSViewMinXMargin | NSViewMaxYMargin]; |
78 [view_ setCornerFlags:kRoundedTopLeftCorner | kRoundedTopRightCorner]; | |
75 | 79 |
76 // Create the text label and position it. We'll resize it later when the | 80 // Create the text label and position it. We'll resize it later when the |
77 // label gets updated. The view owns the label, we only hold a weak reference. | 81 // label gets updated. The view owns the label, we only hold a weak reference. |
78 NSRect labelFrame = NSMakeRect(kLabelPaddingX, | 82 NSRect labelFrame = NSMakeRect(kLabelPaddingX, |
79 0, | 83 0, |
80 startFrame.size.width - kCloseBoxSize, | 84 startFrame.size.width - kCloseBoxSize, |
81 startFrame.size.height); | 85 startFrame.size.height); |
82 popupButton_ = [[[NSPopUpButton alloc] initWithFrame:labelFrame] autorelease]; | 86 popupButton_ = [[[NSPopUpButton alloc] initWithFrame:labelFrame] autorelease]; |
83 [popupButton_ setAutoresizingMask:NSViewWidthSizable]; | 87 [popupButton_ setAutoresizingMask:NSViewWidthSizable]; |
84 [popupButton_ setBordered:NO]; | 88 [popupButton_ setBordered:NO]; |
85 [popupButton_ setBezelStyle:NSTexturedRoundedBezelStyle]; | 89 [popupButton_ setBezelStyle:NSTexturedRoundedBezelStyle]; |
86 [popupButton_ setPullsDown:YES]; | 90 [popupButton_ setPullsDown:YES]; |
87 // TODO(pinkerton): this doesn't work, not sure why. | 91 // TODO(pinkerton): this doesn't work, not sure why. |
88 [popupButton_ setPreferredEdge:NSMaxYEdge]; | 92 [popupButton_ setPreferredEdge:NSMaxYEdge]; |
89 // TODO(pinkerton): no matter what, the arrows always draw in the middle | 93 // TODO(pinkerton): no matter what, the arrows always draw in the middle |
90 // of the button. We can turn off the arrows entirely, but then will the | 94 // of the button. We can turn off the arrows entirely, but then will the |
91 // user ever know to click it? Leave them on for now. | 95 // user ever know to click it? |
92 //[[popupButton_ cell] setArrowPosition:NSPopUpNoArrow]; | 96 [[popupButton_ cell] setArrowPosition:NSPopUpNoArrow]; |
93 [[popupButton_ cell] setAltersStateOfSelectedItem:NO]; | 97 [[popupButton_ cell] setAltersStateOfSelectedItem:NO]; |
94 // If we don't add this, no title will ever display. | 98 // If we don't add this, no title will ever display. |
95 [popupButton_ addItemWithTitle:@"placeholder"]; | 99 [popupButton_ addItemWithTitle:@"placeholder"]; |
96 [view_ addSubview:popupButton_]; | 100 [view_ addSubview:popupButton_]; |
97 | 101 |
98 // Register for notifications that the menu is about to display so we can | 102 // Register for notifications that the menu is about to display so we can |
99 // fill it in lazily | 103 // fill it in lazily |
100 [[NSNotificationCenter defaultCenter] | 104 [[NSNotificationCenter defaultCenter] |
101 addObserver:self | 105 addObserver:self |
102 selector:@selector(showMenu:) | 106 selector:@selector(showMenu:) |
103 name:NSPopUpButtonCellWillPopUpNotification | 107 name:NSPopUpButtonCellWillPopUpNotification |
104 object:[popupButton_ cell]]; | 108 object:[popupButton_ cell]]; |
105 | 109 |
106 // Create the close box and position at the left of the view. | 110 // Create the close box and position at the left of the view. |
107 NSRect closeFrame = NSMakeRect(startFrame.size.width - kCloseBoxSize, | 111 NSRect closeFrame = NSMakeRect(startFrame.size.width - kCloseBoxSize, |
108 kCloseBoxPaddingY, | 112 kCloseBoxPaddingY, |
109 kCloseBoxSize, | 113 kCloseBoxSize, |
110 kCloseBoxSize); | 114 kCloseBoxSize); |
111 NSButton* close = [[[NSButton alloc] initWithFrame:closeFrame] autorelease]; | 115 closeButton_.reset([[NSButton alloc] initWithFrame:closeFrame]); |
112 [close setAutoresizingMask:NSViewMinXMargin]; | 116 [closeButton_ setAutoresizingMask:NSViewMinXMargin]; |
113 [close setImage:nsimage_cache::ImageNamed(@"close_bar.pdf")]; | 117 [closeButton_ setButtonType:NSMomentaryChangeButton]; |
114 [close setAlternateImage:nsimage_cache::ImageNamed(@"close_bar_p.pdf")]; | 118 [closeButton_ setImage:nsimage_cache::ImageNamed(@"close_bar.pdf")]; |
115 [close setBordered:NO]; | 119 [closeButton_ setAlternateImage:nsimage_cache::ImageNamed(@"close_bar_p.pdf")] ; |
rohitrao (ping after 24h)
2009/09/08 19:25:21
Line too long.
pink (ping after 24hrs)
2009/09/08 19:50:17
Done.
| |
116 [close setTarget:self]; | 120 [closeButton_ setBordered:NO]; |
117 [close setAction:@selector(closePopup:)]; | 121 [closeButton_ setTarget:self]; |
118 [view_ addSubview:close]; | 122 [closeButton_ setAction:@selector(closePopup:)]; |
123 [view_ addSubview:closeButton_]; | |
124 | |
125 // Set up the tracking rect for the close button mouseover. Add it | |
126 // to the |closeButton_| view, but we'll handle the message ourself. | |
127 // The mouseover is always enabled, because the close button works | |
128 // regardless of key/main/active status. | |
129 closeTrackingArea_.reset( | |
130 [[NSTrackingArea alloc] initWithRect:[closeButton_ bounds] | |
131 options:NSTrackingMouseEnteredAndExited | | |
132 NSTrackingActiveAlways | |
133 owner:self | |
134 userInfo:nil]); | |
135 [closeButton_ addTrackingArea:closeTrackingArea_.get()]; | |
119 } | 136 } |
120 | 137 |
121 // Returns the C++ brige object. | 138 // Returns the C++ brige object. |
122 - (BlockedPopupContainerView*)bridge { | 139 - (BlockedPopupContainerView*)bridge { |
123 return bridge_.get(); | 140 return bridge_.get(); |
124 } | 141 } |
125 | 142 |
126 // Returns the parent of the RWHVMac. We insert our popup blocker as a sibling | 143 // Returns the parent of the RWHVMac. We insert our popup blocker as a sibling |
127 // so that it stays around as the RWHVMac is created/destroyed during | 144 // so that it stays around as the RWHVMac is created/destroyed during |
128 // navigation. | 145 // navigation. |
129 - (NSView*)containingView { | 146 - (NSView*)containingView { |
130 return container_->GetConstrainingContents(NULL)->view()->GetNativeView(); | 147 NSView* view = nil; |
148 if (container_) | |
149 view = container_->GetConstrainingContents(NULL)->view()->GetNativeView(); | |
150 return view; | |
131 } | 151 } |
132 | 152 |
133 - (void)show { | 153 - (void)show { |
134 const float kLeftPadding = 20; // Leave room for the scrollbar. | 154 const float kLeftPadding = 20; // Leave room for the scrollbar. |
135 | 155 |
136 // No need to do anything if it's already on screen. | 156 // No need to do anything if it's already on screen. |
137 if ([view_ superview]) return; | 157 if ([view_ superview]) return; |
138 | 158 |
139 // Position the view at the bottom right corner, always leaving room for the | 159 // Position the view at the bottom right corner, always leaving room for the |
140 // scrollbar. This is what window does. It also doesn't care about covering | 160 // scrollbar. This is what window does. It also doesn't care about covering |
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
178 NSString* label = nil; | 198 NSString* label = nil; |
179 if (blockedPopups) { | 199 if (blockedPopups) { |
180 label = base::SysUTF16ToNSString( | 200 label = base::SysUTF16ToNSString( |
181 l10n_util::GetStringFUTF16(IDS_POPUPS_BLOCKED_COUNT, | 201 l10n_util::GetStringFUTF16(IDS_POPUPS_BLOCKED_COUNT, |
182 UintToString16(blockedPopups))); | 202 UintToString16(blockedPopups))); |
183 } else { | 203 } else { |
184 label = base::SysUTF16ToNSString( | 204 label = base::SysUTF16ToNSString( |
185 l10n_util::GetStringUTF16(IDS_POPUPS_UNBLOCKED)); | 205 l10n_util::GetStringUTF16(IDS_POPUPS_UNBLOCKED)); |
186 } | 206 } |
187 [self resizeWithLabel:label]; | 207 [self resizeWithLabel:label]; |
188 [popupButton_ setTitle:label]; | 208 [view_ setContent:label]; |
189 } | 209 } |
190 | 210 |
191 // Called when the user selects an item from the popup menu. The tag, if below | 211 // Called when the user selects an item from the popup menu. The tag, if below |
192 // |kImpossibleNumberOfPopups| will be the index into the container's popup | 212 // |kImpossibleNumberOfPopups| will be the index into the container's popup |
193 // array. In that case, we should display the popup. If >= | 213 // array. In that case, we should display the popup. If >= |
194 // |kImpossibleNumberOfPopups|, it represents a host that we should whitelist. | 214 // |kImpossibleNumberOfPopups|, it represents a host that we should whitelist. |
195 // |sender| is the NSMenuItem that was chosen. | 215 // |sender| is the NSMenuItem that was chosen. |
196 - (void)menuAction:(id)sender { | 216 - (void)menuAction:(id)sender { |
197 size_t tag = static_cast<size_t>([sender tag]); | 217 size_t tag = static_cast<size_t>([sender tag]); |
198 if (tag < BlockedPopupContainer::kImpossibleNumberOfPopups) { | 218 if (tag < BlockedPopupContainer::kImpossibleNumberOfPopups) { |
(...skipping 91 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
290 | 310 |
291 - (NSPopUpButton*)popupButton { | 311 - (NSPopUpButton*)popupButton { |
292 return popupButton_; | 312 return popupButton_; |
293 } | 313 } |
294 | 314 |
295 // Only used for testing. | 315 // Only used for testing. |
296 - (void)setContainer:(BlockedPopupContainer*)container { | 316 - (void)setContainer:(BlockedPopupContainer*)container { |
297 container_ = container; | 317 container_ = container; |
298 } | 318 } |
299 | 319 |
320 // Called when the mouse enters the tracking rect for the close box. | |
321 - (void)mouseEntered:(NSEvent *)theEvent { | |
322 if ([theEvent trackingArea] == closeTrackingArea_) | |
323 [closeButton_ setImage:nsimage_cache::ImageNamed(@"close_bar_h.pdf")]; | |
324 } | |
325 | |
326 // Called when the mouse exits the tracking rect for the close box. | |
327 - (void)mouseExited:(NSEvent *)theEvent { | |
328 if ([theEvent trackingArea] == closeTrackingArea_) | |
329 [closeButton_ setImage:nsimage_cache::ImageNamed(@"close_bar.pdf")]; | |
330 } | |
331 | |
300 @end | 332 @end |
301 | 333 |
302 //--------------------------------------------------------------------------- | 334 //--------------------------------------------------------------------------- |
303 | 335 |
304 BlockedPopupContainerView* BlockedPopupContainerView::Create( | 336 BlockedPopupContainerView* BlockedPopupContainerView::Create( |
305 BlockedPopupContainer* container) { | 337 BlockedPopupContainer* container) { |
306 // We "leak" |blocker| for now, we'll release it when the bridge class | 338 // We "leak" |blocker| for now, we'll release it when the bridge class |
307 // gets a Destroy() message. | 339 // gets a Destroy() message. |
308 BlockedPopupContainerController* blocker = | 340 BlockedPopupContainerController* blocker = |
309 [[BlockedPopupContainerController alloc] initWithContainer:container]; | 341 [[BlockedPopupContainerController alloc] initWithContainer:container]; |
(...skipping 21 matching lines...) Expand all Loading... | |
331 [controller_ update]; | 363 [controller_ update]; |
332 } | 364 } |
333 | 365 |
334 void BlockedPopupContainerViewBridge::HideView() { | 366 void BlockedPopupContainerViewBridge::HideView() { |
335 [controller_ hide]; | 367 [controller_ hide]; |
336 } | 368 } |
337 | 369 |
338 void BlockedPopupContainerViewBridge::Destroy() { | 370 void BlockedPopupContainerViewBridge::Destroy() { |
339 [controller_ autorelease]; | 371 [controller_ autorelease]; |
340 } | 372 } |
OLD | NEW |