macOS开发 开机自动启动

简介

建议不要默认就开启自启动,可以放到设置中,让用户自己选择开启/关闭。
Mac OS上运行的App,想要支持用户登录后App自动启动的功能,可以使用Service Management Framework 或 Shared File List实现。对于沙箱开启的应用,苹果推荐的做法是使用Service Management Framework;对于沙箱未开启的应用,苹果推荐使用Shared File List。Service Management Framework对于沙箱未开启的APP也是可以实现登录后自动启动的。二者的区别主要如下:

.使用Service Management Framework方式添加的登录项不会显示在系统偏好设置->用户与群组->登录项中,只有把应用.app文件移到废纸篓,自动启动才会失效。
.使用System Preferences方式添加的登录项会显示在系统偏好设置->用户与群组->登录项中,因此可以勾选隐藏按钮来控制自动启动的功能是否生效。

以下是Service Management Framework的实现方式

步骤

1.在主项目中添加target

我们需要注册一个Helper Target App用来作为开机自启动我们的NeewerLiveProject(主项目),点击Targets下面的加号,添加一个新的OS X APP。取名为NeewerLiveHelper(帮助项目)
在这里插入图片描述

2.分别开启NeewerLiveProject和NeewerLiveHelper的App Sandbox,注意两边的设置要一致

在这里插入图片描述

3.配置属性

  1. 删除NeewerLiveHelper(帮助项目)中的windows,让它没有可展示的Window。
    在这里插入图片描述

  2. 设置NeewerLiveHelper(帮助项目)的Info中Application is background only为YES
    在这里插入图片描述

  3. 在NeewerLiveProject(主项目)中添加CopyFile到Contents/Library/LoginItems
    在这里插入图片描述
    在这里插入图片描述

  4. 在NeewerLiveProject(主项目)中设置Build Setting 下Strip Debug Symbols During Copy为NO, 这个是默认的为No

  5. 在NeewerLiveProject(主项目)链接所需要的库Cocoa.framwork 和ServiceManagerment.framework

4.代码添加

  1. 主项目NeewerLiveProject AppDelegate方法中
- (void)applicationDidFinishLaunching:(NSNotification *)aNotification {
	//在启动主项目的时候 发送通知 关闭帮助程序
  	 [[NSDistributedNotificationCenter defaultCenter]postNotificationName:@"TerminateAppHelperNotificationName" object:[NSBundle mainBundle].bundleIdentifier];
}
  1. 主项目NeewerLiveProject 控制自启动的开关方法中
//根据开关状态控制是否启动自启动
- (void) setAppAutoStart:(BOOL) isAutoStart
{
   //这里注意改成自己的帮助工程名称
    NSString *helperPath = [[[NSBundle mainBundle] bundlePath] stringByAppendingPathComponent:@"Contents/Library/LoginItems/帮助工程.app"];
    if (![[NSFileManager defaultManager] fileExistsAtPath:helperPath])
    {
        return;
    }
    NSURL *helperUrl = [NSURL fileURLWithPath:helperPath];
    // Registering helper app
    if (LSRegisterURL((__bridge CFURLRef)helperUrl, true) != noErr)
    {
        NSLog(@"LSRegisterURL failed!");
    }
    // 这里是帮助项目的bundle identifier
    //SMLoginItemSetEnabled注册开机自启动项 传入两个参数 第一个帮助程序可执行包的标识符。第二个表示辅助可执行文件状态的布尔值。该值仅对当前登录的用户有效。如果YES,帮助工具可立即执行(并在后续登录时)并保持运行。如果NO,辅助可执行文件停止。
    if (!SMLoginItemSetEnabled((CFStringRef)@"helper.bunduleID",isAutoStart))
    {
        NSLog(@"SMLoginItemSetEnabled failed!");
    }
    BOOL alreadRunning = NO;
    NSArray *runnings = [NSWorkspace sharedWorkspace].runningApplications;
    for (NSRunningApplication *app in runnings) {
    	//这里是帮助项目的bundle identifier
        if ([app.bundleIdentifier isEqualToString:@"helper.bunduleID"]) {
            alreadRunning = YES;
            break;
        }
    }
    if (alreadRunning) {
		//发送终止帮助程序的通知
        [[NSDistributedNotificationCenter defaultCenter]postNotificationName:@"TerminateAppHelperNotificationName" object:[NSBundle mainBundle].bundleIdentifier];
    }
    
}
  1. 在帮助项目NeewerLiveHelper AppDelegate方法中
- (void)applicationDidFinishLaunching:(NSNotification *)aNotification {
		//主项目的bundle identifier
    	NSString *mainAPP = @"mainApp.bunduleID";
    	BOOL alreadRunning = NO;
     	NSArray *runnings = [NSWorkspace sharedWorkspace].runningApplications;
     	for (NSRunningApplication *app in runnings) {
         if ([app.bundleIdentifier isEqualToString:mainAPP]) {
             alreadRunning = YES;
             break;
         }
     	}
     if (!alreadRunning) {
		//这里是注册的关闭帮助程序的通知监听
         [[NSDistributedNotificationCenter defaultCenter] addObserver:self
                                                             selector:@selector(terminate) name:@"TerminateAppHelperNotificationName" object:mainAPP];
         
         NSString *appPath = [[NSBundle mainBundle] bundlePath];
		//这里是帮助程序的路径
         appPath = [appPath stringByReplacingOccurrencesOfString:@"/Contents/Library/LoginItems/帮助程序.app" withString:@""];
		//这里是主程序的路径
         appPath = [appPath stringByAppendingPathComponent:@"Contents/MacOS/NeewerLiveProject(主程序)"];
         if (![[NSFileManager defaultManager] fileExistsAtPath:appPath])
         {
             return;
         }
         [[NSWorkspace sharedWorkspace] launchApplication:appPath];
     }else{
         [self terminate];
     }
 }

 - (void)terminate{
     [NSApp terminate:nil];
 }

