Java Android AltBeacon后台服务
我正在使用AltBeacon库开发蓝牙应用程序。似乎每个应用程序只允许使用Java Android AltBeacon后台服务,java,android,bluetooth,ibeacon,altbeacon,Java,Android,Bluetooth,Ibeacon,Altbeacon,我正在使用AltBeacon库开发蓝牙应用程序。似乎每个应用程序只允许使用BeaconManager的实例。我所面临的问题是:我需要一个持续运行的后台服务,该服务不断地进行蓝牙测距和发送通知。如果我打开我的应用程序(把它放到前台),我就是暂停测距的服务。前台活动将进行测距并在屏幕上显示内容 问题是活动和服务中的信标管理器(来自BeaconManager BeaconManager=BeaconManager.getInstanceForApplication(this);)是同一个实例。因此,当
BeaconManager
的实例。我所面临的问题是:我需要一个持续运行的后台服务,该服务不断地进行蓝牙测距和发送通知。如果我打开我的应用程序(把它放到前台),我就是暂停测距的服务。前台活动将进行测距并在屏幕上显示内容
问题是活动和服务中的信标管理器(来自BeaconManager BeaconManager=BeaconManager.getInstanceForApplication(this);
)是同一个实例。因此,当活动关闭时,beaconManager.unbind(这个)代码>被调用,服务中的范围通知程序不再触发
是否可以获得两个独立的beacon manager实例?如果没有,我如何在连续运行的服务和活动中进行测距
Ranging活动
@Override
protected void onCreate(Bundle savedInstanceState) {
...
regionEstimote = new Region("estimote", null, null, null);
beaconManager.getBeaconParsers().add(new BeaconParser().setBeaconLayout("m:2-3=0215,i:4-19,i:20-21,i:22-23,p:24-24"));
beaconManager.bind(this);
}
@Override
protected void onDestroy() {
super.onDestroy();
notificationManager.cancel(NOTIFICATION_ID);
//beaconManager.unbind(this);
}
@Override
public void onBeaconServiceConnect() {
beaconManager.setRangeNotifier(new RangeNotifier() {
....
});
try {
beaconManager.startRangingBeaconsInRegion(regionEstimote);
} catch (RemoteException e) {
Log.e(TAG, "RangingActivity", e);
}
}
beacervice.java
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
if(beaconHistory == null)
beaconHistory = new HashMap<Integer, Date>();
mBeaconManager = BeaconManager.getInstanceForApplication(this);
mBeaconManager.getBeaconParsers().add(new BeaconParser().
setBeaconLayout("m:2-3=0215,i:4-19,i:20-21,i:22-23,p:24-24"));
return START_STICKY;
}
@Override
public void onDestroy() {
super.onDestroy();
beaconHistory = null;
mBeaconManager.unbind(this);
}
@Override
public void onBeaconServiceConnect() {
mBeaconManager.setRangeNotifier(new RangeNotifier() {
@Override
public void didRangeBeaconsInRegion(Collection<Beacon> beacons, Region region) {
if(ActivityBase.isActivityVisible()) { //don't do ranging logic if any activity from my app is in the foreground
return;
}
...
}
});
try {
mBeaconManager.startRangingBeaconsInRegion(regionMint);
} catch (RemoteException e) {
Log.e(TAG, "BeaconService", e);
}
}
@覆盖
公共int onStartCommand(Intent Intent、int标志、int startId){
if(beaconHistory==null)
beaconHistory=新HashMap();
mBeaconManager=BeaconManager.getInstanceForApplication(此应用程序);
mBeaconManager.getBeaconParsers().add(新建BeaconParser()。
立根布置(“m:2-3=0215,i:4-19,i:20-21,i:22-23,p:24-24”);
返回开始时间;
}
@凌驾
公共空间{
super.ondestory();
beaconHistory=null;
mBeaconManager.unbind(此);
}
@凌驾
beacerviceconnect()上的公共无效{
mBeaconManager.setRangeNotifier(新的RangeNotifier(){
@凌驾
公共无效范围信标区域(收集信标,区域){
如果(ActivityBase.isActivityVisible()){//如果我的应用程序中有任何活动在前台,请不要执行测距逻辑
返回;
}
...
}
});
试一试{
MBEACON经理。StarTrangbeaconregion(regionMint);
}捕获(远程异常){
日志e(标签“BeaconService”,e);
}
}
在这种情况下,定制的android.app.Application
类非常有用。BeaconManager
是一个单例,因此同时只允许存在一个。类似地,应用程序
类在每个活动的Android应用程序中都有一个实例。如果要同时在活动
和服务
中执行信标检测,请使用集中式应用程序
类绑定到BeaconManager
,然后将回调转发给活动
和服务
您可以在应用程序中看到绑定到BeaconManager
的示例,然后将回调传递到参考应用程序中的活动中:您应该扩展应用程序类,并按照说明启动区域后台监控(请参阅“在后台启动应用程序”)
为了进行测距,在同一类中实现RangeNotifier:
public class AndroidApp extends Application implements BootstrapNotifier, RangeNotifier {...
在以下区域开始测距:
@Override
public void didEnterRegion(Region region) {
try {
mBeaconManager.startRangingBeaconsInRegion(region);
}
catch (RemoteException e) {
if (BuildConfig.DEBUG) Log.d(Const.TAG, "Can't start ranging");
}
}
实施DidRangeBeanConsistinRegion方法:
@Override
public void didRangeBeaconsInRegion(Collection<Beacon> beacons, Region region) {
if (beacons.size() > 0) {
Beacon firstBeacon = beacons.iterator().next();
if (BuildConfig.DEBUG) Log.d(Const.TAG, "Beacon ranged: UUID: "
+ firstBeacon.getId1().toString() + " Major: "
+ firstBeacon.getId2().toString() + " Minor: "
+ firstBeacon.getId3().toString());
// Do something with the result
// Stop ranging
try {
mBeaconManager.stopRangingBeaconsInRegion(region);
} catch (RemoteException e) {
e.printStackTrace();
}
}
}
@覆盖
公共无效范围信标区域(收集信标,区域){
如果(beacons.size()>0){
Beacon firstBeacon=beacons.iterator().next();
if(BuildConfig.DEBUG)Log.d(Const.TAG,“信标范围:UUID:”
+firstBeacon.getId1().toString()+“主要:”
+firstBeacon.getId2().toString()+“次要:”
+firstBeacon.getId3().toString());
//对结果做点什么
//停止测距
试一试{
MBeaconsistenregion(区域)停车场管理人员;
}捕获(远程异常){
e、 printStackTrace();
}
}
}
嗨,DavidYoung,我想在后台服务中扫描信标,即使应用程序ui不可见。请您指导我,并分享代码片段,以实现这一点。提前感谢这里的示例:在后台启动应用程序下。您不需要自己的服务,因为图书馆提供了一种服务。只需在自定义应用程序类中实现回调。非常感谢。。我试过了,但一旦你从应用程序中出来,扫描就会停止。如果你来到主屏幕。我想实现连续扫描。请帮助我。不,扫描将在后台以较低的速率继续。(默认情况下每5分钟一次)查看reference应用程序,这是一个基于上述示例执行此操作的工作应用程序。看到这里,也非常感谢..我明白了..:)你能和RangeNotifier分享一个应用程序的示例类吗?为什么你需要停止测距信标?@DiegoRivera,为了节省电池寿命,你需要停止测距信标。