| OLD | NEW |
| 1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2010 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/cocoa/fullscreen_controller.h" | 5 #import "chrome/browser/cocoa/fullscreen_controller.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 | 8 |
| 9 #import "chrome/browser/cocoa/browser_window_controller.h" | 9 #import "chrome/browser/cocoa/browser_window_controller.h" |
| 10 #import "chrome/browser/cocoa/floating_bar_backing_view.h" |
| 11 #import "chrome/browser/cocoa/fullscreen_window.h" |
| 10 #import "third_party/GTM/AppKit/GTMNSAnimation+Duration.h" | 12 #import "third_party/GTM/AppKit/GTMNSAnimation+Duration.h" |
| 11 | 13 |
| 12 NSString* const kWillEnterFullscreenNotification = | 14 NSString* const kWillEnterFullscreenNotification = |
| 13 @"WillEnterFullscreenNotification"; | 15 @"WillEnterFullscreenNotification"; |
| 14 NSString* const kWillLeaveFullscreenNotification = | 16 NSString* const kWillLeaveFullscreenNotification = |
| 15 @"WillLeaveFullscreenNotification"; | 17 @"WillLeaveFullscreenNotification"; |
| 16 | 18 |
| 17 namespace { | 19 namespace { |
| 18 // The activation zone for the main menu is 4 pixels high; if we make it any | 20 // The activation zone for the main menu is 4 pixels high; if we make it any |
| 19 // smaller, then the menu can be made to appear without the bar sliding down. | 21 // smaller, then the menu can be made to appear without the bar sliding down. |
| (...skipping 140 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 160 | 162 |
| 161 | 163 |
| 162 @implementation FullscreenController | 164 @implementation FullscreenController |
| 163 | 165 |
| 164 @synthesize isFullscreen = isFullscreen_; | 166 @synthesize isFullscreen = isFullscreen_; |
| 165 | 167 |
| 166 - (id)initWithBrowserController:(BrowserWindowController*)controller { | 168 - (id)initWithBrowserController:(BrowserWindowController*)controller { |
| 167 if ((self == [super init])) { | 169 if ((self == [super init])) { |
| 168 browserController_ = controller; | 170 browserController_ = controller; |
| 169 currentFullscreenMode_ = mac_util::kFullScreenModeNormal; | 171 currentFullscreenMode_ = mac_util::kFullScreenModeNormal; |
| 172 |
| 173 NSScreen* screen = [[browserController_ window] screen]; |
| 174 fullscreenWindow_.reset([[FullscreenWindow alloc] initForScreen:screen]); |
| 175 |
| 176 floatingBarBackingView_.reset( |
| 177 [[FloatingBarBackingView alloc] initWithFrame:NSZeroRect]); |
| 170 } | 178 } |
| 171 | 179 |
| 172 // Let the world know what we're up to. | 180 // Let the world know what we're up to. |
| 173 [[NSNotificationCenter defaultCenter] | 181 [[NSNotificationCenter defaultCenter] |
| 174 postNotificationName:kWillEnterFullscreenNotification | 182 postNotificationName:kWillEnterFullscreenNotification |
| 175 object:nil]; | 183 object:nil]; |
| 176 | 184 |
| 177 return self; | 185 return self; |
| 178 } | 186 } |
| 179 | 187 |
| 180 - (void)dealloc { | 188 - (void)dealloc { |
| 181 DCHECK(!isFullscreen_); | 189 DCHECK(!isFullscreen_); |
| 182 DCHECK(!trackingArea_); | 190 DCHECK(!trackingArea_); |
| 183 [super dealloc]; | 191 [super dealloc]; |
| 184 } | 192 } |
| 185 | 193 |
| 186 - (void)enterFullscreenForContentView:(NSView*)contentView | 194 - (void)enterFullscreenForContentView:(NSView*)contentView |
| 187 showDropdown:(BOOL)showDropdown { | 195 showDropdown:(BOOL)showDropdown { |
| 188 DCHECK(!isFullscreen_); | 196 DCHECK(!isFullscreen_); |
| 189 isFullscreen_ = YES; | 197 isFullscreen_ = YES; |
| 190 contentView_ = contentView; | 198 contentView_ = contentView; |
| 191 [self changeFloatingBarShownFraction:(showDropdown ? 1 : 0)]; | 199 [self changeFloatingBarShownFraction:(showDropdown ? 1 : 0)]; |
| 192 | 200 |
| 193 // Register for notifications. Self is removed as an observer in |-cleanup|. | 201 // Register for notifications. Self is removed as an observer in |-cleanup|. |
| 194 NSNotificationCenter* nc = [NSNotificationCenter defaultCenter]; | 202 NSNotificationCenter* nc = [NSNotificationCenter defaultCenter]; |
| 195 NSWindow* window = [browserController_ window]; | |
| 196 [nc addObserver:self | 203 [nc addObserver:self |
| 197 selector:@selector(windowDidChangeScreen:) | 204 selector:@selector(windowDidChangeScreen:) |
| 198 name:NSWindowDidChangeScreenNotification | 205 name:NSWindowDidChangeScreenNotification |
| 199 object:window]; | 206 object:fullscreenWindow_]; |
| 200 | 207 |
| 201 [nc addObserver:self | 208 [nc addObserver:self |
| 202 selector:@selector(windowDidBecomeMain:) | 209 selector:@selector(windowDidBecomeMain:) |
| 203 name:NSWindowDidBecomeMainNotification | 210 name:NSWindowDidBecomeMainNotification |
| 204 object:window]; | 211 object:fullscreenWindow_]; |
| 205 | 212 |
| 206 [nc addObserver:self | 213 [nc addObserver:self |
| 207 selector:@selector(windowDidResignMain:) | 214 selector:@selector(windowDidResignMain:) |
| 208 name:NSWindowDidResignMainNotification | 215 name:NSWindowDidResignMainNotification |
| 209 object:window]; | 216 object:fullscreenWindow_]; |
| 210 } | 217 } |
| 211 | 218 |
| 212 - (void)exitFullscreen { | 219 - (void)exitFullscreen { |
| 213 [[NSNotificationCenter defaultCenter] | 220 [[NSNotificationCenter defaultCenter] |
| 214 postNotificationName:kWillLeaveFullscreenNotification | 221 postNotificationName:kWillLeaveFullscreenNotification |
| 215 object:nil]; | 222 object:nil]; |
| 216 DCHECK(isFullscreen_); | 223 DCHECK(isFullscreen_); |
| 217 [self cleanup]; | 224 [self cleanup]; |
| 218 isFullscreen_ = NO; | 225 isFullscreen_ = NO; |
| 219 } | 226 } |
| 220 | 227 |
| 228 - (FullscreenWindow*)window { |
| 229 return fullscreenWindow_.get(); |
| 230 } |
| 231 |
| 232 - (BOOL)hasFloatingBarBackingView { |
| 233 return floatingBarBackingView_.get() != nil; |
| 234 } |
| 235 |
| 236 - (NSView*)floatingBarBackingView { |
| 237 return floatingBarBackingView_.get(); |
| 238 } |
| 239 |
| 221 - (void)windowDidChangeScreen:(NSNotification*)notification { | 240 - (void)windowDidChangeScreen:(NSNotification*)notification { |
| 222 [browserController_ resizeFullscreenWindow]; | 241 [browserController_ resizeFullscreenWindow]; |
| 223 } | 242 } |
| 224 | 243 |
| 225 - (void)windowDidBecomeMain:(NSNotification*)notification { | 244 - (void)windowDidBecomeMain:(NSNotification*)notification { |
| 226 [self showActiveWindowUI]; | 245 [self showActiveWindowUI]; |
| 227 } | 246 } |
| 228 | 247 |
| 229 - (void)windowDidResignMain:(NSNotification*)notification { | 248 - (void)windowDidResignMain:(NSNotification*)notification { |
| 230 [self hideActiveWindowUI]; | 249 [self hideActiveWindowUI]; |
| (...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 293 } | 312 } |
| 294 } | 313 } |
| 295 | 314 |
| 296 - (void)cancelAnimationAndTimers { | 315 - (void)cancelAnimationAndTimers { |
| 297 [self cancelAllTimers]; | 316 [self cancelAllTimers]; |
| 298 [currentAnimation_ stopAnimation]; | 317 [currentAnimation_ stopAnimation]; |
| 299 currentAnimation_.reset(); | 318 currentAnimation_.reset(); |
| 300 } | 319 } |
| 301 | 320 |
| 302 - (CGFloat)floatingBarShownFraction { | 321 - (CGFloat)floatingBarShownFraction { |
| 303 return [browserController_ floatingBarShownFraction]; | 322 return floatingBarShownFraction_; |
| 304 } | 323 } |
| 305 | 324 |
| 306 - (void)changeFloatingBarShownFraction:(CGFloat)fraction { | 325 - (void)changeFloatingBarShownFraction:(CGFloat)fraction { |
| 307 [browserController_ setFloatingBarShownFraction:fraction]; | 326 floatingBarShownFraction_ = fraction; |
| 308 | 327 |
| 309 mac_util::FullScreenMode desiredMode = [self desiredFullscreenMode]; | 328 mac_util::FullScreenMode desiredMode = [self desiredFullscreenMode]; |
| 310 if (desiredMode != currentFullscreenMode_ && [self shouldToggleMenuBar]) { | 329 if (desiredMode != currentFullscreenMode_ && [self shouldToggleMenuBar]) { |
| 311 if (currentFullscreenMode_ == mac_util::kFullScreenModeNormal) | 330 if (currentFullscreenMode_ == mac_util::kFullScreenModeNormal) |
| 312 mac_util::RequestFullScreen(desiredMode); | 331 mac_util::RequestFullScreen(desiredMode); |
| 313 else | 332 else |
| 314 mac_util::SwitchFullScreenModes(currentFullscreenMode_, desiredMode); | 333 mac_util::SwitchFullScreenModes(currentFullscreenMode_, desiredMode); |
| 315 currentFullscreenMode_ = desiredMode; | 334 currentFullscreenMode_ = desiredMode; |
| 316 } | 335 } |
| 336 |
| 337 [browserController_ floatingBarShownFractionChanged]; |
| 317 } | 338 } |
| 318 | 339 |
| 319 // Used to activate the floating bar in fullscreen mode. | 340 // Used to activate the floating bar in fullscreen mode. |
| 320 - (void)mouseEntered:(NSEvent*)event { | 341 - (void)mouseEntered:(NSEvent*)event { |
| 321 DCHECK(isFullscreen_); | 342 DCHECK(isFullscreen_); |
| 322 | 343 |
| 323 // Having gotten a mouse entered, we no longer need to do exit checks. | 344 // Having gotten a mouse entered, we no longer need to do exit checks. |
| 324 [self cancelMouseExitCheck]; | 345 [self cancelMouseExitCheck]; |
| 325 | 346 |
| 326 NSTrackingArea* trackingArea = [event trackingArea]; | 347 NSTrackingArea* trackingArea = [event trackingArea]; |
| (...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 379 if (![self mouseInsideTrackingRect]) | 400 if (![self mouseInsideTrackingRect]) |
| 380 [self scheduleHideForMouse]; | 401 [self scheduleHideForMouse]; |
| 381 } | 402 } |
| 382 | 403 |
| 383 @end | 404 @end |
| 384 | 405 |
| 385 | 406 |
| 386 @implementation FullscreenController (PrivateMethods) | 407 @implementation FullscreenController (PrivateMethods) |
| 387 | 408 |
| 388 - (BOOL)isWindowOnPrimaryScreen { | 409 - (BOOL)isWindowOnPrimaryScreen { |
| 389 NSScreen* screen = [[browserController_ window] screen]; | 410 NSScreen* screen = [fullscreenWindow_ screen]; |
| 390 NSScreen* primaryScreen = [[NSScreen screens] objectAtIndex:0]; | 411 NSScreen* primaryScreen = [[NSScreen screens] objectAtIndex:0]; |
| 391 return (screen == primaryScreen); | 412 return (screen == primaryScreen); |
| 392 } | 413 } |
| 393 | 414 |
| 394 - (BOOL)shouldToggleMenuBar { | 415 - (BOOL)shouldToggleMenuBar { |
| 395 return [self isWindowOnPrimaryScreen] && | 416 return [self isWindowOnPrimaryScreen] && [fullscreenWindow_ isMainWindow]; |
| 396 [[browserController_ window] isMainWindow]; | |
| 397 } | 417 } |
| 398 | 418 |
| 399 - (mac_util::FullScreenMode)desiredFullscreenMode { | 419 - (mac_util::FullScreenMode)desiredFullscreenMode { |
| 400 if ([browserController_ floatingBarShownFraction] >= 1.0) | 420 if (floatingBarShownFraction_ >= 1.0) |
| 401 return mac_util::kFullScreenModeHideDock; | 421 return mac_util::kFullScreenModeHideDock; |
| 402 return mac_util::kFullScreenModeHideAll; | 422 return mac_util::kFullScreenModeHideAll; |
| 403 } | 423 } |
| 404 | 424 |
| 405 - (void)changeOverlayToFraction:(CGFloat)fraction | 425 - (void)changeOverlayToFraction:(CGFloat)fraction |
| 406 withAnimation:(BOOL)animate { | 426 withAnimation:(BOOL)animate { |
| 407 // The non-animated case is really simple, so do it and return. | 427 // The non-animated case is really simple, so do it and return. |
| 408 if (!animate) { | 428 if (!animate) { |
| 409 [currentAnimation_ stopAnimation]; | 429 [currentAnimation_ stopAnimation]; |
| 410 [self changeFloatingBarShownFraction:fraction]; | 430 [self changeFloatingBarShownFraction:fraction]; |
| 411 return; | 431 return; |
| 412 } | 432 } |
| 413 | 433 |
| 414 // If we're already animating to the given fraction, then there's nothing more | 434 // If we're already animating to the given fraction, then there's nothing more |
| 415 // to do. | 435 // to do. |
| 416 if (currentAnimation_ && [currentAnimation_ endFraction] == fraction) | 436 if (currentAnimation_ && [currentAnimation_ endFraction] == fraction) |
| 417 return; | 437 return; |
| 418 | 438 |
| 419 // In all other cases, we want to cancel any running animation (which may be | 439 // In all other cases, we want to cancel any running animation (which may be |
| 420 // to show or to hide). | 440 // to show or to hide). |
| 421 [currentAnimation_ stopAnimation]; | 441 [currentAnimation_ stopAnimation]; |
| 422 | 442 |
| 423 // Now, if it happens to already be in the right state, there's nothing more | 443 // Now, if it happens to already be in the right state, there's nothing more |
| 424 // to do. | 444 // to do. |
| 425 if ([browserController_ floatingBarShownFraction] == fraction) | 445 if (floatingBarShownFraction_ == fraction) |
| 426 return; | 446 return; |
| 427 | 447 |
| 428 // Create the animation and set it up. | 448 // Create the animation and set it up. |
| 429 currentAnimation_.reset( | 449 currentAnimation_.reset( |
| 430 [[DropdownAnimation alloc] initWithFraction:fraction | 450 [[DropdownAnimation alloc] initWithFraction:fraction |
| 431 fullDuration:kDropdownAnimationDuration | 451 fullDuration:kDropdownAnimationDuration |
| 432 animationCurve:NSAnimationEaseOut | 452 animationCurve:NSAnimationEaseOut |
| 433 controller:self]); | 453 controller:self]); |
| 434 DCHECK(currentAnimation_); | 454 DCHECK(currentAnimation_); |
| 435 [currentAnimation_ setAnimationBlockingMode:NSAnimationNonblocking]; | 455 [currentAnimation_ setAnimationBlockingMode:NSAnimationNonblocking]; |
| (...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 478 | 498 |
| 479 - (void)removeTrackingAreaIfNecessary { | 499 - (void)removeTrackingAreaIfNecessary { |
| 480 if (trackingArea_) { | 500 if (trackingArea_) { |
| 481 DCHECK(contentView_); // |contentView_| better be valid. | 501 DCHECK(contentView_); // |contentView_| better be valid. |
| 482 [contentView_ removeTrackingArea:trackingArea_]; | 502 [contentView_ removeTrackingArea:trackingArea_]; |
| 483 trackingArea_.reset(); | 503 trackingArea_.reset(); |
| 484 } | 504 } |
| 485 } | 505 } |
| 486 | 506 |
| 487 - (BOOL)mouseInsideTrackingRect { | 507 - (BOOL)mouseInsideTrackingRect { |
| 488 NSWindow* window = [browserController_ window]; | 508 NSPoint mouseLoc = [fullscreenWindow_ mouseLocationOutsideOfEventStream]; |
| 489 NSPoint mouseLoc = [window mouseLocationOutsideOfEventStream]; | |
| 490 NSPoint mousePos = [contentView_ convertPoint:mouseLoc fromView:nil]; | 509 NSPoint mousePos = [contentView_ convertPoint:mouseLoc fromView:nil]; |
| 491 return NSMouseInRect(mousePos, trackingAreaBounds_, [contentView_ isFlipped]); | 510 return NSMouseInRect(mousePos, trackingAreaBounds_, [contentView_ isFlipped]); |
| 492 } | 511 } |
| 493 | 512 |
| 494 - (void)setupMouseExitCheck { | 513 - (void)setupMouseExitCheck { |
| 495 [self performSelector:@selector(checkForMouseExit) | 514 [self performSelector:@selector(checkForMouseExit) |
| 496 withObject:nil | 515 withObject:nil |
| 497 afterDelay:kMouseExitCheckDelay]; | 516 afterDelay:kMouseExitCheckDelay]; |
| 498 } | 517 } |
| 499 | 518 |
| (...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 587 // This isn't tracked when not in fullscreen mode. | 606 // This isn't tracked when not in fullscreen mode. |
| 588 [browserController_ releaseBarVisibilityForOwner:self | 607 [browserController_ releaseBarVisibilityForOwner:self |
| 589 withAnimation:NO | 608 withAnimation:NO |
| 590 delay:NO]; | 609 delay:NO]; |
| 591 | 610 |
| 592 // Call the main status resignation code to perform the associated cleanup, | 611 // Call the main status resignation code to perform the associated cleanup, |
| 593 // since we will no longer be receiving actual status resignation | 612 // since we will no longer be receiving actual status resignation |
| 594 // notifications. | 613 // notifications. |
| 595 [self hideActiveWindowUI]; | 614 [self hideActiveWindowUI]; |
| 596 | 615 |
| 616 // Just in case. |
| 617 [floatingBarBackingView_ removeFromSuperview]; |
| 618 |
| 597 // No more calls back up to the BWC. | 619 // No more calls back up to the BWC. |
| 598 browserController_ = nil; | 620 browserController_ = nil; |
| 599 } | 621 } |
| 600 | 622 |
| 601 - (void)showActiveWindowUI { | 623 - (void)showActiveWindowUI { |
| 602 DCHECK_EQ(currentFullscreenMode_, mac_util::kFullScreenModeNormal); | 624 DCHECK_EQ(currentFullscreenMode_, mac_util::kFullScreenModeNormal); |
| 603 if (currentFullscreenMode_ != mac_util::kFullScreenModeNormal) | 625 if (currentFullscreenMode_ != mac_util::kFullScreenModeNormal) |
| 604 return; | 626 return; |
| 605 | 627 |
| 606 if ([self shouldToggleMenuBar]) { | 628 if ([self shouldToggleMenuBar]) { |
| 607 mac_util::FullScreenMode desiredMode = [self desiredFullscreenMode]; | 629 mac_util::FullScreenMode desiredMode = [self desiredFullscreenMode]; |
| 608 mac_util::RequestFullScreen(desiredMode); | 630 mac_util::RequestFullScreen(desiredMode); |
| 609 currentFullscreenMode_ = desiredMode; | 631 currentFullscreenMode_ = desiredMode; |
| 610 } | 632 } |
| 611 | 633 |
| 612 // TODO(rohitrao): Insert the Exit Fullscreen button. http://crbug.com/35956 | 634 // TODO(rohitrao): Insert the Exit Fullscreen button. http://crbug.com/35956 |
| 613 } | 635 } |
| 614 | 636 |
| 615 - (void)hideActiveWindowUI { | 637 - (void)hideActiveWindowUI { |
| 616 if (currentFullscreenMode_ != mac_util::kFullScreenModeNormal) { | 638 if (currentFullscreenMode_ != mac_util::kFullScreenModeNormal) { |
| 617 mac_util::ReleaseFullScreen(currentFullscreenMode_); | 639 mac_util::ReleaseFullScreen(currentFullscreenMode_); |
| 618 currentFullscreenMode_ = mac_util::kFullScreenModeNormal; | 640 currentFullscreenMode_ = mac_util::kFullScreenModeNormal; |
| 619 } | 641 } |
| 620 | 642 |
| 621 // TODO(rohitrao): Remove the Exit Fullscreen button. http://crbug.com/35956 | 643 // TODO(rohitrao): Remove the Exit Fullscreen button. http://crbug.com/35956 |
| 622 } | 644 } |
| 623 | 645 |
| 624 @end | 646 @end |
| OLD | NEW |