summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRĂ©mi Verschelde <rverschelde@gmail.com>2018-03-03 12:53:01 +0100
committerGitHub <noreply@github.com>2018-03-03 12:53:01 +0100
commit26d42cd9a4fb533a1682fcda6ca57a3943a7ce0e (patch)
treebb75d37fa17b892da0f8a824e36a2153997e6bc3
parent618b22bbec68bd2fbabef879007bb4f682d101b5 (diff)
parent506e17ee7075b107b96cc52854b72c9f2bc3014f (diff)
Merge pull request #17187 from bruvzg/macos_unbundled_app_focus_hack
[macOS] Hack to force window activation for non-bundled app.
-rw-r--r--platform/osx/os_osx.mm36
1 files changed, 35 insertions, 1 deletions
diff --git a/platform/osx/os_osx.mm b/platform/osx/os_osx.mm
index 049191c7de..f530da8b71 100644
--- a/platform/osx/os_osx.mm
+++ b/platform/osx/os_osx.mm
@@ -150,10 +150,44 @@ static Vector2 get_mouse_pos(NSEvent *event) {
@end
@interface GodotApplicationDelegate : NSObject
+- (void)forceUnbundledWindowActivationHackStep1;
+- (void)forceUnbundledWindowActivationHackStep2;
+- (void)forceUnbundledWindowActivationHackStep3;
@end
@implementation GodotApplicationDelegate
+- (void)forceUnbundledWindowActivationHackStep1 {
+ // Step1: Switch focus to macOS Dock.
+ // Required to perform step 2, TransformProcessType will fail if app is already the in focus.
+ for (NSRunningApplication *app in [NSRunningApplication runningApplicationsWithBundleIdentifier:@"com.apple.dock"]) {
+ [app activateWithOptions:NSApplicationActivateIgnoringOtherApps];
+ break;
+ }
+ [self performSelector:@selector(forceUnbundledWindowActivationHackStep2) withObject:nil afterDelay:0.02];
+}
+
+- (void)forceUnbundledWindowActivationHackStep2 {
+ // Step 2: Register app as foreground process.
+ ProcessSerialNumber psn = { 0, kCurrentProcess };
+ (void)TransformProcessType(&psn, kProcessTransformToForegroundApplication);
+
+ [self performSelector:@selector(forceUnbundledWindowActivationHackStep3) withObject:nil afterDelay:0.02];
+}
+
+- (void)forceUnbundledWindowActivationHackStep3 {
+ // Step 3: Switch focus back to app window.
+ [[NSRunningApplication currentApplication] activateWithOptions:NSApplicationActivateIgnoringOtherApps];
+}
+
+- (void)applicationDidFinishLaunching:(NSNotification *)notice {
+ NSString *nsappname = [[[NSBundle mainBundle] infoDictionary] objectForKey:@"CFBundleName"];
+ if (nsappname == nil) {
+ // If executable is not a bundled, macOS WindowServer won't register and activate app window correctly (menu and title bar are grayed out and input ignored).
+ [self performSelector:@selector(forceUnbundledWindowActivationHackStep1) withObject:nil afterDelay:0.02];
+ }
+}
+
- (BOOL)application:(NSApplication *)sender openFile:(NSString *)filename {
// Note: called before main loop init!
char *utfs = strdup([filename UTF8String]);
@@ -2340,7 +2374,7 @@ OS_OSX::OS_OSX() {
NSMenuItem *menu_item;
NSString *title;
- NSString *nsappname = [[[NSBundle mainBundle] performSelector:@selector(localizedInfoDictionary)] objectForKey:@"CFBundleName"];
+ NSString *nsappname = [[[NSBundle mainBundle] infoDictionary] objectForKey:@"CFBundleName"];
if (nsappname == nil)
nsappname = [[NSProcessInfo processInfo] processName];