Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to start and terminate an application from inside a cocoa application on Mac

Tags:

cocoa

My Cocoa application needs to start and terminate other applications. Please let me know of any example code which can do the following:

  1. Start an application from inside Cocoa code
  2. Terminate an application from inside Cocoa code
like image 845
Anisha Saigal Avatar asked Jan 07 '11 02:01

Anisha Saigal


2 Answers

As previously mentioned it‘s quite easy to launch other applications with the help of the NSWorkspace class, for example:

- (BOOL)launchApplicationWithPath:(NSString *)path
{
    // As recommended for OS X >= 10.6.
    if ([[NSWorkspace sharedWorkspace] respondsToSelector:@selector(launchApplicationAtURL:options:configuration:error:)])
        return nil != [[NSWorkspace sharedWorkspace] launchApplicationAtURL:[NSURL fileURLWithPath:path isDirectory:NO] options:NSWorkspaceLaunchDefault configuration:nil error:NULL];

    // For older systems.
    return [[NSWorkspace sharedWorkspace] launchApplication:path];
}

You have to do a bit more work in order to quit another application, especially if the target is pre-10.6, but it‘s not too hard. Here is an example:

- (BOOL)terminateApplicationWithBundleID:(NSString *)bundleID
{
    // For OS X >= 10.6 NSWorkspace has the nifty runningApplications-method.
    if ([[NSWorkspace sharedWorkspace] respondsToSelector:@selector(runningApplications)])
        for (NSRunningApplication *app in [[NSWorkspace sharedWorkspace] runningApplications])
            if ([bundleID isEqualToString:[app bundleIdentifier]])
                return [app terminate];

    // If that didn‘t work then try using the apple event method, also works for OS X < 10.6.

    AppleEvent event = {typeNull, nil};
    const char *bundleIDString = [bundleID UTF8String];

    OSStatus result = AEBuildAppleEvent(kCoreEventClass, kAEQuitApplication, typeApplicationBundleID, bundleIDString, strlen(bundleIDString), kAutoGenerateReturnID, kAnyTransactionID, &event, NULL, "");

    if (result == noErr) {
        result = AESendMessage(&event, NULL, kAEAlwaysInteract|kAENoReply, kAEDefaultTimeout);
        AEDisposeDesc(&event);
    }
    return result == noErr;
}
like image 109
Fredric Avatar answered Oct 10 '22 19:10

Fredric


Assuming this is targeted for 10.6, you can use NSRunningApplication along with NSWorkspace. First, you should determine if the application is already running using:

[[NSWorkspace sharedWorkspace] runningApplications]

If it's not running, then you can launch it using NSWorkspace, but I recommend the newer call, launchApplicationAtURL:options:configuration:error:, which will return an NSRunningApplication, which you can use to terminate the application. See NSWorkspace for more details.

like image 32
Rob Napier Avatar answered Oct 10 '22 19:10

Rob Napier