Chromium Code Reviews| 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/base_bubble_controller.h" | 5 #import "chrome/browser/ui/cocoa/base_bubble_controller.h" |
| 6 | 6 |
| 7 #include "base/logging.h" | 7 #include "base/logging.h" |
| 8 #include "base/mac/bundle_locations.h" | 8 #include "base/mac/bundle_locations.h" |
| 9 #include "base/mac/foundation_util.h" | 9 #include "base/mac/foundation_util.h" |
| 10 #include "base/mac/mac_util.h" | 10 #include "base/mac/mac_util.h" |
| 11 #include "base/mac/scoped_nsobject.h" | 11 #include "base/mac/scoped_nsobject.h" |
| 12 #include "base/mac/sdk_forward_declarations.h" | 12 #include "base/mac/sdk_forward_declarations.h" |
| 13 #include "base/strings/string_util.h" | 13 #include "base/strings/string_util.h" |
| 14 #import "chrome/browser/ui/cocoa/browser_window_controller.h" | 14 #import "chrome/browser/ui/cocoa/browser_window_controller.h" |
| 15 #import "chrome/browser/ui/cocoa/info_bubble_view.h" | 15 #import "chrome/browser/ui/cocoa/info_bubble_view.h" |
| 16 #import "chrome/browser/ui/cocoa/info_bubble_window.h" | 16 #import "chrome/browser/ui/cocoa/info_bubble_window.h" |
| 17 #import "chrome/browser/ui/cocoa/tabs/tab_strip_model_observer_bridge.h" | 17 #import "chrome/browser/ui/cocoa/tabs/tab_strip_model_observer_bridge.h" |
| 18 #include "components/bubble/bubble_controller.h" | |
| 18 | 19 |
| 19 @interface BaseBubbleController (Private) | 20 @interface BaseBubbleController (Private) |
| 20 - (void)registerForNotifications; | 21 - (void)registerForNotifications; |
| 21 - (void)updateOriginFromAnchor; | 22 - (void)updateOriginFromAnchor; |
| 22 - (void)activateTabWithContents:(content::WebContents*)newContents | 23 - (void)activateTabWithContents:(content::WebContents*)newContents |
| 23 previousContents:(content::WebContents*)oldContents | 24 previousContents:(content::WebContents*)oldContents |
| 24 atIndex:(NSInteger)index | 25 atIndex:(NSInteger)index |
| 25 reason:(int)reason; | 26 reason:(int)reason; |
| 26 - (void)recordAnchorOffset; | 27 - (void)recordAnchorOffset; |
| 27 - (void)parentWindowDidResize:(NSNotification*)notification; | 28 - (void)parentWindowDidResize:(NSNotification*)notification; |
| 28 - (void)parentWindowWillClose:(NSNotification*)notification; | 29 - (void)parentWindowWillClose:(NSNotification*)notification; |
| 29 - (void)parentWindowWillToggleFullScreen:(NSNotification*)notification; | 30 - (void)parentWindowWillToggleFullScreen:(NSNotification*)notification; |
| 30 - (void)closeCleanup; | 31 - (void)closeCleanup; |
| 32 | |
| 33 // Temporary methods to decide how to close the bubble controller. | |
| 34 // TODO(hcarmona): remove these methods when all bubbles use the new API. | |
| 35 - (void)closeBubbleWithReason:(BubbleCloseReason)reason; | |
| 36 // Will be a noop in new bubble API because this is handled elsewhere. | |
| 37 - (void)closeBubbleWithoutReason; | |
|
groby-ooo-7-16
2015/09/04 19:13:38
Just call it closeBubble - it's not like we're act
hcarmona
2015/09/09 23:33:02
Done.
| |
| 31 @end | 38 @end |
| 32 | 39 |
| 33 @implementation BaseBubbleController | 40 @implementation BaseBubbleController |
| 34 | 41 |
| 35 @synthesize anchorPoint = anchor_; | 42 @synthesize anchorPoint = anchor_; |
| 36 @synthesize bubble = bubble_; | 43 @synthesize bubble = bubble_; |
| 37 @synthesize shouldOpenAsKeyWindow = shouldOpenAsKeyWindow_; | 44 @synthesize shouldOpenAsKeyWindow = shouldOpenAsKeyWindow_; |
| 38 @synthesize shouldCloseOnResignKey = shouldCloseOnResignKey_; | 45 @synthesize shouldCloseOnResignKey = shouldCloseOnResignKey_; |
| 46 @synthesize bubbleReference = bubbleReference_; | |
| 39 | 47 |
| 40 - (id)initWithWindowNibPath:(NSString*)nibPath | 48 - (id)initWithWindowNibPath:(NSString*)nibPath |
| 41 parentWindow:(NSWindow*)parentWindow | 49 parentWindow:(NSWindow*)parentWindow |
| 42 anchoredAt:(NSPoint)anchoredAt { | 50 anchoredAt:(NSPoint)anchoredAt { |
| 43 nibPath = [base::mac::FrameworkBundle() pathForResource:nibPath | 51 nibPath = [base::mac::FrameworkBundle() pathForResource:nibPath |
| 44 ofType:@"nib"]; | 52 ofType:@"nib"]; |
| 45 if ((self = [super initWithWindowNibPath:nibPath owner:self])) { | 53 if ((self = [super initWithWindowNibPath:nibPath owner:self])) { |
| 46 [self setParentWindow:parentWindow]; | 54 [self setParentWindow:parentWindow]; |
| 47 anchor_ = anchoredAt; | 55 anchor_ = anchoredAt; |
| 48 shouldOpenAsKeyWindow_ = YES; | 56 shouldOpenAsKeyWindow_ = YES; |
| (...skipping 172 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 221 DCHECK_EQ(parentWindow_, [notification object]); | 229 DCHECK_EQ(parentWindow_, [notification object]); |
| 222 NSPoint newOrigin = NSMakePoint(NSMinX([parentWindow_ frame]), | 230 NSPoint newOrigin = NSMakePoint(NSMinX([parentWindow_ frame]), |
| 223 NSMaxY([parentWindow_ frame])); | 231 NSMaxY([parentWindow_ frame])); |
| 224 newOrigin.x -= anchorOffset_.x; | 232 newOrigin.x -= anchorOffset_.x; |
| 225 newOrigin.y -= anchorOffset_.y; | 233 newOrigin.y -= anchorOffset_.y; |
| 226 [self setAnchorPoint:newOrigin]; | 234 [self setAnchorPoint:newOrigin]; |
| 227 } | 235 } |
| 228 | 236 |
| 229 - (void)parentWindowWillClose:(NSNotification*)notification { | 237 - (void)parentWindowWillClose:(NSNotification*)notification { |
| 230 [self setParentWindow:nil]; | 238 [self setParentWindow:nil]; |
| 231 [self close]; | 239 [self closeBubbleWithoutReason]; |
| 232 } | 240 } |
| 233 | 241 |
| 234 - (void)parentWindowWillToggleFullScreen:(NSNotification*)notification { | 242 - (void)parentWindowWillToggleFullScreen:(NSNotification*)notification { |
| 235 [self setParentWindow:nil]; | 243 [self setParentWindow:nil]; |
| 236 [self close]; | 244 [self closeBubbleWithoutReason]; |
| 237 } | 245 } |
| 238 | 246 |
| 239 - (void)closeCleanup { | 247 - (void)closeCleanup { |
| 240 if (eventTap_) { | 248 if (eventTap_) { |
| 241 [NSEvent removeMonitor:eventTap_]; | 249 [NSEvent removeMonitor:eventTap_]; |
| 242 eventTap_ = nil; | 250 eventTap_ = nil; |
| 243 } | 251 } |
| 244 if (resignationObserver_) { | 252 if (resignationObserver_) { |
| 245 [[NSNotificationCenter defaultCenter] | 253 [[NSNotificationCenter defaultCenter] |
| 246 removeObserver:resignationObserver_ | 254 removeObserver:resignationObserver_ |
| 247 name:NSWindowDidResignKeyNotification | 255 name:NSWindowDidResignKeyNotification |
| 248 object:nil]; | 256 object:nil]; |
| 249 resignationObserver_ = nil; | 257 resignationObserver_ = nil; |
| 250 } | 258 } |
| 251 | 259 |
| 252 tabStripObserverBridge_.reset(); | 260 tabStripObserverBridge_.reset(); |
| 253 } | 261 } |
| 254 | 262 |
| 263 - (void)closeBubbleWithReason:(BubbleCloseReason)reason { | |
| 264 if ([self bubbleReference]) | |
| 265 [self bubbleReference]->CloseBubble(reason); | |
| 266 else | |
| 267 [self close]; | |
| 268 } | |
| 269 | |
| 270 - (void)closeBubbleWithoutReason { | |
|
groby-ooo-7-16
2015/09/04 19:13:38
That's rather... icky. This means that we won't cl
hcarmona
2015/09/04 20:58:01
This should only be called where it's redundant fo
groby-ooo-7-16
2015/09/04 21:38:03
Can we kill that duplication?
hcarmona
2015/09/04 21:49:39
That's what this is attempting to do by not callin
| |
| 271 if (![self bubbleReference]) | |
| 272 [self close]; | |
| 273 } | |
| 274 | |
| 255 - (void)windowWillClose:(NSNotification*)notification { | 275 - (void)windowWillClose:(NSNotification*)notification { |
| 256 [self closeCleanup]; | 276 [self closeCleanup]; |
| 257 [[NSNotificationCenter defaultCenter] removeObserver:self]; | 277 [[NSNotificationCenter defaultCenter] removeObserver:self]; |
| 258 [self autorelease]; | 278 [self autorelease]; |
| 259 } | 279 } |
| 260 | 280 |
| 261 // We want this to be a child of a browser window. addChildWindow: | 281 // We want this to be a child of a browser window. addChildWindow: |
| 262 // (called from this function) will bring the window on-screen; | 282 // (called from this function) will bring the window on-screen; |
| 263 // unfortunately, [NSWindowController showWindow:] will also bring it | 283 // unfortunately, [NSWindowController showWindow:] will also bring it |
| 264 // on-screen (but will cause unexpected changes to the window's | 284 // on-screen (but will cause unexpected changes to the window's |
| (...skipping 24 matching lines...) Expand all Loading... | |
| 289 DCHECK_EQ([notification object], window); | 309 DCHECK_EQ([notification object], window); |
| 290 | 310 |
| 291 // If the window isn't visible, it is already closed, and this notification | 311 // If the window isn't visible, it is already closed, and this notification |
| 292 // has been sent as part of the closing operation, so no need to close. | 312 // has been sent as part of the closing operation, so no need to close. |
| 293 if (![window isVisible]) | 313 if (![window isVisible]) |
| 294 return; | 314 return; |
| 295 | 315 |
| 296 // Don't close when explicily disabled, or if there's an attached sheet (e.g. | 316 // Don't close when explicily disabled, or if there's an attached sheet (e.g. |
| 297 // Open File dialog). | 317 // Open File dialog). |
| 298 if ([self shouldCloseOnResignKey] && ![window attachedSheet]) { | 318 if ([self shouldCloseOnResignKey] && ![window attachedSheet]) { |
| 299 [self close]; | 319 [self closeBubbleWithReason:BUBBLE_CLOSE_FOCUS_LOST]; |
| 300 return; | 320 return; |
| 301 } | 321 } |
| 302 | 322 |
| 303 // The bubble should not receive key events when it is no longer key window, | 323 // The bubble should not receive key events when it is no longer key window, |
| 304 // so disable sharing parent key state. Share parent key state is only used | 324 // so disable sharing parent key state. Share parent key state is only used |
| 305 // to enable the close/minimize/maximize buttons of the parent window when | 325 // to enable the close/minimize/maximize buttons of the parent window when |
| 306 // the bubble has key state, so disabling it here is safe. | 326 // the bubble has key state, so disabling it here is safe. |
| 307 InfoBubbleWindow* bubbleWindow = | 327 InfoBubbleWindow* bubbleWindow = |
| 308 base::mac::ObjCCastStrict<InfoBubbleWindow>([self window]); | 328 base::mac::ObjCCastStrict<InfoBubbleWindow>([self window]); |
| 309 [bubbleWindow setAllowShareParentKeyState:NO]; | 329 [bubbleWindow setAllowShareParentKeyState:NO]; |
| (...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 362 if (![[notif object] isSheet] && | 382 if (![[notif object] isSheet] && |
| 363 [NSApp keyWindow] != [self window]) | 383 [NSApp keyWindow] != [self window]) |
| 364 [self windowDidResignKey:note]; | 384 [self windowDidResignKey:note]; |
| 365 }]; | 385 }]; |
| 366 } | 386 } |
| 367 | 387 |
| 368 // By implementing this, ESC causes the window to go away. | 388 // By implementing this, ESC causes the window to go away. |
| 369 - (IBAction)cancel:(id)sender { | 389 - (IBAction)cancel:(id)sender { |
| 370 // This is not a "real" cancel as potential changes to the radio group are not | 390 // This is not a "real" cancel as potential changes to the radio group are not |
| 371 // undone. That's ok. | 391 // undone. That's ok. |
| 372 [self close]; | 392 [self closeBubbleWithReason:BUBBLE_CLOSE_CANCELED]; |
| 373 } | 393 } |
| 374 | 394 |
| 375 // Takes the |anchor_| point and adjusts the window's origin accordingly. | 395 // Takes the |anchor_| point and adjusts the window's origin accordingly. |
| 376 - (void)updateOriginFromAnchor { | 396 - (void)updateOriginFromAnchor { |
| 377 NSWindow* window = [self window]; | 397 NSWindow* window = [self window]; |
| 378 NSPoint origin = anchor_; | 398 NSPoint origin = anchor_; |
| 379 | 399 |
| 380 switch ([bubble_ alignment]) { | 400 switch ([bubble_ alignment]) { |
| 381 case info_bubble::kAlignArrowToAnchor: { | 401 case info_bubble::kAlignArrowToAnchor: { |
| 382 NSSize offsets = NSMakeSize(info_bubble::kBubbleArrowXOffset + | 402 NSSize offsets = NSMakeSize(info_bubble::kBubbleArrowXOffset + |
| (...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 422 | 442 |
| 423 origin.y -= NSHeight([window frame]); | 443 origin.y -= NSHeight([window frame]); |
| 424 [window setFrameOrigin:origin]; | 444 [window setFrameOrigin:origin]; |
| 425 } | 445 } |
| 426 | 446 |
| 427 - (void)activateTabWithContents:(content::WebContents*)newContents | 447 - (void)activateTabWithContents:(content::WebContents*)newContents |
| 428 previousContents:(content::WebContents*)oldContents | 448 previousContents:(content::WebContents*)oldContents |
| 429 atIndex:(NSInteger)index | 449 atIndex:(NSInteger)index |
| 430 reason:(int)reason { | 450 reason:(int)reason { |
| 431 // The user switched tabs; close. | 451 // The user switched tabs; close. |
| 432 [self close]; | 452 [self closeBubbleWithoutReason]; |
| 433 } | 453 } |
| 434 | 454 |
| 435 @end // BaseBubbleController | 455 @end // BaseBubbleController |
| OLD | NEW |