changeset 18072:5666d9dcc35a draft

(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
author planetmaker <planetmaker@openttd.org>
date Sun, 04 Sep 2011 17:49:08 +0000
parents bc29668c71a8
children 02b8027eef0b
files src/os/macosx/macos.h src/video/cocoa/cocoa_v.h src/video/cocoa/cocoa_v.mm src/video/cocoa/fullscreen.mm src/video/cocoa/wnd_quartz.mm
diffstat 5 files changed, 91 insertions(+), 7 deletions(-) [+]
line wrap: on
line diff
--- 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);
--- a/src/video/cocoa/cocoa_v.h
+++ b/src/video/cocoa/cocoa_v.h
@@ -88,6 +88,7 @@
 	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;
--- a/src/video/cocoa/cocoa_v.mm
+++ b/src/video/cocoa/cocoa_v.mm
@@ -143,6 +143,11 @@
 	[ 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 @@
  * @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 @@
 	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 @@
 {
 	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();
--- a/src/video/cocoa/fullscreen.mm
+++ b/src/video/cocoa/fullscreen.mm
@@ -309,8 +309,17 @@
 			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 @@
 
 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)) {
--- a/src/video/cocoa/wnd_quartz.mm
+++ b/src/video/cocoa/wnd_quartz.mm
@@ -78,6 +78,7 @@
 	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 @@
 	);
 }
 
+/** 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 @@
 			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];