5.测试

运行程序,打开自己项目中自动启动的开关。接下来就可以重新启动电脑看应用程序是否重启成功。

.在终端输入命令查看自启动是否注册成功 launchctl print-disabled “user/$(id -u)”

特别注意

1.打包测试,主程序必须移到Application目录下
在这里插入图片描述
2.需要把电脑内的所有的主程序包删除掉,避免路径冲突造成自启动失败
例如

.~Library/Developer/Xcode/Archives中的包
.~Library/Developer/Xcode/DerivedData中的包
.下载文件中的包
.废纸篓中的包

3.以下还未得到验证
在发布app时,遇到因为使用了testHelper证书而导致上传到app store时的错误,这时需要深入到“…/Products/Applications/test.app/Contents/Library/LoginItems/testHelper.app/Contents”目录下,删除embedded.provisionprofile文件,就可以正确上传了。

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: 如果你想在 macOS 上使用 Java 实现应用程序开机自启动,你需要做以下步骤: 1. 首先,你需要确保你的计算机上已经安装了 Java 环境,并且你已经编写好了你要自动启动Java 程序。 2. 然后,你需要打开 macOS 的「用户与群组」设置,选择「登录项」标签。 3. 在「登录项」标签中,你可以看到「自动启动程序」列表,点击「+」号按钮,选择你要自动启动Java 程序的执行文件。 4. 最后,你需要将你的 Java 程序加入「自动启动程序」列表中,这样它就会在你的计算机开机自动启动。 注意:如果你的 Java 程序是由可执行的 JAR 文件生成的,你可能需要在执行文件前面加上 "java -jar" 命令,才能让系统正确地启动你的程序。 ### 回答2: 在macOS中,我们可以使用Java编写一个应用程序,并实现开机自启动的功能。下面是使用Java实现应用程序开机自启动的步骤: 步骤1:创建一个Java应用程序。可以使用Java开发工具,如Eclipse或IntelliJ IDEA,创建一个新的Java项目。在项目中编写我们的应用程序代码。 步骤2:创建一个启动脚本。在macOS中,我们可以使用shell脚本来启动我们的Java应用程序。创建一个文本文件,将以下内容复制粘贴到文件中: ``` #!/bin/sh java -jar /path/to/your/java/application.jar ``` 将`/path/to/your/java/application.jar`替换为你的Java应用程序的路径。 步骤3:将启动脚本添加到用户的登录项中。打开“系统偏好设置” -> “用户与群组” -> “登录项”,将启动脚本拖放到列表中。 步骤4:设置脚本的可执行权限。在终端中,使用以下命令修改脚本的权限: ``` chmod +x /path/to/your/startup/script.sh ``` 将`/path/to/your/startup/script.sh`替换为你的启动脚本的路径。 现在,当你的macOS启动时,你的Java应用程序将自动启动。 需要注意的是,以上步骤仅适用于当前登录的用户。如果你希望所有用户都能够启动应用程序,可以将启动脚本添加到“/Library/LaunchAgents”目录下。 ### 回答3: 要实现 macOS 上的应用程序开机自启动,可以使用Java编写一个小型的启动器程序来实现。 首先,需要创建一个启动器程序,它可以在系统启动自动运行,并负责启动您的Java应用程序。这个启动器程序可以是一个独立的Java应用程序,可以在系统启动时由操作系统自动运行,或者可以将其作为系统服务运行。 为了实现启动器程序,在Java中可以使用`java.awt.Desktop`类来打开指定的应用程序。可以在启动器程序中使用以下代码启动您的Java应用程序: ``` import java.awt.Desktop; import java.io.File; import java.io.IOException; public class Launcher { public static void main(String[] args) throws IOException { String appPath = "/Applications/YourApp.app"; // 替换为您的应用程序的路径 File appFile = new File(appPath); if (Desktop.isDesktopSupported()) { Desktop.getDesktop().open(appFile); } } } ``` 请注意,您需要将路径`/Applications/YourApp.app`替换为您的应用程序的准确路径。确保路径是指向您的应用程序的实际位置。 然后,将编译后的启动器程序与您的应用程序一起打包,并将启动器程序添加到您的macOS用户登录项中。这样,当用户登录时,启动器程序将自动运行,并启动您的Java应用程序。 要将启动器程序添加到登录项中,您可以打开“系统偏好设置”,然后选择“用户与群组”。在用户偏好设置中的“登录项”选项中,可以将启动器程序拖动到该列表中,从而实现开机自启动。 这样,在macOS启动时,启动器程序将自动运行,并启动您的Java应用程序,实现应用程序的开机自启动
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值