安卓 服务 的 一些 相关代码,自动启动服务或定时启动APP。
很久以前,有很多人问如何自动启动 APP,我说去抄 JAVA ,没人相信。也有人问 如何用定时器,我也说 去抄 Java。也没人相信。
在 XE5 末期,我就实现了 开机自启动。
XE7 的时候,写了一个简单的 WORD 文档。
现在已经过去很久了,先公开一部分代码吧。
下面是调用代码。
const
FlyReceiverClass = 'com.delphi.flying.CommonReceiver';
FlyReceiverDefaultAction = 'com.delphi.flying.BootReceiver.Default';
procedure TForm1.Button2Click(Sender: TObject);
var
PendingIntent: JPendingIntent;
Intent: JIntent;
FireDate: TDateTime;
ACommonReceiver: JCommonReceiver;
begin
Intent := TJIntent.Create;
ACommonReceiver := TJCommonReceiver.JavaClass.init;
Intent.setClass(TAndroidHelper.Context, ACommonReceiver.getClass);
//由于 Recevicer 写了一个 getAction 的代码,这里随便传一个吧。
Intent.setAction(StringToJString(FlyReceiverDefaultAction));
Intent.putExtra(StringToJString('AutoRunApp'), StringToJString('1'));
PendingIntent := TJPendingIntent.JavaClass.getBroadcast(
TAndroidHelper.Context, 0, Intent,
TJPendingIntent.JavaClass.FLAG_UPDATE_CURRENT);
FireDate := Now + Round((SpinBox1.Value / 60) / 24) +
EncodeTime(Round(SpinBox1.Value / 60) mod 24,
Round(SpinBox1.Value) mod 60, Round(SpinBox2.Value), 0);
if CheckBox1.IsChecked then
begin
TAndroidHelper.AlarmManager.&set(
TJAlarmManager.JavaClass.RTC_WAKEUP,
DateTimeToUnix(FireDate),
PendingIntent);
end
else
begin
TAndroidHelper.AlarmManager.&set(
TJAlarmManager.JavaClass.RTC,
DateTimeToUnix(FireDate),
PendingIntent);
end;
Application.Terminate;
end;
上面没看到定时器代码吗?
后来,完整教程公开了,下面是地址。
安卓服务,自启动,开机运行app 简单教程
http://2pascal.com/forum.php?mod=viewthread&tid=2977&fromuid=4
(出处: 2Pascal-新时代的Pascal)
此 Java 代码只是示例,建议用多个 java 代码 来 收多个不同类型的 消息。
可以建立一个 基类 来处理公用部分。
派生的 Java 代码 负责特定类型的消息。
**** Hidden Message *****
java 代码 需编译为 jar ,加入工程中。
jar 调用接口,需转换为 pas ,加入到工程中。
具体 编译和转换,请到别的帖子找。 procedure TAndroidServiceDM.AndroidServiceStratApp(Msg:string);
var
launchintent: JIntent;
begin
launchintent := TJIntent.JavaClass.init;
launchintent.setClassName(
TAndroidHelper.Context,
StringToJString('com.embarcadero.firemonkey.FMXNativeActivity'));
launchintent.addFlags(TJIntent.JavaClass.FLAG_ACTIVITY_NEW_TASK);
launchintent.putExtra(StringToJString('FlyService'),
StringToJString('1'));
launchintent.putExtra(StringToJString(Msg),
StringToJString('1'));
TAndroidHelper.Context.startActivity(launchintent);
PostToast('APP 通过服务启动了!');
end;
function TAndroidServiceDM.AndroidServiceStartCommand(const Sender: TObject;
const Intent: JIntent; Flags, StartId: Integer): Integer;
var
MyNotification : TNotification;
AVal: JString;
begin
Result := TJService.JavaClass.START_STICKY;
try
PostToast('服务启动了');
if Intent <> nil then
begin
AVal := Intent.getStringExtra(StringToJString('AutoRunApp'));
if Assigned(AVal) then
begin
PostToast('收到启动 APP 命令');
AndroidServiceStratApp('AutoRunApp');
end;
end;
if Intent <> nil then
begin
AVal := Intent.getStringExtra(StringToJString('BOOT_COMPLETED'));
if Assigned(AVal) then
begin
PostToast('一会 APP 会自动启动。');
AndroidServiceStratApp('BOOT_COMPLETED');
end;
end;
//这边可以添加开机自动启动的其他代码。
finally
PostToast('服务运行完毕');
end;
end;
以上代码。
负责完成 开机启动 APP
定时 启动 APP 。
但是想要正常完成 开机启动 APP,需要配置 XML。然后手机的安全软件要设置你的APP 允许开机运行。否则无效。
配置了 XML,只是一部分。
你还得编译 Java 代码为 JAR,然后加入到你的 APP 中。
这些在我们群已经是烂大街的技术了。
下面是 XML 的配置。
注意 action的不同。
<!-- add by flying wang -->
<receiver android:name="com.delphi.flying.BootReceiver"
android:permission="android.permission.RECEIVE_BOOT_COMPLETED">
<intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</receiver>
<receiver android:name="com.delphi.flying.CommonReceiver">
<intent-filter>
<action android:name="android.intent.action.USER_PRESENT" />
</intent-filter>
</receiver>
<receiver
android:name="com.delphi.flying.CommonReceiver"
android:permission="android.permission.CHANGE_NETWORK_STATE">
<intent-filter>
<action android:name="android.net.conn.CONNECTIVITY_CHANGE" />
<action android:name="android.net.wifi.WIFI_STATE_CHANGED" />
</intent-filter>
</receiver>
<receiver
android:name="com.delphi.flying.CommonReceiver"
android:permission="android.permission.CHANGE_WIFI_STATE">
<intent-filter>
<action android:name="android.net.conn.CONNECTIVITY_CHANGE" />
<action android:name="android.net.wifi.WIFI_STATE_CHANGED" />
</intent-filter>
</receiver>
<receiver
android:name="com.delphi.flying.CommonReceiver"
android:permission="android.permission.CHANGE_WIFI_MULTICAST_STATE">
<intent-filter>
<action android:name="android.net.conn.CONNECTIVITY_CHANGE" />
<action android:name="android.net.wifi.WIFI_STATE_CHANGED" />
</intent-filter>
</receiver>
我写 XE5 自启动,参考的是 Brian Long 写的英文文章。
2014年8月,成功实现自启动。
2014年 11月份 XE7 版本只是写成了中文的 WORD 文档。同时支持 jar 了。再也不用傻逼似的合并 DEX 了。
到了 RAD10,安卓可以写 服务 了。
2015 年 9月份 就改成 不直接启动 APP,先启动服务。
服务来做具体的任务。
在我们群,很多人都收到了相关代码。
但是 开机启动 APP 或服务,依然受到手机内置安全程序的控制。
所以,实际意义不大。
真正有意义的,是大家可以写 服务了。
服务 可以通过配置 XML 实现 WIFI 或 3G 网络变化就启动。
APP 启动,服务也启动。
服务定时启动服务。
例如 每隔 5 分钟 启动一次服务。
服务启动后,切记,不能长时间运行,顶多 几分钟,一般几秒钟即可,当然用于音频播放的服务可以做到长期运行。
不过,有一些白痴,不相信我。你们爱咋咋地吧。
另外再说一个,如果你用 定时的方法让 安卓显示消息,那么请给 APP 震动的权限,否则部分手机会提示 你的 应用 已经 结束或退出了。也就是 闪退了。
手机从休眠中恢复,会先联网。
开机之后也会联网。
配置 XML 接收 网络变化消息。
用这个消息 启动 服务,基本上等同于 开机启动 服务。
你服务启动后,用楼主的 定时器代码 来 定时启动 服务。
这样,服务就能 在 非休眠状态 连续运行了。
休眠之后,就只能看 厂家 ROM 的 脸色了。
但是 从 休眠中 恢复后,肯定会联网的。你的服务也肯定会继续运行的。
休眠的时候,服务 不运行,也就不是什么问题了。
最近公开了如下旧代码。
安卓服务,自启动,开机运行app 简单教程
http://www.2pascal.com/forum.php?mod=viewthread&tid=2977&fromuid=4
(出处: 2Pascal-新时代的Pascal)
Toast For Android Service 安卓服务专用 Toast 代码
http://2pascal.com/forum.php?mod=viewthread&tid=2616&fromuid=4
(出处: 2Pascal-新时代的Pascal)
关于 调用 JNI JAR java 的说明和注意事项,调用第 靠写不下了
http://2pascal.com/forum.php?mod=viewthread&tid=1384&fromuid=4
(出处: 2Pascal-新时代的Pascal)
一种简单的 jar 转 pas 工具,不如 EMB 官方提供的 工具 强大。
JarOrClass2Pas FlyingWang V1.0.2016.426 附赠 java 转 Jar.zip
http://www.2pascal.com/forum.php?mod=viewthread&tid=891&fromuid=4
(出处: 2Pascal-新时代的Pascal)
如果你希望使用 EMB 官方工具,请打开你的 帮助,搜索 Java2OP.exe 。
给一个赞。 OKOKOK!!!!!!!!!!!!!!!!!!!!!!!! 老猫威武