diff --git a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/activities/devicesettings/DeviceSettingsPreferenceConst.java b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/activities/devicesettings/DeviceSettingsPreferenceConst.java index 89426647f..ea7b3d088 100644 --- a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/activities/devicesettings/DeviceSettingsPreferenceConst.java +++ b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/activities/devicesettings/DeviceSettingsPreferenceConst.java @@ -371,6 +371,7 @@ public class DeviceSettingsPreferenceConst { public static final String PREF_AUTH_KEY = "authkey"; public static final String PREF_USER_FITNESS_GOAL = "fitness_goal"; public static final String PREF_USER_FITNESS_GOAL_NOTIFICATION = "fitness_goal_notification"; + public static final String PREF_USER_FITNESS_GOAL_SECONDARY = "fitness_goal_secondary"; public static final String PREF_HOURLY_CHIME_ENABLE = "hourly_chime_enable"; public static final String PREF_HOURLY_CHIME_START = "hourly_chime_start"; diff --git a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/activities/devicesettings/DeviceSpecificSettingsFragment.java b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/activities/devicesettings/DeviceSpecificSettingsFragment.java index eaf04b249..a7db56e3d 100644 --- a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/activities/devicesettings/DeviceSpecificSettingsFragment.java +++ b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/activities/devicesettings/DeviceSpecificSettingsFragment.java @@ -515,6 +515,7 @@ public class DeviceSpecificSettingsFragment extends AbstractPreferenceFragment i addPreferenceHandlerFor(PREF_QC35_NOISE_CANCELLING_LEVEL); addPreferenceHandlerFor(PREF_USER_FITNESS_GOAL); addPreferenceHandlerFor(PREF_USER_FITNESS_GOAL_NOTIFICATION); + addPreferenceHandlerFor(PREF_USER_FITNESS_GOAL_SECONDARY); addPreferenceHandlerFor(PREF_UM25_SHOW_THRESHOLD_NOTIFICATION); addPreferenceHandlerFor(PREF_UM25_SHOW_THRESHOLD); diff --git a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/xiaomi/XiaomiCoordinator.java b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/xiaomi/XiaomiCoordinator.java index 317a4cd4c..b79833e4d 100644 --- a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/xiaomi/XiaomiCoordinator.java +++ b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/devices/xiaomi/XiaomiCoordinator.java @@ -371,7 +371,8 @@ public abstract class XiaomiCoordinator extends AbstractBLEDeviceCoordinator { settings.add(R.xml.devicesettings_heartrate_sleep_alert_activity_stress_spo2); settings.add(R.xml.devicesettings_inactivity_dnd_no_threshold); settings.add(R.xml.devicesettings_sleep_mode_schedule); - // TODO not implemented settings.add(R.xml.devicesettings_goal_notification); + settings.add(R.xml.devicesettings_goal_notification); + settings.add(R.xml.devicesettings_goal_secondary); // // Workout diff --git a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/service/devices/xiaomi/services/XiaomiHealthService.java b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/service/devices/xiaomi/services/XiaomiHealthService.java index 864cbfdc0..5337fbedb 100644 --- a/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/service/devices/xiaomi/services/XiaomiHealthService.java +++ b/app/src/main/java/nodomain/freeyourgadget/gadgetbridge/service/devices/xiaomi/services/XiaomiHealthService.java @@ -52,7 +52,6 @@ import nodomain.freeyourgadget.gadgetbridge.model.ActivitySample; import nodomain.freeyourgadget.gadgetbridge.model.ActivityUser; import nodomain.freeyourgadget.gadgetbridge.model.DeviceService; import nodomain.freeyourgadget.gadgetbridge.proto.xiaomi.XiaomiProto; -import nodomain.freeyourgadget.gadgetbridge.service.btle.TransactionBuilder; import nodomain.freeyourgadget.gadgetbridge.service.devices.xiaomi.XiaomiPreferences; import nodomain.freeyourgadget.gadgetbridge.service.devices.xiaomi.XiaomiSupport; import nodomain.freeyourgadget.gadgetbridge.service.devices.xiaomi.activity.XiaomiActivityFileFetcher; @@ -78,6 +77,8 @@ public class XiaomiHealthService extends AbstractXiaomiService { private static final int CMD_CONFIG_STANDING_REMINDER_SET = 13; private static final int CMD_CONFIG_STRESS_GET = 14; private static final int CMD_CONFIG_STRESS_SET = 15; + private static final int CMD_CONFIG_GOAL_GET = 21; + private static final int CMD_CONFIG_GOAL_SET = 22; private static final int CMD_WORKOUT_WATCH_STATUS = 26; private static final int CMD_WORKOUT_WATCH_OPEN = 30; private static final int CMD_WORKOUT_LOCATION = 48; @@ -127,7 +128,6 @@ public class XiaomiHealthService extends AbstractXiaomiService { case CMD_CONFIG_HEART_RATE_SET: LOG.debug("Got heart rate set ack, status={}", cmd.getStatus()); return; - case CMD_CONFIG_HEART_RATE_GET: handleHeartRateConfig(cmd.getHealth().getHeartRate()); return; @@ -143,6 +143,12 @@ public class XiaomiHealthService extends AbstractXiaomiService { case CMD_CONFIG_STRESS_SET: LOG.debug("Got stress set ack, status={}", cmd.getStatus()); return; + case CMD_CONFIG_GOAL_GET: + handleGoalConfig(cmd.getHealth().getAchievementReminders()); + return; + case CMD_CONFIG_GOAL_SET: + LOG.debug("Got goal set ack, status={}", cmd.getStatus()); + return; case CMD_WORKOUT_WATCH_STATUS: handleWorkoutStatus(cmd.getHealth().getWorkoutStatusWatch()); return; @@ -164,6 +170,7 @@ public class XiaomiHealthService extends AbstractXiaomiService { getSupport().sendCommand("get heart rate config", COMMAND_TYPE, CMD_CONFIG_HEART_RATE_GET); getSupport().sendCommand("get standing reminders config", COMMAND_TYPE, CMD_CONFIG_STANDING_REMINDER_GET); getSupport().sendCommand("get stress config", COMMAND_TYPE, CMD_CONFIG_STRESS_GET); + getSupport().sendCommand("get goal config", COMMAND_TYPE, CMD_CONFIG_GOAL_GET); } @Override @@ -179,6 +186,10 @@ public class XiaomiHealthService extends AbstractXiaomiService { case ActivityUser.PREF_USER_ACTIVETIME_MINUTES: setUserInfo(); return true; + case DeviceSettingsPreferenceConst.PREF_USER_FITNESS_GOAL_NOTIFICATION: + case DeviceSettingsPreferenceConst.PREF_USER_FITNESS_GOAL_SECONDARY: + sendGoalConfig(); + return true; case DeviceSettingsPreferenceConst.PREF_HEARTRATE_USE_FOR_SLEEP_DETECTION: case DeviceSettingsPreferenceConst.PREF_HEARTRATE_SLEEP_BREATHING_QUALITY_MONITORING: case DeviceSettingsPreferenceConst.PREF_HEARTRATE_MEASUREMENT_INTERVAL: @@ -253,6 +264,57 @@ public class XiaomiHealthService extends AbstractXiaomiService { ); } + private void handleGoalConfig(final XiaomiProto.AchievementReminders achievementReminders) { + LOG.debug("Got goal config"); + + final String secondaryValue; + + switch (achievementReminders.getSuggested()) { + case 0: + secondaryValue = "active_time"; + break; + case 1: + default: + secondaryValue = "standing_time"; + } + + final GBDeviceEventUpdatePreferences eventUpdatePreferences = new GBDeviceEventUpdatePreferences() + .withPreference(DeviceSettingsPreferenceConst.PREF_USER_FITNESS_GOAL_NOTIFICATION, achievementReminders.getEnabled()) + .withPreference(DeviceSettingsPreferenceConst.PREF_USER_FITNESS_GOAL_SECONDARY, secondaryValue); + + getSupport().evaluateGBDeviceEvent(eventUpdatePreferences); + } + + public void sendGoalConfig() { + final boolean goalNotification = getDevicePrefs().getBoolean(DeviceSettingsPreferenceConst.PREF_USER_FITNESS_GOAL_NOTIFICATION, false); + final String goalSecondary = getDevicePrefs().getString(DeviceSettingsPreferenceConst.PREF_USER_FITNESS_GOAL_SECONDARY, "standing_time"); + + LOG.debug("Setting goal config, notification={}, secondary={}", goalNotification, goalSecondary); + + final XiaomiProto.AchievementReminders.Builder achievementReminders = XiaomiProto.AchievementReminders.newBuilder() + .setEnabled(goalNotification) + .setSuggested(1); + + if (goalSecondary.equals("active_time")) { + achievementReminders.setSuggested(0); + } else { + achievementReminders.setSuggested(1); + } + + final XiaomiProto.Health health = XiaomiProto.Health.newBuilder() + .setAchievementReminders(achievementReminders) + .build(); + + getSupport().sendCommand( + "set goal config", + XiaomiProto.Command.newBuilder() + .setType(COMMAND_TYPE) + .setSubtype(CMD_CONFIG_GOAL_SET) + .setHealth(health) + .build() + ); + } + private void handleSpo2Config(final XiaomiProto.SpO2 spo2) { LOG.debug("Got SpO2 config"); diff --git a/app/src/main/res/values/arrays.xml b/app/src/main/res/values/arrays.xml index 4d05fdf2c..5447d402c 100644 --- a/app/src/main/res/values/arrays.xml +++ b/app/src/main/res/values/arrays.xml @@ -2089,6 +2089,16 @@ @string/timeformat_am_pm + + active_time + standing_time + + + + @string/active_time + @string/standing_time + + @string/p_timeformat_auto @string/p_timeformat_24h diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 2be00ba70..121163615 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -408,6 +408,7 @@ Units Time format Screen on duration + Secondary goal All day heart rate measurement HPlus/Makibes settings @@ -1100,6 +1101,8 @@ Daily target: active time in minutes Daily target: standing time in minutes Daily target: fat burn time in minutes + Active time + Standing time Store raw record in the database Stores the data \"as is\", increasing the database usage to allow for later interpretation. Data management diff --git a/app/src/main/res/xml/devicesettings_goal_secondary.xml b/app/src/main/res/xml/devicesettings_goal_secondary.xml new file mode 100644 index 000000000..bfb1c47d0 --- /dev/null +++ b/app/src/main/res/xml/devicesettings_goal_secondary.xml @@ -0,0 +1,12 @@ + + + +