Android Geofencing в Nativescript.Фоновое событие вызывает java.lang.RuntimeException: невозможно создать экземпляр получателя - PullRequest
1 голос
/ 24 сентября 2019

поэтому моя цель - создать плагин nativescript, который позволяет разработчику устанавливать геозону в любом месте, которая будет срабатывать даже тогда, когда приложение было закрыто (удалено) пользователем.У меня есть рабочий пример, когда приложение находится на переднем плане или когда приложение просто скрыто.Я также успешно получаю событие триггера, даже когда приложение полностью закрыто, однако это приводит к следующему исключению:

n uncaught Исключение произошло в «главном» потоке.Невозможно создать получательтак как есть один для реального приложения в имя-приложения / App_resources / Android / src / AndroidManifest.xml , а затем есть только один для плагина в: src / platform / android / AndroidManifest.xml

Вот соответствующая часть манифеста для (демонстрационного) приложения, я клонирован из nativescript (демо-угловой):

<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_BACKGROUND_LOCATION"/>

<application
    android:name="com.tns.NativeScriptApplication"
    android:allowBackup="true"
    android:icon="@drawable/icon"
    android:label="@string/app_name"
    android:theme="@style/AppTheme">

    <activity
        android:name="com.tns.NativeScriptActivity"
        android:label="@string/title_activity_kimera"
        android:configChanges="keyboard|keyboardHidden|orientation|screenSize|smallestScreenSize|screenLayout|locale|uiMode"
        android:theme="@style/LaunchScreenTheme">

        <meta-data android:name="SET_THEME_ON_LAUNCH" android:resource="@style/AppTheme" />

        <intent-filter>
            <action android:name="android.intent.action.MAIN" />
            <category android:name="android.intent.category.LAUNCHER" />
        </intent-filter>
    </activity>
    <activity android:name="com.tns.ErrorReportActivity"/>
            <!-- GEOFENCING Receiver    -->
    <receiver
        android:name="carTabako.GeofenceBroadcastReceiver"
        android:enabled="true"
        android:exported="true" />
</application>

И это манифест изплагин:

<?xml version="1.0" encoding="UTF-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
  <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
    <uses-permission android:name="android.permission.ACCESS_BACKGROUND_LOCATION"/>
    <application>
           <receiver
            android:name="carTabako.GeofenceBroadcastReceiver"
            android:enabled="true"
            android:exported="true" />
   </application>
</manifest>

Как видите, я уже играю с манифестом плагина.Я регистрирую получателя дважды, что не имеет никакого значения.Я до сих пор не уверен, какой манифест уместен в конце концов, так как нет четкой документации по нему.Мне бы очень хотелось услышать ваши мысли, откуда моя проблема и как ее исправить.

Редактировать: Вот реализация моего BroadcastReceiver: он имеет много журналов и систему создания файлов, чтобы отслеживать, происходит ли событие в фоновом режиме / при закрытии.

module carTabako {

        @JavaProxy("carTabako.GeofenceBroadcastReceiver")
        export class GeofenceBroadcastReceiver extends android.content.BroadcastReceiver {

            public onReceive(context, intent) {

                console.log("INTENT IN Receiver: ", intent);
                let geofencingEvent =  com.google.android.gms.location.GeofencingEvent.fromIntent(intent);
                if (geofencingEvent.hasError()) {
                    console.log("Error with the geofencing Event: "+geofencingEvent.getErrorCode());
                    return;
                }
                const directory = android.os.Environment.getExternalStoragePublicDirectory(android.os.Environment.DIRECTORY_DOWNLOADS).getAbsolutePath();
                const path1 = path.join(directory.toString(), "Geofences");
                const folder = Folder.fromPath(directory);

                let file = folder.getFile("geofenceFile"+ new Date().toString());
                        file.writeText("some random content;" + intent)
                            .then(result => {
                                file.readText()
                                    .then(res => {
                                        console.log("Successfully saved in " + file.path);
                                        console.log("read file: " + file.readTextSync());
                                    });

                            }).catch(err => {
                                console.log(err);
                            });
                let geofenceTransition = geofencingEvent.getGeofenceTransition();
                dialogs.alert(""+ geofencingEvent).then(()=> {
                    console.log("Dialog closed!");
                });
                if (geofenceTransition == com.google.android.gms.location.Geofence.GEOFENCE_TRANSITION_ENTER) {

                    // Get the geofences that were triggered. A single event can trigger
                    // multiple geofences.
                    let triggeringGeofences = geofencingEvent.getTriggeringGeofences();

                    // Get the transition details as a String.
                    let geofenceTransitionDetails =  triggeringGeofences.toString();

                    console.log("Transition received: ", geofenceTransitionDetails);
                } else {
                    console.log("event with no interest for us received");
                }
            }
        }
}

1 Ответ

0 голосов
/ 24 сентября 2019

Так что я решил это.ОЧЕНЬ ОГРОМНОЕ СПАСИБО @ Manoj , который спас меня своим советом, чтобы добавить его в webpack.config.js

Для людей, нашедших эту тему: вы должны добавить ее в webpack.config.js основного плагина вот так:

const appComponents = [
    "tns-core-modules/ui/frame",
    "tns-core-modules/ui/frame/activity",
    "nativescript-geolocation"
];

Просто добавление к нему geolocation.android не помогло, потому что в плагине довольно много зависимостей от nativescript.если файл полностью автономный, то все должно быть хорошо.

После этого у меня возникла исключительная ситуация java nullpointer при запуске приложения.Это было вызвано назначением pendingIntent, которое требуется для геозоны в geolocation.android.ts слишком рано (вне какой-либо функции).Я переместил его в функцию, в которой сначала требуется ожидающее намерение, и -> готово:)

Еще раз спасибо @ Manoj

...