From 3be6ec00073327a272cdf1e45fc66409971e8f61 Mon Sep 17 00:00:00 2001 From: Severin von Wnuck-Lipinski Date: Sun, 11 Aug 2024 11:39:08 +0200 Subject: [PATCH] Add weight measurement support for MiScale --- .../gadgetbridge/daogen/GBDaoGenerator.java | 9 ++++ .../devices/AbstractDeviceCoordinator.java | 11 ++++ .../devices/DeviceCoordinator.java | 12 +++++ .../miscale/MiScaleSampleProvider.java | 54 +++++++++++++++++++ .../entities/AbstractWeightSample.java | 35 ++++++++++++ .../gadgetbridge/model/WeightSample.java | 24 +++++++++ 6 files changed, 145 insertions(+) create mode 100644 app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/miscale/MiScaleSampleProvider.java create mode 100644 app/src/main/java/nodomain/freeyourgadget/gadgetbridge/entities/AbstractWeightSample.java create mode 100644 app/src/main/java/nodomain/freeyourgadget/gadgetbridge/model/WeightSample.java diff --git a/GBDaoGenerator/src/nodomain/freeyourgadget/gadgetbridge/daogen/GBDaoGenerator.java b/GBDaoGenerator/src/nodomain/freeyourgadget/gadgetbridge/daogen/GBDaoGenerator.java index fb821a5d8..21671886e 100644 --- a/GBDaoGenerator/src/nodomain/freeyourgadget/gadgetbridge/daogen/GBDaoGenerator.java +++ b/GBDaoGenerator/src/nodomain/freeyourgadget/gadgetbridge/daogen/GBDaoGenerator.java @@ -40,6 +40,7 @@ public class GBDaoGenerator { private static final String SAMPLE_HEART_RATE = "heartRate"; private static final String SAMPLE_TEMPERATURE = "temperature"; private static final String SAMPLE_TEMPERATURE_TYPE = "temperatureType"; + private static final String SAMPLE_WEIGHT_KG = "weightKg"; private static final String TIMESTAMP_FROM = "timestampFrom"; private static final String TIMESTAMP_TO = "timestampTo"; @@ -125,6 +126,7 @@ public class GBDaoGenerator { addWena3Vo2Sample(schema, user, device); addWena3StressSample(schema, user, device); addFemometerVinca2TemperatureSample(schema, user, device); + addMiScaleWeightSample(schema, user, device); addHuaweiActivitySample(schema, user, device); @@ -1315,4 +1317,11 @@ public class GBDaoGenerator { addTemperatureProperties(sample); return sample; } + + private static Entity addMiScaleWeightSample(Schema schema, Entity user, Entity device) { + Entity sample = addEntity(schema, "MiScaleWeightSample"); + addCommonTimeSampleProperties("AbstractWeightSample", sample, user, device); + sample.addFloatProperty(SAMPLE_WEIGHT_KG).notNull().codeBeforeGetter(OVERRIDE); + return sample; + } } diff --git a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/AbstractDeviceCoordinator.java b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/AbstractDeviceCoordinator.java index fe44123a3..e6e6c8f88 100644 --- a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/AbstractDeviceCoordinator.java +++ b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/AbstractDeviceCoordinator.java @@ -81,6 +81,7 @@ import nodomain.freeyourgadget.gadgetbridge.model.SleepRespiratoryRateSample; import nodomain.freeyourgadget.gadgetbridge.model.Spo2Sample; import nodomain.freeyourgadget.gadgetbridge.model.StressSample; import nodomain.freeyourgadget.gadgetbridge.model.TemperatureSample; +import nodomain.freeyourgadget.gadgetbridge.model.WeightSample; import nodomain.freeyourgadget.gadgetbridge.service.ServiceDeviceSupport; import nodomain.freeyourgadget.gadgetbridge.util.FileUtils; import nodomain.freeyourgadget.gadgetbridge.util.GBPrefs; @@ -275,6 +276,11 @@ public abstract class AbstractDeviceCoordinator implements DeviceCoordinator { return null; } + @Override + public TimeSampleProvider getWeightSampleProvider(GBDevice device, DaoSession session) { + return null; + } + @Override @Nullable public ActivitySummaryParser getActivitySummaryParser(final GBDevice device) { @@ -522,6 +528,11 @@ public abstract class AbstractDeviceCoordinator implements DeviceCoordinator { return false; } + @Override + public boolean supportsWeightMeasurement() { + return false; + } + @Override public boolean supportsAlarmSnoozing() { return false; diff --git a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/DeviceCoordinator.java b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/DeviceCoordinator.java index e25dc7ab2..4517f5b7a 100644 --- a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/DeviceCoordinator.java +++ b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/DeviceCoordinator.java @@ -61,6 +61,7 @@ import nodomain.freeyourgadget.gadgetbridge.model.Spo2Sample; import nodomain.freeyourgadget.gadgetbridge.model.StressSample; import nodomain.freeyourgadget.gadgetbridge.model.TemperatureSample; import nodomain.freeyourgadget.gadgetbridge.model.TimeSample; +import nodomain.freeyourgadget.gadgetbridge.model.WeightSample; import nodomain.freeyourgadget.gadgetbridge.service.DeviceSupport; import nodomain.freeyourgadget.gadgetbridge.service.ServiceDeviceSupport; import nodomain.freeyourgadget.gadgetbridge.service.SleepAsAndroidSender; @@ -268,6 +269,12 @@ public interface DeviceCoordinator { */ boolean supportsSleepRespiratoryRate(); + /** + * Returns true if measurement and fetching of body weight is supported by the device + * (with this coordinator). + */ + boolean supportsWeightMeasurement(); + /** * Returns true if activity data fetching is supported AND possible at this * very moment. This will consider the device state (being connected/disconnected/busy...) @@ -350,6 +357,11 @@ public interface DeviceCoordinator { */ TimeSampleProvider getSleepRespiratoryRateSampleProvider(GBDevice device, DaoSession session); + /** + * Returns the sample provider for weight data, for the device being supported. + */ + TimeSampleProvider getWeightSampleProvider(GBDevice device, DaoSession session); + /** * Returns the {@link ActivitySummaryParser} for the device being supported. * diff --git a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/miscale/MiScaleSampleProvider.java b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/miscale/MiScaleSampleProvider.java new file mode 100644 index 000000000..9de9b70da --- /dev/null +++ b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/miscale/MiScaleSampleProvider.java @@ -0,0 +1,54 @@ +/* Copyright (C) 2024 Severin von Wnuck-Lipinski + + This file is part of Gadgetbridge. + + Gadgetbridge is free software: you can redistribute it and/or modify + it under the terms of the GNU Affero General Public License as published + by the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Gadgetbridge is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU Affero General Public License for more details. + + You should have received a copy of the GNU Affero General Public License + along with this program. If not, see . */ +package nodomain.freeyourgadget.gadgetbridge.devices.miscale; + +import androidx.annotation.NonNull; + +import de.greenrobot.dao.AbstractDao; +import de.greenrobot.dao.Property; +import nodomain.freeyourgadget.gadgetbridge.devices.AbstractTimeSampleProvider; +import nodomain.freeyourgadget.gadgetbridge.entities.DaoSession; +import nodomain.freeyourgadget.gadgetbridge.entities.MiScaleWeightSample; +import nodomain.freeyourgadget.gadgetbridge.entities.MiScaleWeightSampleDao; +import nodomain.freeyourgadget.gadgetbridge.impl.GBDevice; + +public class MiScaleSampleProvider extends AbstractTimeSampleProvider { + public MiScaleSampleProvider(GBDevice device, DaoSession session) { + super(device, session); + } + + @Override + @NonNull + public AbstractDao getSampleDao() { + return getSession().getMiScaleWeightSampleDao(); + } + + @NonNull + protected Property getTimestampSampleProperty() { + return MiScaleWeightSampleDao.Properties.Timestamp; + } + + @NonNull + protected Property getDeviceIdentifierSampleProperty() { + return MiScaleWeightSampleDao.Properties.DeviceId; + } + + @Override + public MiScaleWeightSample createSample() { + return new MiScaleWeightSample(); + } +} diff --git a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/entities/AbstractWeightSample.java b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/entities/AbstractWeightSample.java new file mode 100644 index 000000000..e4422c54e --- /dev/null +++ b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/entities/AbstractWeightSample.java @@ -0,0 +1,35 @@ +/* Copyright (C) 2024 Severin von Wnuck-Lipinski + + This file is part of Gadgetbridge. + + Gadgetbridge is free software: you can redistribute it and/or modify + it under the terms of the GNU Affero General Public License as published + by the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Gadgetbridge is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU Affero General Public License for more details. + + You should have received a copy of the GNU Affero General Public License + along with this program. If not, see . */ +package nodomain.freeyourgadget.gadgetbridge.entities; + +import androidx.annotation.NonNull; + +import nodomain.freeyourgadget.gadgetbridge.model.WeightSample; +import nodomain.freeyourgadget.gadgetbridge.util.DateTimeUtils; + +public abstract class AbstractWeightSample extends AbstractTimeSample implements WeightSample { + @NonNull + @Override + public String toString() { + return getClass().getSimpleName() + "{" + + "timestamp=" + DateTimeUtils.formatDateTime(DateTimeUtils.parseTimestampMillis(getTimestamp())) + + ", weightKg=" + getWeightKg() + + ", userId=" + getUserId() + + ", deviceId=" + getDeviceId() + + "}"; + } +} diff --git a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/model/WeightSample.java b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/model/WeightSample.java new file mode 100644 index 000000000..fac25751d --- /dev/null +++ b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/model/WeightSample.java @@ -0,0 +1,24 @@ +/* Copyright (C) 2024 Severin von Wnuck-Lipinski + + This file is part of Gadgetbridge. + + Gadgetbridge is free software: you can redistribute it and/or modify + it under the terms of the GNU Affero General Public License as published + by the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Gadgetbridge is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU Affero General Public License for more details. + + You should have received a copy of the GNU Affero General Public License + along with this program. If not, see . */ +package nodomain.freeyourgadget.gadgetbridge.model; + +public interface WeightSample extends TimeSample { + /** + * Returns the weight value. + */ + float getWeightKg(); +}