Phe*_*nom 23 android geofencing google-play-services android-geofence location-client
我正在编写一个应用程序,当有人在正在安装的应用程序的生命周期内进入/退出多个站点时,需要使用地理围栏.
我的地理围栏实现(非常类似于下面的第二个链接)在我第一次安装应用程序时工作正常,无论是在移入/移出地理围栏时还是在使用模拟位置进行模拟时,都会重新启动设备.
在重新启动时,模拟位置或实际上物理移入和移出地理围栏似乎都会触发事件并将未决意图发送到我的广播接收器.
我已经查看了以下三个链接,并且还阅读了相当多的文档,但我无法找到一个明确的答案,直接说注册地理围栏持续存在或重启后不会持续存在.
这些是我在堆栈溢出时查看的链接: Android地理围栏是否能够在重启时幸存?
Android Geofences是否在删除/过期之前保持活动状态,或者直到我的PendingIntent启动为止
如果有人碰巧知道他们是否坚持重新启动后的答案,或者如果他们没有解决问题,那将非常感谢!我目前的最后一个希望是为BOOT_COMPLETED创建一个监听器,并在启动时重新注册它们,但id更喜欢只在必要时才这样做.
非常感谢提前!
编辑:虽然我没有找到明确的(书面)答案,但我很确定TonyC先生发布的内容是正确的,并选择了解决方案.非常感谢TonyC!
如果有人想看到我的解决方案,我会在设备启动时监听启动完成操作,然后重新注册我需要的所有地理围栏.
这是显而易见的:
<!-- Listen for the device starting up -->
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/>
<receiver android:name="com.YOUR.PACKAGE.geofence.BootCompleteReceiver">
<intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED"/>
</intent-filter>
</receiver>
Run Code Online (Sandbox Code Playgroud)
然后为它创建一个广播接收器,它将在启动时重新注册地理围栏:
package com.YOUR.PACKAGE.geofence;
import android.app.PendingIntent.CanceledException;
import android.content.Context;
import android.content.Intent;
import android.support.v4.content.WakefulBroadcastReceiver;
import com.google.android.gms.common.ConnectionResult;
import com.google.android.gms.common.GooglePlayServicesUtil;
import com.google.android.gms.location.Geofence;
public class BootCompleteReceiver extends WakefulBroadcastReceiver
{
private static final String TAG = "BootCompleteReceiver";
@Override
public void onReceive(Context context, Intent intent)
{
//Do what you want/Register Geofences
}
}
Run Code Online (Sandbox Code Playgroud)
同样值得注意的是,如果您在启动时处于地理围栏内,那么一旦注册了地理围栏,这通常会触发地理围栏的未决意图.
因此,例如,如果地理围栏启动应用程序,那么当您启动恰好位于地理围栏中的设备时,一旦启动完整广播接收器已注册地理围栏,它也将打开应用程序,并且位置服务已经解决了您的位置是.
希望对某人有所帮助.
Mic*_*use 10
地理围栏在重启后无法生存.在其他情况下,您还必须重新注册地理围栏.
在重新注册地理围栏只有当需要,你需要重新注册地理围栏文档召唤出除了BOOT_COMPLETED几种情况.不幸的是,它含糊不清.
让我们逐点考虑从Android O开始强加的新背景执行限制:
可以通过在intent-filter中添加以下内容来处理这个问题,因为这些免除了隐式广播禁令:
<action android:name="android.intent.action.BOOT_COMPLETED" />
Run Code Online (Sandbox Code Playgroud)
然后,确保将以下权限添加到清单:
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
Run Code Online (Sandbox Code Playgroud)
您可能想要捕获Android N中引入的较新的LOCKED_BOOT_COMPLETED意图:
<action android:name="android.intent.action.LOCKED_BOOT_COMPLETED" />
Run Code Online (Sandbox Code Playgroud)
但是,如果你这样做,你还需要标记你的接收器android:directBootAware=”true”.这会为您的应用引入分支.即,您访问的任何基于文件的数据必须使用受设备保护的存储来完成.它的长短是,如果在设备启动到锁定屏幕时不需要通知,请不要使用LOCKED_BOOT_COMPLETED.
再次,我们在这里很幸运,因为你可以使用这个明确的意图:
<action android:name="android.intent.action.MY_PACKAGE_REPLACED" />
Run Code Online (Sandbox Code Playgroud)
这是我不知道的地方.有一个免于隐式广播禁令的ACTION_PACKAGE_DATA_CLEARED,但只有在清除了另一个包的数据时才会触发它.我已经尝试了这一点,并且可以确认在您自己的应用数据被清除时您不会被呼叫.
这可以通过将以下内容添加到您的接收器来处理:
<intent-filter>
<!-- Used to watch for Google Play Services data cleared -->
<action android:name="android.intent.action.PACKAGE_DATA_CLEARED" />
<data android:scheme="package" android:sspPrefix="com.google.android.gms"/>
</intent-filter>
Run Code Online (Sandbox Code Playgroud)
然后将以下代码添加到您的BroadcastReceiver的onReceive方法:
String action = intent.getAction();
if (TextUtils.equals(Intent.ACTION_PACKAGE_DATA_CLEARED, action)) {
Uri uri = intent.getData();
if (uri.toString().equals("package:com.google.android.gms")) {
// Code here to handle Google Play services data cleared
}
}
Run Code Online (Sandbox Code Playgroud)
这是通知您通过地理界线的API,定位服务不再可用,并通过发送所指的Android的方式GeofencingEvent用的错误和状态码GEOFENCE_NOT_AVAILABLE.
但是,只需遵循地理围栏文档的模糊建议,您就会相信您可以在此时重新注册地理围栏.这可能很糟糕,因为位置服务可能仍然被禁用,这样做会导致更多GEOFENCE_NOT_AVAILABLE.我们需要的是一个挂钩来判断何时切换了位置服务.
直到Android O,为android.location.MODE_CHANGED_ACTION注册BroadcastReceiver 会给你这个钩子.在Android O及更高版本中,此隐式意图被禁止,您的BroadcastReceiver将不再被调用,因此需要另一个钩子.
对于Android O及更高版本,我发现使用JobScheduler与JobInfo.Builder.addTriggerContentUri一起监视Settings.Secure.LOCATION_PROVIDERS_ALLOWED URI可用于此目的,如果当前没有运行调用,它甚至会启动你的应用程序你的JobService.这种方法要求API> = 24.我已经证实这是有效的,包括Android P(API 28).
使用JobScheduler方法的一些注意事项:
因此,如果你的minApi版本为24,那么你可以使用JobScheduler/JobService获取Settings.Secure.LOCATION_PROVIDERS_ALLOWED钩子.
但是,如果您不喜欢放弃10%的用户群(截至撰写本文时,KitKat(API 19)占据了Android活跃用户群的9.1%)且需要较低的minApi,则需要同时使用BroadcastReceiver和JobService.
| 归档时间: |
|
| 查看次数: |
6431 次 |
| 最近记录: |