OLD | NEW |
---|---|
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #import "chrome/browser/ui/cocoa/extensions/extension_popup_controller.h" | 5 #import "chrome/browser/ui/cocoa/extensions/extension_popup_controller.h" |
6 | 6 |
7 #include <algorithm> | 7 #include <algorithm> |
8 | 8 |
9 #include "chrome/browser/debugger/devtools_window.h" | 9 #include "chrome/browser/debugger/devtools_window.h" |
10 #include "chrome/browser/extensions/extension_host.h" | 10 #include "chrome/browser/extensions/extension_host.h" |
(...skipping 101 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
112 ExtensionPopupController* controller_; | 112 ExtensionPopupController* controller_; |
113 }; | 113 }; |
114 | 114 |
115 @implementation ExtensionPopupController | 115 @implementation ExtensionPopupController |
116 | 116 |
117 - (id)initWithHost:(ExtensionHost*)host | 117 - (id)initWithHost:(ExtensionHost*)host |
118 parentWindow:(NSWindow*)parentWindow | 118 parentWindow:(NSWindow*)parentWindow |
119 anchoredAt:(NSPoint)anchoredAt | 119 anchoredAt:(NSPoint)anchoredAt |
120 arrowLocation:(info_bubble::BubbleArrowLocation)arrowLocation | 120 arrowLocation:(info_bubble::BubbleArrowLocation)arrowLocation |
121 devMode:(BOOL)devMode { | 121 devMode:(BOOL)devMode { |
122 | |
123 parentWindow_ = parentWindow; | |
124 anchor_ = [parentWindow convertBaseToScreen:anchoredAt]; | |
125 host_.reset(host); | |
126 beingInspected_ = devMode; | |
Nico
2012/03/14 21:26:17
wow
| |
127 | |
128 scoped_nsobject<InfoBubbleView> view([[InfoBubbleView alloc] init]); | |
129 if (!view.get()) | |
130 return nil; | |
131 [view setArrowLocation:arrowLocation]; | |
132 | |
133 extensionView_ = host->view()->native_view(); | |
134 container_.reset(new ExtensionPopupContainer(self)); | |
135 host->view()->set_container(container_.get()); | |
136 | |
137 NSNotificationCenter* center = [NSNotificationCenter defaultCenter]; | |
138 [center addObserver:self | |
139 selector:@selector(extensionViewFrameChanged) | |
140 name:NSViewFrameDidChangeNotification | |
141 object:extensionView_]; | |
142 | |
143 // Watch to see if the parent window closes, and if so, close this one. | |
144 [center addObserver:self | |
145 selector:@selector(parentWindowWillClose:) | |
146 name:NSWindowWillCloseNotification | |
147 object:parentWindow_]; | |
148 | |
149 [view addSubview:extensionView_]; | |
150 scoped_nsobject<InfoBubbleWindow> window( | 122 scoped_nsobject<InfoBubbleWindow> window( |
151 [[InfoBubbleWindow alloc] | 123 [[InfoBubbleWindow alloc] |
152 initWithContentRect:NSZeroRect | 124 initWithContentRect:NSZeroRect |
153 styleMask:NSBorderlessWindowMask | 125 styleMask:NSBorderlessWindowMask |
154 backing:NSBackingStoreBuffered | 126 backing:NSBackingStoreBuffered |
155 defer:YES]); | 127 defer:YES]); |
156 if (!window.get()) | 128 if (!window.get()) |
157 return nil; | 129 return nil; |
130 anchoredAt = [parentWindow convertBaseToScreen:anchoredAt]; | |
131 if ((self = [super initWithWindow:window | |
132 parentWindow:parentWindow | |
133 anchoredAt:anchoredAt])) { | |
134 host_.reset(host); | |
135 beingInspected_ = devMode; | |
158 | 136 |
159 [window setDelegate:self]; | 137 InfoBubbleView* view = |
160 [window setContentView:view]; | 138 static_cast<InfoBubbleView*>(self.window.contentView); |
Nico
2012/03/14 21:26:17
DCHECK isKindOfClass
Robert Sesek
2012/03/14 23:56:41
Switched to using BaseBubbleController.bubble inst
| |
161 self = [super initWithWindow:window]; | 139 [view setArrowLocation:arrowLocation]; |
162 if (beingInspected_) { | 140 |
163 // Listen for the the devtools window closing. | 141 extensionView_ = host->view()->native_view(); |
164 notificationBridge_.reset(new DevtoolsNotificationBridge(self)); | 142 container_.reset(new ExtensionPopupContainer(self)); |
165 registrar_.reset(new content::NotificationRegistrar); | 143 host->view()->set_container(container_.get()); |
166 registrar_->Add(notificationBridge_.get(), | 144 |
167 content::NOTIFICATION_DEVTOOLS_WINDOW_CLOSING, | 145 NSNotificationCenter* center = [NSNotificationCenter defaultCenter]; |
168 content::Source<content::BrowserContext>(host->profile())); | 146 [center addObserver:self |
169 registrar_->Add(notificationBridge_.get(), | 147 selector:@selector(extensionViewFrameChanged) |
170 chrome::NOTIFICATION_EXTENSION_HOST_DID_STOP_LOADING, | 148 name:NSViewFrameDidChangeNotification |
171 content::Source<Profile>(host->profile())); | 149 object:extensionView_]; |
150 | |
151 [view addSubview:extensionView_]; | |
152 | |
153 if (beingInspected_) { | |
154 // Listen for the the devtools window closing. | |
155 notificationBridge_.reset(new DevtoolsNotificationBridge(self)); | |
156 registrar_.reset(new content::NotificationRegistrar); | |
157 registrar_->Add(notificationBridge_.get(), | |
158 content::NOTIFICATION_DEVTOOLS_WINDOW_CLOSING, | |
159 content::Source<content::BrowserContext>( | |
160 host->profile())); | |
161 registrar_->Add(notificationBridge_.get(), | |
162 chrome::NOTIFICATION_EXTENSION_HOST_DID_STOP_LOADING, | |
163 content::Source<Profile>(host->profile())); | |
164 } | |
172 } | 165 } |
173 return self; | 166 return self; |
174 } | 167 } |
175 | 168 |
176 - (void)showDevTools { | 169 - (void)showDevTools { |
177 DevToolsWindow::OpenDevToolsWindow(host_->render_view_host()); | 170 DevToolsWindow::OpenDevToolsWindow(host_->render_view_host()); |
178 } | 171 } |
179 | 172 |
180 - (void)dealloc { | |
181 [[NSNotificationCenter defaultCenter] removeObserver:self]; | |
Nico
2012/03/14 21:26:17
Keeping this is probably nicer, since the class st
Robert Sesek
2012/03/14 23:56:41
Done.
| |
182 [super dealloc]; | |
183 } | |
184 | |
185 - (void)parentWindowWillClose:(NSNotification*)notification { | |
186 [self close]; | |
187 } | |
188 | |
189 - (void)windowWillClose:(NSNotification *)notification { | 173 - (void)windowWillClose:(NSNotification *)notification { |
190 [[NSNotificationCenter defaultCenter] removeObserver:self]; | 174 [super windowWillClose:notification]; |
191 [gPopup autorelease]; | |
192 gPopup = nil; | 175 gPopup = nil; |
193 if (host_->view()) | 176 if (host_->view()) |
194 host_->view()->set_container(NULL); | 177 host_->view()->set_container(NULL); |
195 } | 178 } |
196 | 179 |
197 - (void)windowDidResignKey:(NSNotification *)notification { | 180 - (void)windowDidResignKey:(NSNotification*)notification { |
198 NSWindow* window = [self window]; | 181 if (!beingInspected_) |
199 DCHECK_EQ([notification object], window); | 182 [super windowDidResignKey:notification]; |
200 // If the window isn't visible, it is already closed, and this notification | |
201 // has been sent as part of the closing operation, so no need to close. | |
202 if ([window isVisible] && !beingInspected_) { | |
203 [self close]; | |
204 } | |
205 } | |
206 | |
207 - (void)close { | |
208 [[[self window] parentWindow] removeChildWindow:[self window]]; | |
209 [super close]; | |
210 } | 183 } |
211 | 184 |
212 - (BOOL)isClosing { | 185 - (BOOL)isClosing { |
213 return [static_cast<InfoBubbleWindow*>([self window]) isClosing]; | 186 return [static_cast<InfoBubbleWindow*>([self window]) isClosing]; |
214 } | 187 } |
215 | 188 |
216 - (ExtensionHost*)extensionHost { | 189 - (ExtensionHost*)extensionHost { |
217 return host_.get(); | 190 return host_.get(); |
218 } | 191 } |
219 | 192 |
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
284 CGFloat inset = info_bubble::kBubbleCornerRadius / 2.0; | 257 CGFloat inset = info_bubble::kBubbleCornerRadius / 2.0; |
285 [extensionView_ setFrameOrigin:NSMakePoint(inset, inset)]; | 258 [extensionView_ setFrameOrigin:NSMakePoint(inset, inset)]; |
286 | 259 |
287 NSRect frame = [extensionView_ frame]; | 260 NSRect frame = [extensionView_ frame]; |
288 frame.size.height += info_bubble::kBubbleArrowHeight + | 261 frame.size.height += info_bubble::kBubbleArrowHeight + |
289 info_bubble::kBubbleCornerRadius; | 262 info_bubble::kBubbleCornerRadius; |
290 frame.size.width += info_bubble::kBubbleCornerRadius; | 263 frame.size.width += info_bubble::kBubbleCornerRadius; |
291 frame = [extensionView_ convertRectToBase:frame]; | 264 frame = [extensionView_ convertRectToBase:frame]; |
292 // Adjust the origin according to the height and width so that the arrow is | 265 // Adjust the origin according to the height and width so that the arrow is |
293 // positioned correctly at the middle and slightly down from the button. | 266 // positioned correctly at the middle and slightly down from the button. |
294 NSPoint windowOrigin = anchor_; | 267 NSPoint windowOrigin = self.anchorPoint; |
295 NSSize offsets = NSMakeSize(info_bubble::kBubbleArrowXOffset + | 268 NSSize offsets = NSMakeSize(info_bubble::kBubbleArrowXOffset + |
296 info_bubble::kBubbleArrowWidth / 2.0, | 269 info_bubble::kBubbleArrowWidth / 2.0, |
297 info_bubble::kBubbleArrowHeight / 2.0); | 270 info_bubble::kBubbleArrowHeight / 2.0); |
298 offsets = [extensionView_ convertSize:offsets toView:nil]; | 271 offsets = [extensionView_ convertSize:offsets toView:nil]; |
299 windowOrigin.x -= NSWidth(frame) - offsets.width; | 272 windowOrigin.x -= NSWidth(frame) - offsets.width; |
300 windowOrigin.y -= NSHeight(frame) - offsets.height; | 273 windowOrigin.y -= NSHeight(frame) - offsets.height; |
301 frame.origin = windowOrigin; | 274 frame.origin = windowOrigin; |
302 | 275 |
303 // Is the window still animating in? If so, then cancel that and create a new | 276 // Is the window still animating in? If so, then cancel that and create a new |
304 // animation setting the opacity and new frame value. Otherwise the current | 277 // animation setting the opacity and new frame value. Otherwise the current |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
347 return; | 320 return; |
348 | 321 |
349 [extensionView_ setFrame:frame]; | 322 [extensionView_ setFrame:frame]; |
350 [extensionView_ setNeedsDisplay:YES]; | 323 [extensionView_ setNeedsDisplay:YES]; |
351 } | 324 } |
352 | 325 |
353 - (void)onViewDidShow { | 326 - (void)onViewDidShow { |
354 [self onPreferredSizeChanged:pendingPreferredSize_]; | 327 [self onPreferredSizeChanged:pendingPreferredSize_]; |
355 } | 328 } |
356 | 329 |
357 // We want this to be a child of a browser window. addChildWindow: (called from | |
358 // this function) will bring the window on-screen; unfortunately, | |
359 // [NSWindowController showWindow:] will also bring it on-screen (but will cause | |
360 // unexpected changes to the window's position). We cannot have an | |
361 // addChildWindow: and a subsequent showWindow:. Thus, we have our own version. | |
362 - (void)showWindow:(id)sender { | |
363 [parentWindow_ addChildWindow:[self window] ordered:NSWindowAbove]; | |
364 [[self window] makeKeyAndOrderFront:self]; | |
365 } | |
366 | |
367 - (void)windowDidResize:(NSNotification*)notification { | 330 - (void)windowDidResize:(NSNotification*)notification { |
368 // Let the extension view know, so that it can tell plugins. | 331 // Let the extension view know, so that it can tell plugins. |
369 if (host_->view()) | 332 if (host_->view()) |
370 host_->view()->WindowFrameChanged(); | 333 host_->view()->WindowFrameChanged(); |
371 } | 334 } |
372 | 335 |
373 - (void)windowDidMove:(NSNotification*)notification { | 336 - (void)windowDidMove:(NSNotification*)notification { |
374 // Let the extension view know, so that it can tell plugins. | 337 // Let the extension view know, so that it can tell plugins. |
375 if (host_->view()) | 338 if (host_->view()) |
376 host_->view()->WindowFrameChanged(); | 339 host_->view()->WindowFrameChanged(); |
(...skipping 10 matching lines...) Expand all Loading... | |
387 return minSize; | 350 return minSize; |
388 } | 351 } |
389 | 352 |
390 // Private (TestingAPI) | 353 // Private (TestingAPI) |
391 + (NSSize)maxPopupSize { | 354 + (NSSize)maxPopupSize { |
392 NSSize maxSize = {ExtensionViewMac::kMaxWidth, ExtensionViewMac::kMaxHeight}; | 355 NSSize maxSize = {ExtensionViewMac::kMaxWidth, ExtensionViewMac::kMaxHeight}; |
393 return maxSize; | 356 return maxSize; |
394 } | 357 } |
395 | 358 |
396 @end | 359 @end |
OLD | NEW |