aboutsummaryrefslogtreecommitdiff
path: root/app/src/main/java/io/trygvis/android/bt/BtActionExecutor.java
diff options
context:
space:
mode:
Diffstat (limited to 'app/src/main/java/io/trygvis/android/bt/BtActionExecutor.java')
-rw-r--r--app/src/main/java/io/trygvis/android/bt/BtActionExecutor.java358
1 files changed, 174 insertions, 184 deletions
diff --git a/app/src/main/java/io/trygvis/android/bt/BtActionExecutor.java b/app/src/main/java/io/trygvis/android/bt/BtActionExecutor.java
index 8cbf87c..984c738 100644
--- a/app/src/main/java/io/trygvis/android/bt/BtActionExecutor.java
+++ b/app/src/main/java/io/trygvis/android/bt/BtActionExecutor.java
@@ -12,6 +12,9 @@ import java.util.Iterator;
import java.util.List;
import java.util.Queue;
+import io.trygvis.android.F2;
+import io.trygvis.android.Function;
+
import static io.trygvis.android.bt.BtActionExecutor.EventType.onCharacteristicChanged;
import static io.trygvis.android.bt.BtActionExecutor.EventType.onCharacteristicRead;
import static io.trygvis.android.bt.BtActionExecutor.EventType.onCharacteristicWrite;
@@ -19,239 +22,146 @@ import static io.trygvis.android.bt.BtActionExecutor.EventType.onConnectionState
import static io.trygvis.android.bt.BtActionExecutor.EventType.onDescriptorRead;
import static io.trygvis.android.bt.BtActionExecutor.EventType.onDescriptorWrite;
import static io.trygvis.android.bt.BtActionExecutor.EventType.onFailure;
+import static io.trygvis.android.bt.BtActionExecutor.EventType.onFinally;
import static io.trygvis.android.bt.BtActionExecutor.EventType.onReliableWriteCompleted;
import static io.trygvis.android.bt.BtActionExecutor.EventType.onServicesDiscovered;
public class BtActionExecutor {
private final static String TAG = BtActionExecutor.class.getSimpleName();
private final Queue<BtCallback> actionQ = new ArrayDeque<>();
+ private final Queue<BtCallback> failureQ = new ArrayDeque<>();
private final Queue<BtCallback> finallyQ = new ArrayDeque<>();
- private final List<BluetoothGattCallback> remoteRssi = new ArrayList<>();
-
- public BtActionExecutor() {
- }
-
- public BtActionExecutor(BtCallback first) {
- actionQ.add(first);
- }
-// public static final BtCallback waitForIt = new BtCallback("Wait for it") {
-// @Override
-// public boolean onCharacteristicWrite(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic) {
-// Log.w(TAG, "wait for it...!");
-// return true;
-// }
-// };
-
-// public synchronized BtActionExecutor onSuccess(BtCallback btCallback) {
-// actionQ.add(btCallback);
-// return this;
-// }
-
- public synchronized BtActionExecutor onConnectionStateChange(OnConnectionStateChange callback) {
+ public synchronized BtActionExecutor onConnectionStateChange(F2<BluetoothGatt, Integer, Boolean> callback) {
actionQ.add(new BtCallback("onConnectionStateChange") {
@Override
public boolean onConnectionStateChange(BluetoothGatt gatt, int newState) {
- return callback.onConnectionStateChange(gatt, newState);
+ return callback.apply(gatt, newState);
}
});
return this;
}
- public synchronized BtActionExecutor onServicesDiscovered(OnServicesDiscovered callback) {
+ public synchronized BtActionExecutor onServicesDiscovered(Function<BluetoothGatt, Boolean> callback) {
actionQ.add(new BtCallback("onServicesDiscovered") {
@Override
public boolean onServicesDiscovered(BluetoothGatt gatt) {
- return callback.onServicesDiscovered(gatt);
+ return callback.apply(gatt);
}
});
return this;
}
- public synchronized BtActionExecutor onCharacteristicRead(OnCharacteristicRead callback) {
+ public synchronized BtActionExecutor onCharacteristicRead(F2<BluetoothGatt, BluetoothGattCharacteristic, Boolean> callback) {
actionQ.add(new BtCallback("onCharacteristicRead") {
@Override
public boolean onCharacteristicRead(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic) {
- return callback.onCharacteristicRead(gatt, characteristic);
+ return callback.apply(gatt, characteristic);
}
});
return this;
}
- public synchronized BtActionExecutor onCharacteristicWrite(OnCharacteristicWrite callback) {
+ public synchronized BtActionExecutor onCharacteristicWrite(F2<BluetoothGatt, BluetoothGattCharacteristic, Boolean> callback) {
actionQ.add(new BtCallback("onCharacteristicWrite") {
@Override
public boolean onCharacteristicWrite(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic) {
- return callback.onCharacteristicWrite(gatt, characteristic);
+ return callback.apply(gatt, characteristic);
}
});
return this;
}
- public synchronized BtActionExecutor onCharacteristicChanged(OnCharacteristicChanged callback) {
+ public synchronized BtActionExecutor onCharacteristicChanged(F2<BluetoothGatt, BluetoothGattCharacteristic, Boolean> callback) {
actionQ.add(new BtCallback("onCharacteristicChanged") {
@Override
public boolean onCharacteristicChanged(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic) {
- return callback.onCharacteristicChanged(gatt, characteristic);
+ return callback.apply(gatt, characteristic);
}
});
return this;
}
- public synchronized BtActionExecutor onDescriptorRead(OnDescriptorRead callback) {
+ public synchronized BtActionExecutor onDescriptorRead(F2<BluetoothGatt, BluetoothGattDescriptor, Boolean> callback) {
actionQ.add(new BtCallback("onDescriptorRead") {
@Override
public boolean onDescriptorRead(BluetoothGatt gatt, BluetoothGattDescriptor descriptor) {
- return callback.onDescriptorRead(gatt, descriptor);
+ return callback.apply(gatt, descriptor);
}
});
return this;
}
- public synchronized BtActionExecutor onDescriptorWrite(OnDescriptorWrite callback) {
+ public synchronized BtActionExecutor onDescriptorWrite(F2<BluetoothGatt, BluetoothGattDescriptor, Boolean> callback) {
actionQ.add(new BtCallback("onDescriptorWrite") {
@Override
public boolean onDescriptorWrite(BluetoothGatt gatt, BluetoothGattDescriptor descriptor) {
- return callback.onDescriptorWrite(gatt, descriptor);
+ return callback.apply(gatt, descriptor);
}
});
return this;
}
- public synchronized BtActionExecutor onReliableWriteCompleted(OnReliableWriteCompleted callback) {
+ public synchronized BtActionExecutor onReliableWriteCompleted(Function<BluetoothGatt, Boolean> callback) {
actionQ.add(new BtCallback("onReliableWriteCompleted") {
@Override
public boolean onReliableWriteCompleted(BluetoothGatt gatt) {
- return callback.onReliableWriteCompleted(gatt);
+ return callback.apply(gatt);
}
});
return this;
}
- public synchronized BtActionExecutor onReadRemoteRssi(OnReadRemoteRssi callback) {
+ public synchronized BtActionExecutor onReadRemoteRssi(F2<BluetoothGatt, Integer, Boolean> callback) {
actionQ.add(new BtCallback("onReadRemoteRssi") {
@Override
public boolean onReadRemoteRssi(BluetoothGatt gatt, int rssi) {
- return callback.onReadRemoteRssi(gatt, rssi);
+ return callback.apply(gatt, rssi);
}
});
return this;
}
- public synchronized BtActionExecutor onFailure(OnFailure callback) {
- actionQ.add(new BtCallback("onFailure") {
+ public synchronized BtActionExecutor onFailure(Runnable callback) {
+ failureQ.add(new BtCallback("onFailure") {
@Override
public void onFailure() {
- callback.onFailure();
+ callback.run();
}
});
return this;
}
- public static interface OnConnectionStateChange {
- boolean onConnectionStateChange(BluetoothGatt gatt, int newState);
- }
-
- public static interface OnServicesDiscovered {
- boolean onServicesDiscovered(BluetoothGatt gatt);
- }
-
- public static interface OnCharacteristicRead {
- boolean onCharacteristicRead(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic);
- }
-
- public static interface OnCharacteristicWrite {
- boolean onCharacteristicWrite(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic);
- }
-
- public static interface OnCharacteristicChanged {
- boolean onCharacteristicChanged(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic);
- }
-
- public static interface OnDescriptorRead {
- boolean onDescriptorRead(BluetoothGatt gatt, BluetoothGattDescriptor descriptor);
- }
-
- public static interface OnDescriptorWrite {
- boolean onDescriptorWrite(BluetoothGatt gatt, BluetoothGattDescriptor descriptor);
- }
-
- public static interface OnReliableWriteCompleted {
- boolean onReliableWriteCompleted(BluetoothGatt gatt);
- }
-
- public static interface OnReadRemoteRssi {
- boolean onReadRemoteRssi(BluetoothGatt gatt, int rssi);
- }
-
- public static interface OnFailure {
- void onFailure();
- }
-
- public synchronized BtActionExecutor addFinally(BtCallback btCallback) {
- finallyQ.add(btCallback);
+ public synchronized BtActionExecutor onFinally(Runnable callback) {
+ finallyQ.add(new BtCallback("finally") {
+ @Override
+ public void onFinally() {
+ callback.run();
+ }
+ });
return this;
}
-// public synchronized BtActionExecutor onRemoteRssi(BluetoothGattCallback callback) {
-// remoteRssi.add(callback);
-// return this;
-// }
-
- void onEvent(EventType key, String values, BluetoothGatt gatt, BluetoothGattCharacteristic characteristic, BluetoothGattDescriptor descriptor, int status, int newState) {
- if (status != BluetoothGatt.GATT_SUCCESS) {
- Log.w(TAG, "Operation failed: " + key + ", " + values);
- doFinally();
- return;
- }
-
- Log.i(TAG, "Bt action completed successfully: callback=" + key);
-
- BtCallback btCallback;
- synchronized (this) {
- if (actionQ.isEmpty()) {
- Log.d(TAG, "All Bluetooth actions are done");
+ public String toString() {
+ StringBuilder s = new StringBuilder("Queue: ");
- doFinally();
- return;
- }
+ Iterator<BtCallback> it = actionQ.iterator();
- try {
- Thread.sleep(1000);
- } catch (InterruptedException e) {
- // ignore
+ int i = 0;
+ while (it.hasNext()) {
+ BtCallback c = it.next();
+ if (i > 0) {
+ s.append(", ");
}
- btCallback = actionQ.remove();
- Log.i(TAG, "Executing bt action: " + btCallback.name);
+ s.append(c.name);
+ i++;
}
- try {
- boolean ok = callCallback(key, gatt, characteristic, descriptor, newState, btCallback);
-
- if (!ok) {
- Log.w(TAG, "The callback don't want to continue.");
- doFinally();
- }
-
- if (actionQ.isEmpty()) {
- Log.i(TAG, "The queue is empty");
- }
- } catch (NotOverriddenException e) {
- Log.w(TAG, "Unexpected callback by listener: " + key);
- doFinally();
- }
+ return s.toString();
}
- private void doFinally() {
- actionQ.clear();
-
- for (BtCallback callback = finallyQ.poll(); callback != null; callback = finallyQ.poll()) {
- try {
- callCallback(onFailure, null, null, null, 0, callback);
- } catch (NotOverriddenException e) {
- return;
- }
- }
+ public BluetoothGattCallback asCallback() {
+ return new MyBluetoothGattCallback();
}
enum EventType {
@@ -264,10 +174,13 @@ public class BtActionExecutor {
onDescriptorWrite,
onReliableWriteCompleted,
+ onReadRemoteRssi,
+
onFailure,
+ onFinally,
}
- private Boolean callCallback(EventType key, BluetoothGatt gatt, BluetoothGattCharacteristic characteristic, BluetoothGattDescriptor descriptor, int newState, BtCallback btCallback) {
+ private static Boolean callCallback(EventType key, BluetoothGatt gatt, BluetoothGattCharacteristic characteristic, BluetoothGattDescriptor descriptor, int newState, BtCallback btCallback) {
switch (key) {
case onConnectionStateChange:
return btCallback.onConnectionStateChange(gatt, newState);
@@ -289,78 +202,155 @@ public class BtActionExecutor {
case onFailure:
btCallback.onFailure();
return null;
+ case onFinally:
+ btCallback.onFinally();
+ return null;
default:
Log.w(TAG, "Unknown callback: " + key);
return null;
}
}
- public String toString() {
- StringBuilder s = new StringBuilder("Queue: ");
+ private class MyBluetoothGattCallback extends BluetoothGattCallback {
- Iterator<BtCallback> it = actionQ.iterator();
+ private Queue<BtCallback> initialActionQ = new ArrayDeque<>(actionQ);
+ private List<String> events = new ArrayList<>();
- int i = 0;
- while (it.hasNext()) {
- BtCallback c = it.next();
- if (i > 0) {
- s.append(", ");
- }
- s.append(c.name);
- i++;
- }
+ void onEvent(EventType key, String values, BluetoothGatt gatt, BluetoothGattCharacteristic characteristic, BluetoothGattDescriptor descriptor, int status, int newState) {
+ boolean success = status == BluetoothGatt.GATT_SUCCESS;
+ events.add(key + ", " + values + ", success=" + success);
- return s.toString();
- }
+ Log.i(TAG, "Operation failed: " + key + ", " + values + ", success=" + success);
- public BluetoothGattCallback asCallback() {
- return new BluetoothGattCallback() {
- @Override
- public void onConnectionStateChange(BluetoothGatt gatt, int status, int newState) {
- onEvent(onConnectionStateChange, "status=" + status + ", newState=" + newState, gatt, null, null, status, newState);
+ if (!success) {
+ doFailure();
+ return;
}
- @Override
- public void onServicesDiscovered(BluetoothGatt gatt, int status) {
- onEvent(onServicesDiscovered, "status=" + status, gatt, null, null, status, 9);
- }
+ BtCallback btCallback;
+ synchronized (this) {
+ if (actionQ.isEmpty()) {
+ Log.d(TAG, "All Bluetooth actions are done");
- @Override
- public void onCharacteristicRead(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic, int status) {
- onEvent(onCharacteristicRead, "status=" + status + ", characteristic=" + characteristic.getUuid(), gatt, characteristic, null, status, 0);
- }
+ doFinally();
+ return;
+ }
- @Override
- public void onCharacteristicWrite(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic, int status) {
- onEvent(onCharacteristicWrite, "status=" + status + ", characteristic=" + characteristic.getUuid(), gatt, characteristic, null, status, 0);
+ try {
+ Thread.sleep(1000);
+ } catch (InterruptedException e) {
+ // ignore
+ }
+ btCallback = actionQ.remove();
+ Log.i(TAG, "Executing bt action: " + btCallback.name);
}
- @Override
- public void onCharacteristicChanged(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic) {
- onEvent(onCharacteristicChanged, "characteristic=" + characteristic.getUuid(), gatt, characteristic, null, BluetoothGatt.GATT_SUCCESS, 0);
+ try {
+ boolean ok = callCallback(key, gatt, characteristic, descriptor, newState, btCallback);
+
+ if (!ok) {
+ Log.w(TAG, "The callback don't want to continue.");
+ doFinally();
+ }
+
+ if (actionQ.isEmpty()) {
+ Log.i(TAG, "The queue is empty");
+ }
+ } catch (NotOverriddenException e) {
+ Log.w(TAG, "Unexpected callback by listener: " + key);
+ doFailure();
}
+ }
- @Override
- public void onDescriptorRead(BluetoothGatt gatt, BluetoothGattDescriptor descriptor, int status) {
- onEvent(onDescriptorRead, "status=" + status + ", descriptor=" + descriptor.getUuid(), gatt, null, descriptor, status, 0);
+ private void doFailure() {
+ StringBuilder msg = new StringBuilder();
+
+ msg.append("Expected events: \n");
+ for (BtCallback cb : initialActionQ) {
+ msg.append(" ").append(cb.name).append("\n");
}
- @Override
- public void onDescriptorWrite(BluetoothGatt gatt, BluetoothGattDescriptor descriptor, int status) {
- onEvent(onDescriptorWrite, "status=" + status + ", descriptor=" + descriptor.getUuid(), gatt, null, descriptor, status, 0);
+ msg.append("Actual events: \n");
+ for (String event : events) {
+ msg.append(" ").append(event).append("\n");
}
- @Override
- public void onReliableWriteCompleted(BluetoothGatt gatt, int status) {
- onEvent(onReliableWriteCompleted, "status=" + status, gatt, null, null, status, 0);
+ Log.w(TAG, msg.toString());
+
+ Log.w(TAG, "Executing " + failureQ.size() + " failure handlers");
+
+ for (BtCallback callback = failureQ.poll(); callback != null; callback = failureQ.poll()) {
+ try {
+ callCallback(onFailure, null, null, null, 0, callback);
+ } catch (NotOverriddenException e) {
+ return;
+ }
}
- @Override
- public void onReadRemoteRssi(BluetoothGatt gatt, int rssi, int status) {
- for (BluetoothGattCallback callback : remoteRssi) {
- callback.onReadRemoteRssi(gatt, rssi, status);
+ doFinally();
+ }
+
+ private void doFinally() {
+ actionQ.clear();
+
+ Log.w(TAG, "Executing " + finallyQ.size() + " finally handlers");
+
+ for (BtCallback callback = finallyQ.poll(); callback != null; callback = finallyQ.poll()) {
+ try {
+ callCallback(onFinally, null, null, null, 0, callback);
+ } catch (NotOverriddenException e) {
+ return;
}
}
- };
+ }
+
+ // -----------------------------------------------------------------------
+ //
+ // -----------------------------------------------------------------------
+
+ @Override
+ public void onConnectionStateChange(BluetoothGatt gatt, int status, int newState) {
+ onEvent(onConnectionStateChange, "status=" + status + ", newState=" + newState, gatt, null, null, status, newState);
+ }
+
+ @Override
+ public void onServicesDiscovered(BluetoothGatt gatt, int status) {
+ onEvent(onServicesDiscovered, "status=" + status, gatt, null, null, status, 9);
+ }
+
+ @Override
+ public void onCharacteristicRead(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic, int status) {
+ onEvent(onCharacteristicRead, "status=" + status + ", characteristic=" + characteristic.getUuid(), gatt, characteristic, null, status, 0);
+ }
+
+ @Override
+ public void onCharacteristicWrite(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic, int status) {
+ onEvent(onCharacteristicWrite, "status=" + status + ", characteristic=" + characteristic.getUuid(), gatt, characteristic, null, status, 0);
+ }
+
+ @Override
+ public void onCharacteristicChanged(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic) {
+ onEvent(onCharacteristicChanged, "characteristic=" + characteristic.getUuid(), gatt, characteristic, null, BluetoothGatt.GATT_SUCCESS, 0);
+ }
+
+ @Override
+ public void onDescriptorRead(BluetoothGatt gatt, BluetoothGattDescriptor descriptor, int status) {
+ onEvent(onDescriptorRead, "status=" + status + ", descriptor=" + descriptor.getUuid(), gatt, null, descriptor, status, 0);
+ }
+
+ @Override
+ public void onDescriptorWrite(BluetoothGatt gatt, BluetoothGattDescriptor descriptor, int status) {
+ onEvent(onDescriptorWrite, "status=" + status + ", descriptor=" + descriptor.getUuid(), gatt, null, descriptor, status, 0);
+ }
+
+ @Override
+ public void onReliableWriteCompleted(BluetoothGatt gatt, int status) {
+ onEvent(onReliableWriteCompleted, "status=" + status, gatt, null, null, status, 0);
+ }
+
+ @Override
+ public void onReadRemoteRssi(BluetoothGatt gatt, int rssi, int status) {
+// onEvent(onReadRemoteRssi, "status=" + status, gatt, null, null, status, 0);
+ }
}
}