Some initial hacky support for hr readings (Debug activity only)

My Mi2 stopped reporting hr values a while ago though, even on-device.
here
cpfeiffer 2016-10-23 23:53:48 +02:00
parent 069abe17b7
commit b20a9c9ccc
2 changed files with 34 additions and 16 deletions

View File

@ -2,16 +2,23 @@ package nodomain.freeyourgadget.gadgetbridge.service.btle.profiles.heartrate;
import android.bluetooth.BluetoothGatt;
import android.bluetooth.BluetoothGattCharacteristic;
import android.widget.Toast;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import nodomain.freeyourgadget.gadgetbridge.service.btle.AbstractBTLEDeviceSupport;
import nodomain.freeyourgadget.gadgetbridge.service.btle.GattCharacteristic;
import nodomain.freeyourgadget.gadgetbridge.service.btle.TransactionBuilder;
import nodomain.freeyourgadget.gadgetbridge.service.btle.profiles.AbstractBleProfile;
import nodomain.freeyourgadget.gadgetbridge.util.GB;
/**
* https://www.bluetooth.com/specifications/gatt/viewer?attributeXmlFile=org.bluetooth.service.heart_rate.xml
*/
public class HeartRateProfile<T extends AbstractBTLEDeviceSupport> extends AbstractBleProfile<T> {
private static final Logger LOG = LoggerFactory.getLogger(HeartRateProfile.class);
/**
* Returned when a request to the heart rate control point is not supported by the device
*/
@ -26,29 +33,36 @@ public class HeartRateProfile<T extends AbstractBTLEDeviceSupport> extends Abstr
}
protected void writeToControlPoint(byte value, TransactionBuilder builder) {
builder.write(getCharacteristic(GattCharacteristic.UUID_CHARACTERISTIC_HEART_RATE_CONTROL_POINT), new byte[] { value });
writeToControlPoint(new byte[] { value }, builder);
}
protected void writeToControlPoint(byte[] value, TransactionBuilder builder) {
builder.write(getCharacteristic(GattCharacteristic.UUID_CHARACTERISTIC_HEART_RATE_CONTROL_POINT), value);
}
public void requestBodySensorLocation(TransactionBuilder builder) {
}
// TODO: I didn't find anything in the spec to request heart rate readings, so probably this
// should be done in a device specific way.
public void requestHeartRateMeasurement(TransactionBuilder builder) {
writeToControlPoint(new byte[] { 0x15, 0x02, 0x01}, builder);
}
@Override
public boolean onCharacteristicChanged(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic) {
// if (UUID_HEART_RATE_MEASUREMENT.equals(characteristic.getUuid())) {
// int flag = characteristic.getProperties();
// int format = -1;
// if ((flag & 0x01) != 0) {
// format = BluetoothGattCharacteristic.FORMAT_UINT16;
// } else {
// format = BluetoothGattCharacteristic.FORMAT_UINT8;
// }
// final int heartRate = characteristic.getIntValue(format, 1);
// }
if (GattCharacteristic.UUID_CHARACTERISTIC_HEART_RATE_MEASUREMENT.equals(characteristic.getUuid())) {
int flag = characteristic.getProperties();
int format = -1;
if ((flag & 0x01) != 0) {
format = BluetoothGattCharacteristic.FORMAT_UINT16;
} else {
format = BluetoothGattCharacteristic.FORMAT_UINT8;
}
final int heartRate = characteristic.getIntValue(format, 1);
GB.toast(getContext(), "Heart rate: " + heartRate, Toast.LENGTH_LONG, GB.INFO);
}
return false;
}
}

View File

@ -57,6 +57,7 @@ import nodomain.freeyourgadget.gadgetbridge.service.btle.actions.ConditionalWrit
import nodomain.freeyourgadget.gadgetbridge.service.btle.actions.SetDeviceStateAction;
import nodomain.freeyourgadget.gadgetbridge.service.btle.actions.WriteAction;
import nodomain.freeyourgadget.gadgetbridge.service.btle.profiles.deviceinfo.DeviceInfoProfile;
import nodomain.freeyourgadget.gadgetbridge.service.btle.profiles.heartrate.HeartRateProfile;
import nodomain.freeyourgadget.gadgetbridge.service.devices.miband2.Mi2NotificationStrategy;
import nodomain.freeyourgadget.gadgetbridge.service.devices.miband2.operations.InitOperation;
import nodomain.freeyourgadget.gadgetbridge.util.DateTimeUtils;
@ -230,6 +231,7 @@ public class MiBand2Support extends AbstractBTLEDeviceSupport {
builder.notify(getCharacteristic(MiBand2Service.UUID_CHARACTERISTIC_AUTH), enable);
builder.notify(getCharacteristic(MiBand2Service.UUID_UNKNOWN_CHARACTERISTIC3), enable);
builder.notify(getCharacteristic(MiBand2Service.UUID_UNKNOWN_CHARACTERISTIC4), enable);
builder.notify(getCharacteristic(GattCharacteristic.UUID_CHARACTERISTIC_HEART_RATE_MEASUREMENT), enable);
return this;
}
@ -673,12 +675,14 @@ public class MiBand2Support extends AbstractBTLEDeviceSupport {
if (supportsHeartRate()) {
try {
TransactionBuilder builder = performInitialized("HeartRateTest");
builder.write(getCharacteristic(MiBandService.UUID_CHARACTERISTIC_HEART_RATE_CONTROL_POINT), stopHeartMeasurementContinuous);
builder.write(getCharacteristic(MiBandService.UUID_CHARACTERISTIC_HEART_RATE_CONTROL_POINT), stopHeartMeasurementManual);
builder.write(getCharacteristic(MiBandService.UUID_CHARACTERISTIC_HEART_RATE_CONTROL_POINT), startHeartMeasurementManual);
HeartRateProfile<MiBand2Support> profile = new HeartRateProfile<>(this);
profile.requestHeartRateMeasurement(builder);
// builder.write(getCharacteristic(MiBandService.UUID_CHARACTERISTIC_HEART_RATE_CONTROL_POINT), stopHeartMeasurementContinuous);
// builder.write(getCharacteristic(MiBandService.UUID_CHARACTERISTIC_HEART_RATE_CONTROL_POINT), stopHeartMeasurementManual);
// builder.write(getCharacteristic(MiBandService.UUID_CHARACTERISTIC_HEART_RATE_CONTROL_POINT), startHeartMeasurementManual);
builder.queue(getQueue());
} catch (IOException ex) {
LOG.error("Unable to read HearRate in MI1S", ex);
LOG.error("Unable to read HearRate with MI2", ex);
}
} else {
GB.toast(getContext(), "Heart rate is not supported on this device", Toast.LENGTH_LONG, GB.ERROR);