First attempt at parsing the live sensor data, see issue #63

- Live sensor data reading is toggled using the "Set music info" in the debug activity.
- The readings are ONLY logged at the moment
- The miband increments a "counter" (two bytes) at every reading, but it may be that more readings are sent with the same counter value. This is already addressed.
- The name of the axes is general (axis1, 2 and 3) because we still don't know which is which
- It could be that the axes depend on the wear location (especially wearing as a necklace means that the miband rests in a vertical position, while wearing on the wrist means it rests in a horizontal position). NB: It could be that we get RAW data, hence not dependent on the wear location.
- Since the miband may be inserted in two directions in its strap, I guess this also has to be taken into account
- the battery impact of reading this data in unknown
live-sensor-data
Daniele Gobbetti 2015-07-02 10:26:32 +02:00
parent 410b29dd6d
commit d68a4211b6
2 changed files with 41 additions and 5 deletions

View File

@ -137,14 +137,13 @@ public class MiBandService {
public static final byte COMMAND_SET_TIMER = 0x4;
public static final byte COMMAND_GET_SENSOR_DATA = 0x12;
/*
public static final byte COMMAND_FACTORY_RESET = 0x9t;
public static final byte COMMAND_GET_SENSOR_DATA = 0x12t
public static final byte COMMAND_SEND_FIRMWARE_INFO = 0x7t
public static final int COMMAND_SET_COLOR_THEME = et;

View File

@ -73,7 +73,7 @@ public class MiBandSupport extends AbstractBTLEDeviceSupport {
private GregorianCalendar activityDataTimestampToAck = null;
private volatile boolean telephoneRinging;
private volatile boolean isLocatingDevice;
private volatile boolean isReadingSensorData;
public MiBandSupport() {
addSupportedService(MiBandService.UUID_SERVICE_MIBAND_SERVICE);
@ -206,6 +206,8 @@ public class MiBandSupport extends AbstractBTLEDeviceSupport {
private static final byte[] startVibrate = new byte[]{MiBandService.COMMAND_SEND_NOTIFICATION, 1};
private static final byte[] stopVibrate = new byte[]{MiBandService.COMMAND_STOP_MOTOR_VIBRATE};
private static final byte[] reboot = new byte[]{MiBandService.COMMAND_REBOOT};
private static final byte[] sensorRead = new byte[]{MiBandService.COMMAND_GET_SENSOR_DATA, 1};
private static final byte[] sensorStop = new byte[]{MiBandService.COMMAND_GET_SENSOR_DATA, 0};
private static final byte[] fetch = new byte[]{MiBandService.COMMAND_FETCH_DATA};
private byte[] getNotification(long vibrateDuration, int vibrateTimes, int flashTimes, int flashColour, int originalColour, long flashDuration) {
@ -422,7 +424,19 @@ public class MiBandSupport extends AbstractBTLEDeviceSupport {
@Override
public void onSetMusicInfo(String artist, String album, String track) {
// not supported
try {
TransactionBuilder builder = performInitialized("Toggle sensor reading");
if (isReadingSensorData){
builder.write(getCharacteristic(MiBandService.UUID_CHARACTERISTIC_CONTROL_POINT), sensorStop);
isReadingSensorData = false;
}else {
builder.write(getCharacteristic(MiBandService.UUID_CHARACTERISTIC_CONTROL_POINT), sensorRead);
isReadingSensorData = true;
}
builder.queue(getQueue());
} catch (IOException ex) {
LOG.error("Unable to toggle sensor reading MI", ex);
}
}
@Override
@ -527,6 +541,8 @@ public class MiBandSupport extends AbstractBTLEDeviceSupport {
handleBatteryInfo(characteristic.getValue(), BluetoothGatt.GATT_SUCCESS);
} else if (MiBandService.UUID_CHARACTERISTIC_NOTIFICATION.equals(characteristicUUID)) {
// device somehow changed, should we update e.g. battery level?
} else if (MiBandService.UUID_CHARACTERISTIC_SENSOR_DATA.equals(characteristicUUID)) {
handleSensorData(characteristic.getValue());
}
}
@ -647,6 +663,27 @@ public class MiBandSupport extends AbstractBTLEDeviceSupport {
}
}
private void handleSensorData(byte[] value) {
int counter=0, step=0, axis1=0, axis2=0, axis3 =0;
if((value.length - 2) % 6 != 0) {
LOG.warn("GOT UNEXPECTED SENSOR DATA WITH LENGTH: " + value.length);
for (byte b : value) {
LOG.warn("DATA: " + String.format("0x%4x", b));
}
}
else {
counter = (value[0] & 0xff) | ((value[1] & 0xff) << 8);
for (int idx = 0; idx < ((value.length - 2) / 6); idx++) {
step = idx * 6;
axis1 = (value[step+2] & 0xff) | ((value[step+3] & 0xff) << 8);
axis2 = (value[step+4] & 0xff) | ((value[step+5] & 0xff) << 8);
axis3 = (value[step+6] & 0xff) | ((value[step+7] & 0xff) << 8);
}
LOG.info("READ SENSOR DATA VALUES: counter:"+counter+" step:"+step+" axis1:"+axis1+" axis2:"+axis2+" axis3:"+axis3+";");
}
}
private void flushActivityDataHolder() {
GregorianCalendar timestamp = this.activityDataTimestampProgress;
byte category, intensity, steps;