Stability improvement: Delaying BLE operations after Bluetooth enabled

This commit is contained in:
Aleksander Nowakowski
2017-03-13 16:59:06 +01:00
parent cf5eb61019
commit c7a1a0c38d
3 changed files with 55 additions and 11 deletions

View File

@@ -209,6 +209,14 @@ public abstract class BleProfileService extends Service implements BleManagerCal
}
}
/**
* Returns a handler that is created in onCreate().
* The handler may be used to postpone execution of some operations or to run them in UI thread.
*/
protected Handler getHandler() {
return mHandler;
}
/**
* Returns the binder implementation. This must return class implementing the additional manager interface that may be used in the bound activity.
*
@@ -361,6 +369,7 @@ public abstract class BleProfileService extends Service implements BleManagerCal
mBluetoothDevice = null;
mDeviceName = null;
mLogSession = null;
mHandler = null;
}
/**

View File

@@ -88,7 +88,15 @@ public abstract class BleMulticonnectProfileService extends Service implements B
switch (state) {
case BluetoothAdapter.STATE_ON:
onBluetoothEnabled();
// On older phones (tested on Nexus 4 with Android 5.0.1) the Bluetooth requires some time
// after it has been enabled before some operations can start. Starting the GATT server here
// without a delay is very likely to cause a DeadObjectException from BluetoothManager#openGattServer(...).
mHandler.postDelayed(new Runnable() {
@Override
public void run() {
onBluetoothEnabled();
}
}, 600);
break;
case BluetoothAdapter.STATE_TURNING_OFF:
case BluetoothAdapter.STATE_OFF:
@@ -224,6 +232,14 @@ public abstract class BleMulticonnectProfileService extends Service implements B
}
}
/**
* Returns a handler that is created in onCreate().
* The handler may be used to postpone execution of some operations or to run them in UI thread.
*/
protected Handler getHandler() {
return mHandler;
}
/**
* Returns the binder implementation. This must return class implementing the additional manager interface that may be used in the bound activity.
*
@@ -360,6 +376,7 @@ public abstract class BleMulticonnectProfileService extends Service implements B
public void onDestroy() {
super.onDestroy();
onServiceStopped();
mHandler = null;
}
/**

View File

@@ -73,6 +73,9 @@ public class ProximityService extends BleMulticonnectProfileService implements P
*/
private List<BluetoothDevice> mDevicesWithAlarm;
private int mAttempt;
private final static int MAX_ATTEMPTS = 1;
/**
* This local binder is an interface for the bonded activity to operate with the proximity sensor
*/
@@ -170,18 +173,33 @@ public class ProximityService extends BleMulticonnectProfileService implements P
@Override
protected void onBluetoothEnabled() {
// Start the GATT Server only if Bluetooth is enabled
mServerManager.openGattServer(this, new ProximityServerManager.OnServerOpenCallback() {
mAttempt = 0;
getHandler().post(new Runnable() {
@Override
public void onGattServerOpen() {
// We are now ready to reconnect devices
ProximityService.super.onBluetoothEnabled();
}
public void run() {
final Runnable that = this;
// Start the GATT Server only if Bluetooth is enabled
mServerManager.openGattServer(ProximityService.this, new ProximityServerManager.OnServerOpenCallback() {
@Override
public void onGattServerOpen() {
// We are now ready to reconnect devices
ProximityService.super.onBluetoothEnabled();
}
@Override
public void onGattServerFailed(final int error) {
mServerManager.closeGattServer();
showToast(getString(R.string.proximity_server_error, error));
@Override
public void onGattServerFailed(final int error) {
mServerManager.closeGattServer();
if (mAttempt < MAX_ATTEMPTS) {
mAttempt++;
getHandler().postDelayed(that, 2000);
} else {
showToast(getString(R.string.proximity_server_error, error));
// GATT server failed to start, but we may connect as a client
ProximityService.super.onBluetoothEnabled();
}
}
});
}
});
}