From 350812a90a93e7fd45dcfda2fa192347e0a4359d Mon Sep 17 00:00:00 2001 From: planetmaker Date: Sun, 4 Sep 2011 17:49:08 +0000 Subject: [PATCH] (svn r22893) -Fix [FS#4744]: [OSX] Compilation on OSX 10.7 was broken (based on patch by leecbaker) -Add: [OSX] Support for fullscreen mode when compiled against SDK 10.7. Otherwise fullscreen mode is disabled when OpenTTD is run on OSX Lion --- src/os/macosx/macos.h | 8 ++++++++ src/video/cocoa/cocoa_v.h | 1 + src/video/cocoa/cocoa_v.mm | 30 +++++++++++++++++++++++----- src/video/cocoa/fullscreen.mm | 22 +++++++++++++++++++-- src/video/cocoa/wnd_quartz.mm | 37 +++++++++++++++++++++++++++++++++++ 5 files changed, 91 insertions(+), 7 deletions(-) diff --git a/src/os/macosx/macos.h b/src/os/macosx/macos.h index b30cc8fce9..d147dfb0b0 100644 --- a/src/os/macosx/macos.h +++ b/src/os/macosx/macos.h @@ -29,6 +29,14 @@ #define MAC_OS_X_VERSION_10_6 1060 #endif +#ifndef MAC_OS_X_VERSION_10_7 +#define MAC_OS_X_VERSION_10_7 1070 +#endif + +#ifndef MAC_OS_X_VERSION_10_8 +#define MAC_OS_X_VERSION_10_8 1080 +#endif + /** Helper function displaying a message the best possible way. */ void ShowMacDialog(const char *title, const char *message, const char *button_label); diff --git a/src/video/cocoa/cocoa_v.h b/src/video/cocoa/cocoa_v.h index 087b2072c1..498f40cbb8 100644 --- a/src/video/cocoa/cocoa_v.h +++ b/src/video/cocoa/cocoa_v.h @@ -88,6 +88,7 @@ public: virtual bool ChangeResolution(int w, int h) = 0; virtual bool IsFullscreen() = 0; + virtual bool ToggleFullscreen() { return false; }; virtual int GetWidth() = 0; virtual int GetHeight() = 0; virtual void *GetPixelBuffer() = 0; diff --git a/src/video/cocoa/cocoa_v.mm b/src/video/cocoa/cocoa_v.mm index 8be3e87258..434de5994b 100644 --- a/src/video/cocoa/cocoa_v.mm +++ b/src/video/cocoa/cocoa_v.mm @@ -143,6 +143,11 @@ static void setupWindowMenu() [ menuItem setSubmenu:windowMenu ]; [ [ NSApp mainMenu ] addItem:menuItem ]; + if(MacOSVersionIsAtLeast(10, 7, 0)) { + /* The OS will change the name of this menu item automatically */ + [ windowMenu addItemWithTitle:@"Fullscreen" action:@selector(toggleFullScreen:) keyEquivalent:@"^f" ]; + } + /* Tell the application object that this is now the window menu */ [ NSApp setWindowsMenu:windowMenu ]; @@ -273,15 +278,27 @@ static CocoaSubdriver *QZ_CreateWindowSubdriver(int width, int height, int bpp) * @param width Width of display area. * @param height Height of display area. * @param bpp Colour depth of display area. - * @param fullscreen Wether a fullscreen mode is requested. + * @param fullscreen Whether a fullscreen mode is requested. * @param fallback Whether we look for a fallback driver. - * @return Pointer to subdriver. * @return Pointer to window subdriver. */ static CocoaSubdriver *QZ_CreateSubdriver(int width, int height, int bpp, bool fullscreen, bool fallback) { - CocoaSubdriver *ret = fullscreen ? QZ_CreateFullscreenSubdriver(width, height, bpp) : QZ_CreateWindowSubdriver(width, height, bpp); - if (ret != NULL) return ret; + CocoaSubdriver *ret = NULL; + /* OSX 10.7 allows to toggle fullscreen mode differently */ + if (MacOSVersionIsAtLeast(10, 7, 0)) { + ret = QZ_CreateWindowSubdriver(width, height, bpp); + } else { + ret = fullscreen ? QZ_CreateFullscreenSubdriver(width, height, bpp) : QZ_CreateWindowSubdriver(width, height, bpp); + } + + if (ret != NULL) { + /* We cannot set any fullscreen mode on OSX 10.7 when not compiled against SDK 10.7 */ +#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_7 + if (fullscreen) { ret->ToggleFullscreen(); } +#endif + return ret; + } if (!fallback) return NULL; @@ -290,7 +307,7 @@ static CocoaSubdriver *QZ_CreateSubdriver(int width, int height, int bpp, bool f ret = QZ_CreateWindowSubdriver(640, 480, bpp); if (ret != NULL) return ret; -#ifdef _DEBUG +#ifdef _DEBUG && (MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_7) /* Try fullscreen too when in debug mode */ DEBUG(driver, 0, "Setting video mode failed, falling back to 640x480 fullscreen mode."); ret = QZ_CreateFullscreenSubdriver(640, 480, bpp); @@ -402,6 +419,9 @@ bool VideoDriver_Cocoa::ToggleFullscreen(bool full_screen) { assert(_cocoa_subdriver != NULL); + /* For 10.7 and later, we try to toggle using the quartz subdriver. */ + if (_cocoa_subdriver->ToggleFullscreen()) return true; + bool oldfs = _cocoa_subdriver->IsFullscreen(); if (full_screen != oldfs) { int width = _cocoa_subdriver->GetWidth(); diff --git a/src/video/cocoa/fullscreen.mm b/src/video/cocoa/fullscreen.mm index aa28422d3b..56bcc580d1 100644 --- a/src/video/cocoa/fullscreen.mm +++ b/src/video/cocoa/fullscreen.mm @@ -309,8 +309,17 @@ class FullscreenSubdriver: public CocoaSubdriver { goto ERR_NO_SWITCH; } - this->window_buffer = CGDisplayBaseAddress(this->display_id); - this->window_pitch = CGDisplayBytesPerRow(this->display_id); + /* Since CGDisplayBaseAddress and CGDisplayBytesPerRow are no longer available on 10.7, + * disable until a replacement can be found. */ + if (MacOSVersionIsAtLeast(10, 7, 0)) { + this->window_buffer = NULL; + this->window_pitch = NULL; + } else { +#if (MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_7) + this->window_buffer = CGDisplayBaseAddress(this->display_id); + this->window_pitch = CGDisplayBytesPerRow(this->display_id); +#endif + } this->device_width = CGDisplayPixelsWide(this->display_id); this->device_height = CGDisplayPixelsHigh(this->display_id); @@ -565,6 +574,15 @@ public: CocoaSubdriver *QZ_CreateFullscreenSubdriver(int width, int height, int bpp) { + /* OSX 10.7 doesn't support this way of the fullscreen driver. If we end up here + * OpenTTD was compiled without SDK 10.7 available and - and thus we don't support + * fullscreen mode in OSX 10.7 or higher, as necessary elements for this way have + * been removed from the API. + */ + if (MacOSVersionIsAtLeast(10, 7, 0)) { + return NULL; + } + FullscreenSubdriver *ret = new FullscreenSubdriver(bpp); if (!ret->ChangeResolution(width, height)) { diff --git a/src/video/cocoa/wnd_quartz.mm b/src/video/cocoa/wnd_quartz.mm index 0f2b4b0adb..356b7ac7ec 100644 --- a/src/video/cocoa/wnd_quartz.mm +++ b/src/video/cocoa/wnd_quartz.mm @@ -78,6 +78,7 @@ public: virtual bool ChangeResolution(int w, int h); virtual bool IsFullscreen() { return false; } + virtual bool ToggleFullscreen(); /* Full screen mode on OSX 10.7 */ virtual int GetWidth() { return window_width; } virtual int GetHeight() { return window_height; } @@ -220,6 +221,19 @@ void WindowQuartzSubdriver::GetDeviceInfo() ); } +/** Switch to full screen mode on OSX 10.7 + * @return Whether we switched to full screen + */ +bool WindowQuartzSubdriver::ToggleFullscreen() +{ +#if (MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_7) + [this->window toggleFullScreen:this->window]; + return true; +#else + return false; +#endif +} + bool WindowQuartzSubdriver::SetVideoMode(int width, int height) { this->setup = true; @@ -252,6 +266,29 @@ bool WindowQuartzSubdriver::SetVideoMode(int width, int height) return false; } + /* Add built in full-screen support when available (OS X 10.7 and higher) + * This code actually compiles for 10.5 and later, but only makes sense in conjunction + * with the quartz fullscreen support as found only in 10.7 and later + */ +#if (MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_7) + if ([this->window respondsToSelector:@selector(toggleFullScreen:)]) { + /* Constants needed to build on pre-10.7 systems. Source: NSWindow documentation. */ + const int NSWindowCollectionBehaviorFullScreenPrimary = 1 << 7; + const int NSWindowFullScreenButton = 7; + + NSWindowCollectionBehavior behavior = [this->window collectionBehavior]; + behavior |= NSWindowCollectionBehaviorFullScreenPrimary; + [window setCollectionBehavior:behavior]; + + NSButton* fullscreenButton = + [this->window standardWindowButton:NSWindowFullScreenButton]; + [fullscreenButton setAction:@selector(toggleFullScreen:)]; + [fullscreenButton setTarget:this->window]; + + [this->window setCollectionBehavior: NSWindowCollectionBehaviorFullScreenPrimary]; + } +#endif + [ this->window setDriver:this ]; char caption[50];