android - 使用 delphi 创建设备管理应用程序 - java.lang.IllegalArgumentException:无法找到本机库:main
问题描述
我是 android 开发新手,我正在尝试使用 Delphi Tokyo 10.2 为 android 创建一个 KIOSK 应用程序。
这就是我想要做的:该应用程序将有两个按钮,一个用于打开应用程序,另一个用于在输入密码后关闭应用程序。此应用不应让用户打开任何其他应用。
我所做的:我能够制作一个可以在 android 的安全 > 设备管理员下列出的应用程序。但是当我打开它时应用程序崩溃了
我知道要将必须访问 devicepolicymanager 的所需应用程序列入白名单,并且要做到这一点,该应用程序必须是 deviceadmin,并且对于要成为设备管理员的应用程序,清单必须指定权限 MANAGE_DEVICE_ADMINS。此外,从 DeviceAdminReceiver(在 android sdk 中)继承的类必须在此应用程序中注册接收器。
我使用以下内容为 DeviceAdminReceiver 获取 Delphi 等效类。
java2op -classes android.app.admin.DeviceAdminReceiver -unit untDeviceAdminReceiver
显现 :
<?xml version="1.0" encoding="utf-8"?>
<!-- BEGIN_INCLUDE(manifest) -->
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.embarcadero.DeviceAdmin01"
android:versionCode="1"
android:versionName="1.0.0"
android:installLocation="auto">
<!-- This is the platform API where NativeActivity was introduced. -->
<uses-sdk android:minSdkVersion="14" android:targetSdkVersion="14" />
<uses-permission android:name="android.permission.MANAGE_DEVICE_ADMINS" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.CALL_PHONE" />
<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.READ_CALENDAR" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
<uses-permission android:name="android.permission.WRITE_CALENDAR" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-feature android:glEsVersion="0x00020000" android:required="True"/>
<application android:persistent="False"
android:restoreAnyVersion="False"
android:label="DeviceAdmin01"
android:debuggable="True"
android:largeHeap="False"
android:icon="@drawable/ic_launcher"
android:theme="@style/AppTheme"
android:hardwareAccelerated="true">
<!-- Our activity is a subclass of the built-in NativeActivity framework class.
This will take care of integrating with our NDK code. -->
<activity android:name="com.embarcadero.firemonkey.FMXNativeActivity">
<!-- Tell NativeActivity the name of our .so -->
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<receiver android:name="com.embarcadero.firemonkey.FMXNativeActivity"
android:label="DeviceAdmin01"
android:permission="android.permission.BIND_DEVICE_ADMIN">
<meta-data
android:name="android.app.device_admin"
android:resource="@xml/device_admin"/>
<intent-filter>
<action android:name="android.app.action.DEVICE_ADMIN_ENABLED"/>
</intent-filter>
</receiver>
</application>
</manifest>
<!-- END_INCLUDE(manifest) -->
以下是我的完整代码。这没有被编码来做任何事情。我试图让它作为制作信息亭应用程序的第一步运行。
unit untMain;
interface
uses
System.SysUtils, System.Types, System.UITypes, System.Classes, System.Variants,
FMX.Types, FMX.Controls, FMX.Forms, FMX.Graphics, FMX.Dialogs, untDeviceAdminReceiver,
Androidapi.JNI.Embarcadero, Androidapi.JNIBridge, Androidapi.JNI.GraphicsContentViewText,
AndroidAPI.Helpers, FMX.Controls.Presentation, FMX.StdCtrls;
type
TMyReceiver = class (TJDeviceAdminReceiver)
public
constructor Create;
procedure onEnabled(context: JContext; intent: JIntent); cdecl;
procedure onDisabled(context: JContext; intent: JIntent); cdecl;
end;
type
TForm1 = class(TForm)
Button1: TButton;
Button2: TButton;
procedure FormCreate(Sender: TObject);
procedure FormDestroy(Sender: TObject);
private
{ Private-Deklarationen }
FMyListener : TMyReceiver;
FDeviceAdminReceiver : JDeviceAdminReceiver;
public
{ Public-Deklarationen }
end;
var
Form1: TForm1;
implementation
{$R *.fmx}
{ TMyReceiver }
constructor TMyReceiver.Create;
begin
try
inherited create;
Except on E : Exception do
begin
end;
end;
end;
procedure TMyReceiver.onDisabled(context: JContext; intent: JIntent);
begin
try
Except on E : Exception do
begin
end;
end;
end;
procedure TMyReceiver.onEnabled(context: JContext; intent: JIntent);
begin
try
Except on E : Exception do
begin
end;
end;
end;
procedure TForm1.FormCreate(Sender: TObject);
var
Filter: JIntentFilter;
begin
try
FMyListener := TMyReceiver.Create;
FDeviceAdminReceiver := TJDeviceAdminReceiver.JavaClass.init;
TAndroidHelper.Context.getApplicationContext.registerReceiver(FDeviceAdminReceiver, Filter);
Except on E : Exception do
begin
showMessage(E.Message);
end;
end;
end;
procedure TForm1.FormDestroy(Sender: TObject);
begin
try
TAndroidHelper.Context.getApplicationContext.unregisterReceiver(FDeviceAdminReceiver);
Except on E : Exception do
begin
showMessage(E.Message);
end;
end;
end;
end.
当我运行此应用程序时,它无法打开显示:“不幸的是,DevicdAdmin01 已停止。”
以下是错误报告中与此应用程序相关的日志。
09-18 00:33:27.234 24211 24211 E AndroidRuntime: FATAL EXCEPTION: main
09-18 00:33:27.234 24211 24211 E AndroidRuntime: Process: com.embarcadero.DeviceAdmin01, PID: 24211
09-18 00:33:27.234 24211 24211 E AndroidRuntime: java.lang.RuntimeException: Unable to start activity ComponentInfo{com.embarcadero.DeviceAdmin01/com.embarcadero.firemonkey.FMXNativeActivity}: java.lang.IllegalArgumentException: Unable to find native library: main
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2339)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2413)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at android.app.ActivityThread.access$800(ActivityThread.java:155)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1317)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at android.os.Handler.dispatchMessage(Handler.java:102)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at android.os.Looper.loop(Looper.java:135)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at android.app.ActivityThread.main(ActivityThread.java:5343)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at java.lang.reflect.Method.invoke(Native Method)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at java.lang.reflect.Method.invoke(Method.java:372)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:905)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:700)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: Caused by: java.lang.IllegalArgumentException: Unable to find native library: main
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at android.app.NativeActivity.onCreate(NativeActivity.java:170)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at com.embarcadero.firemonkey.FMXNativeActivity.onCreate(FMXNativeActivity.java:139)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at android.app.Activity.performCreate(Activity.java:6010)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1129)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2292)
09-18 00:33:27.234 24211 24211 E AndroidRuntime: ... 10 more
09-18 00:33:27.238 861 876 W ActivityManager: Force finishing activity 1 com.embarcadero.DeviceAdmin01/com.embarcadero.firemonkey.FMXNativeActivity
这里可能出了什么问题?
我将非常感谢您帮助解决此问题..
解决方案
无法找到本机库:主要错误是由于清单文件中缺少信息。注册 adminReceiver 的代码是错误的,但应用程序至少可以打开。
以下是解决“无法找到本机库:主要”问题的新清单文件:
<?xml version="1.0" encoding="utf-8"?>
<!-- BEGIN_INCLUDE(manifest) -->
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.embarcadero.DevAdm02"
android:versionCode="1"
android:versionName="1.0.0"
android:installLocation="auto">
<!-- This is the platform API where NativeActivity was introduced. -->
<uses-sdk android:minSdkVersion="14" android:targetSdkVersion="14" />
<uses-permission android:name="android.permission.MANAGE_DEVICE_ADMINS" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.CALL_PHONE" />
<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.READ_CALENDAR" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
<uses-permission android:name="android.permission.WRITE_CALENDAR" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-feature android:glEsVersion="0x00020000" android:required="True"/>
<application android:persistent="False"
android:restoreAnyVersion="False"
android:label="DevAdm02"
android:debuggable="True"
android:largeHeap="False"
android:icon="@drawable/ic_launcher"
android:theme="@style/AppTheme"
android:hardwareAccelerated="true">
<!-- Our activity is a subclass of the built-in NativeActivity framework class.
This will take care of integrating with our NDK code. -->
<activity android:name="com.embarcadero.firemonkey.FMXNativeActivity"
android:label="DevAdm02"
android:configChanges="orientation|keyboard|keyboardHidden|screenSize"
android:launchMode="singleTask">
<!-- Tell NativeActivity the name of our .so -->
<meta-data android:name="android.app.lib_name"
android:value="DevAdm02" />
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<receiver android:name="com.embarcadero.rtl.notifications.NotificationAlarm" />
<receiver android:name="com.embarcadero.firemonkey.FMXNativeActivity"
android:label="DevAdm02"
android:permission="android.permission.BIND_DEVICE_ADMIN">
<meta-data
android:name="android.app.device_admin"
android:resource="@xml/device_admin"/>
<intent-filter>
<action android:name="android.app.action.DEVICE_ADMIN_ENABLED"/>
</intent-filter>
</receiver>
</application>
</manifest>
<!-- END_INCLUDE(manifest) -->
接下来我要弄清楚如何注册 DeviceAdminReceiver 类对象。我将其发布为答案,因为它解决了当前的问题,即 java.lang.IllegalArgumentException: Unable to find native library: main
推荐阅读
- java - 从多个源中提取 JSON 字段
- javascript - 横向到纵向视图导致页面上出现空白
- tensorflow - tf.keras.preprocessing.image.ImageDataGenerator 不会加载 Google Colab 中存在的所有图像
- visual-studio-code - VS Code 查找和替换:当我输入 ctrl+h 时,有没有办法保留我以前的查找项?
- visual-studio-code - 在 Neon Night VSCode 主题中,他如何使用错误破折号而不是曲线?
- python - Tkinter - 当我尝试打印我使用 Entry 定义的变量时,打印返回“.!entry”
- jenkins - 如何在 Windows 10 Home 上安装 Jenkins?
- javascript - 在 d3.js v6 中创建小倍数的最佳方法是什么?
- python - subprocess.wait(timeout=15) 不工作
- javascript - 通过对象 React 映射