diff --git a/modules/legacy/modules/device_management/lib/src/features/health/presentation/health_screen.dart b/modules/legacy/modules/device_management/lib/src/features/health/presentation/health_screen.dart index 1d60dd31..a6982284 100644 --- a/modules/legacy/modules/device_management/lib/src/features/health/presentation/health_screen.dart +++ b/modules/legacy/modules/device_management/lib/src/features/health/presentation/health_screen.dart @@ -56,14 +56,14 @@ class _HealthScreenState extends ConsumerState final state = ref.watch(healthViewModelProvider); final vm = ref.read(healthViewModelProvider.notifier); - ref.listen( - healthViewModelProvider.select((s) => s.errorMessage), - (previous, next) { - if (next.isNotEmpty) { - showTopSnackbar(context, message: next, type: MessageType.error); - } - }, - ); + ref.listen(healthViewModelProvider.select((s) => s.errorMessage), ( + previous, + next, + ) { + if (next.isNotEmpty) { + showTopSnackbar(context, message: next, type: MessageType.error); + } + }); return LegacyPageLayout( theme: theme, @@ -130,6 +130,29 @@ class _HealthScreenState extends ConsumerState ), ], ), + footer: _SaveSection(), + ); + } +} + +class _SaveSection extends ConsumerWidget { + const _SaveSection(); + + @override + Widget build(BuildContext context, WidgetRef ref) { + final theme = ref.read(themePortProvider); + + final vm = ref.read(healthViewModelProvider.notifier); + + return Padding( + padding: EdgeInsets.symmetric(horizontal: 24, vertical: 10), + child: PrimaryButton( + onPressed: () async { + await vm.measure(); + }, + text: context.translate(I18n.measure), + color: theme.getColorFor(ThemeCode.legacyPrimary), + ), ); } } diff --git a/modules/legacy/modules/device_management/lib/src/features/health/presentation/state/health_view_model.dart b/modules/legacy/modules/device_management/lib/src/features/health/presentation/state/health_view_model.dart index 32a7f3bf..9433affe 100644 --- a/modules/legacy/modules/device_management/lib/src/features/health/presentation/state/health_view_model.dart +++ b/modules/legacy/modules/device_management/lib/src/features/health/presentation/state/health_view_model.dart @@ -14,12 +14,14 @@ final healthViewModelProvider = class HealthViewModel extends Notifier { late final HealthRepository _repository; + late final CommandsRepository _commandsRepository; static const int _historyPageSize = 20; @override HealthViewState build() { _repository = ref.read(healthRepositoryProvider); + _commandsRepository = ref.read(commandsRepositoryProvider); _init(); return const HealthViewState(); } @@ -247,4 +249,29 @@ class HealthViewModel extends Notifier { final msg = e.toString(); return msg.startsWith('Exception: ') ? msg.substring(11) : msg; } + + Future measure() async { + final device = ref.read(selectedDeviceProvider); + if (device == null) return; + + try { + state = state.copyWith(isLoading: true); + + final request = SendCommandRequestModel( + device: device.identificator, + command: DeviceCommand.requestHeartRate, + ); + + await _commandsRepository.send(request: request); + if (!ref.mounted) return; + + state = state.copyWith(isLoading: false); + } catch (e) { + if (!ref.mounted) return; + state = state.copyWith( + isLoading: false, + errorMessage: _formatError(e), + ); + } + } } diff --git a/modules/legacy/packages/legacy_shared/lib/src/data/models/send_command_request_model.dart b/modules/legacy/packages/legacy_shared/lib/src/data/models/send_command_request_model.dart index 921174d0..ae2ab431 100644 --- a/modules/legacy/packages/legacy_shared/lib/src/data/models/send_command_request_model.dart +++ b/modules/legacy/packages/legacy_shared/lib/src/data/models/send_command_request_model.dart @@ -12,12 +12,12 @@ enum DeviceCommand { findDevice, @JsonValue('REQUEST_PHOTO') requestPhoto, + @JsonValue('REQUEST_HEART_RATE') + requestHeartRate, @JsonValue('RESTART') restart, @JsonValue('REWARDS') rewards, - @JsonValue('SET_LANGUAGE') - setLanguage, @JsonValue('SHUTDOWN') shutdown, @JsonValue('SET_SOUND_MODE') diff --git a/modules/legacy/packages/legacy_shared/lib/src/data/models/send_command_request_model.g.dart b/modules/legacy/packages/legacy_shared/lib/src/data/models/send_command_request_model.g.dart index 4633fa37..40dd34be 100644 --- a/modules/legacy/packages/legacy_shared/lib/src/data/models/send_command_request_model.g.dart +++ b/modules/legacy/packages/legacy_shared/lib/src/data/models/send_command_request_model.g.dart @@ -27,9 +27,9 @@ const _$DeviceCommandEnumMap = { DeviceCommand.factory: 'FACTORY', DeviceCommand.findDevice: 'FIND_DEVICE', DeviceCommand.requestPhoto: 'REQUEST_PHOTO', + DeviceCommand.requestHeartRate: 'REQUEST_HEART_RATE', DeviceCommand.restart: 'RESTART', DeviceCommand.rewards: 'REWARDS', - DeviceCommand.setLanguage: 'SET_LANGUAGE', DeviceCommand.shutdown: 'SHUTDOWN', DeviceCommand.setSoundMode: 'SET_SOUND_MODE', }; diff --git a/packages/sf_localizations/assets/l10n/de.json b/packages/sf_localizations/assets/l10n/de.json index 92c75017..015e432e 100644 --- a/packages/sf_localizations/assets/l10n/de.json +++ b/packages/sf_localizations/assets/l10n/de.json @@ -625,5 +625,6 @@ "volumeHint": "Sie können den Schieberegler ziehen, um die Gerätelautstärke anzupassen. Die App speichert nur die zuletzt erfolgreich eingestellte Lautstärke. Die tatsächliche Lautstärke hängt vom Gerät ab.", "volumeSend": "Senden", "photoTaken": "Foto erfolgreich aufgenommen", - "noPhotosAvailable": "Keine Fotos verfügbar" + "noPhotosAvailable": "Keine Fotos verfügbar", + "measure": "Messen" } diff --git a/packages/sf_localizations/assets/l10n/en.json b/packages/sf_localizations/assets/l10n/en.json index 0d47cedc..5e18cd6f 100755 --- a/packages/sf_localizations/assets/l10n/en.json +++ b/packages/sf_localizations/assets/l10n/en.json @@ -757,5 +757,6 @@ "syncClockMessage": "Synchronize the device clock with the current time", "locationWifiNetworksOptional": "WiFi networks (optional)", "photoTaken": "Photo taken successfully", - "noPhotosAvailable": "No photos available" + "noPhotosAvailable": "No photos available", + "measure": "Measure" } diff --git a/packages/sf_localizations/assets/l10n/es.json b/packages/sf_localizations/assets/l10n/es.json index 5add1085..b6458049 100644 --- a/packages/sf_localizations/assets/l10n/es.json +++ b/packages/sf_localizations/assets/l10n/es.json @@ -755,5 +755,6 @@ "syncClockMessage": "Sincroniza el reloj del dispositivo con la hora actual", "locationWifiNetworksOptional": "Redes WiFi (opcional)", "photoTaken": "Foto tomada exitosamente", - "noPhotosAvailable": "No hay fotos disponibles" + "noPhotosAvailable": "No hay fotos disponibles", + "measure": "Medir" } diff --git a/packages/sf_localizations/assets/l10n/fr.json b/packages/sf_localizations/assets/l10n/fr.json index 0ba0991e..449b53bc 100644 --- a/packages/sf_localizations/assets/l10n/fr.json +++ b/packages/sf_localizations/assets/l10n/fr.json @@ -625,5 +625,6 @@ "volumeHint": "Vous pouvez faire glisser le curseur pour régler le volume de l'appareil. L'application ne sauvegarde que le dernier niveau de volume ajusté avec succès. Le volume réel dépendra de l'appareil.", "volumeSend": "Envoyer", "photoTaken": "Photo prise avec succès", - "noPhotosAvailable": "Aucune photo disponible" + "noPhotosAvailable": "Aucune photo disponible", + "measure": "Mesurer" } diff --git a/packages/sf_localizations/assets/l10n/it.json b/packages/sf_localizations/assets/l10n/it.json index 2f6b8f68..f3d4c36a 100644 --- a/packages/sf_localizations/assets/l10n/it.json +++ b/packages/sf_localizations/assets/l10n/it.json @@ -625,5 +625,6 @@ "volumeHint": "Puoi trascinare il cursore per regolare il volume del dispositivo. L'app salva solo l'ultimo livello di volume regolato con successo. Il volume effettivo dipenderà dal dispositivo.", "volumeSend": "Invia", "photoTaken": "Foto scattata con successo", - "noPhotosAvailable": "Nessuna foto disponibile" + "noPhotosAvailable": "Nessuna foto disponibile", + "measure": "Misurare" } diff --git a/packages/sf_localizations/assets/l10n/pt.json b/packages/sf_localizations/assets/l10n/pt.json index 6f51c5a9..cf8186da 100644 --- a/packages/sf_localizations/assets/l10n/pt.json +++ b/packages/sf_localizations/assets/l10n/pt.json @@ -625,5 +625,6 @@ "volumeHint": "Você pode arrastar o controle deslizante para ajustar o volume do dispositivo. O aplicativo salva apenas o nível de volume ajustado com sucesso mais recentemente. O volume real dependerá do dispositivo.", "volumeSend": "Enviar", "photoTaken": "Foto tirada com sucesso", - "noPhotosAvailable": "Nenhuma foto disponível" + "noPhotosAvailable": "Nenhuma foto disponível", + "measure": "Medir" } diff --git a/packages/sf_localizations/lib/src/generated/i18n.dart b/packages/sf_localizations/lib/src/generated/i18n.dart index 273021dc..ebfe6b1a 100755 --- a/packages/sf_localizations/lib/src/generated/i18n.dart +++ b/packages/sf_localizations/lib/src/generated/i18n.dart @@ -762,4 +762,5 @@ class I18n { static const String photoTaken = 'photoTaken'; static const String noPhotosAvailable = 'noPhotosAvailable'; static const String yesterday = 'yesterday'; + static const String measure = 'measure'; }