From 5e046b1deb3e6231fcb769a0d06a152d8b95af68 Mon Sep 17 00:00:00 2001 From: mohammad Date: Sun, 6 Oct 2024 16:48:17 +0300 Subject: [PATCH 1/8] garage door --- .vscode/settings.json | 5 + assets/icons/closed_garage_door.svg | 148 ++++++ assets/icons/garage_countdown.svg | 29 ++ assets/icons/garage_preferences_icon.svg | 11 + assets/icons/garage_schedule.svg | 28 ++ assets/icons/open_garage_door.svg | 117 +++++ .../garage_door_bloc/garage_door_bloc.dart | 411 +++++++++++++++++ .../garage_door_bloc/garage_door_event.dart | 162 +++++++ .../garage_door_bloc/garage_door_state.dart | 82 ++++ .../bloc/one_touch_bloc/one_touch_bloc.dart | 1 - .../bloc/three_gang_bloc/three_gang_bloc.dart | 144 ++++-- .../devices/model/garage_door_model.dart | 81 ++++ .../garage_door/create_schedule_garage.dart | 204 +++++++++ .../garage_door/garage_door_screen.dart | 428 ++++++++++++++++++ .../garage_preferences_settings.dart | 341 ++++++++++++++ .../garage_door/garage_records_screen.dart | 122 +++++ .../widgets/garage_door/garagedialog.dart | 221 +++++++++ .../garage_door/schedule_garage_screen.dart | 163 +++++++ .../view/widgets/garage_door/timer_page.dart | 148 ++++++ .../widgets/one_touch/one_touch_setting.dart | 3 +- .../view/widgets/room_page_switch.dart | 9 + .../shared_widgets/create_schedule.dart | 2 + lib/generated/assets.dart | 6 + lib/utils/resource_manager/constants.dart | 40 +- pubspec.yaml | 2 +- 25 files changed, 2860 insertions(+), 48 deletions(-) create mode 100644 .vscode/settings.json create mode 100644 assets/icons/closed_garage_door.svg create mode 100644 assets/icons/garage_countdown.svg create mode 100644 assets/icons/garage_preferences_icon.svg create mode 100644 assets/icons/garage_schedule.svg create mode 100644 assets/icons/open_garage_door.svg create mode 100644 lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart create mode 100644 lib/features/devices/bloc/garage_door_bloc/garage_door_event.dart create mode 100644 lib/features/devices/bloc/garage_door_bloc/garage_door_state.dart create mode 100644 lib/features/devices/model/garage_door_model.dart create mode 100644 lib/features/devices/view/widgets/garage_door/create_schedule_garage.dart create mode 100644 lib/features/devices/view/widgets/garage_door/garage_door_screen.dart create mode 100644 lib/features/devices/view/widgets/garage_door/garage_preferences_settings.dart create mode 100644 lib/features/devices/view/widgets/garage_door/garage_records_screen.dart create mode 100644 lib/features/devices/view/widgets/garage_door/garagedialog.dart create mode 100644 lib/features/devices/view/widgets/garage_door/schedule_garage_screen.dart create mode 100644 lib/features/devices/view/widgets/garage_door/timer_page.dart diff --git a/.vscode/settings.json b/.vscode/settings.json new file mode 100644 index 0000000..c169a71 --- /dev/null +++ b/.vscode/settings.json @@ -0,0 +1,5 @@ +{ + "cSpell.words": [ + "Scheduleapp" + ] +} \ No newline at end of file diff --git a/assets/icons/closed_garage_door.svg b/assets/icons/closed_garage_door.svg new file mode 100644 index 0000000..464aa07 --- /dev/null +++ b/assets/icons/closed_garage_door.svg @@ -0,0 +1,148 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/assets/icons/garage_countdown.svg b/assets/icons/garage_countdown.svg new file mode 100644 index 0000000..b2a3ead --- /dev/null +++ b/assets/icons/garage_countdown.svg @@ -0,0 +1,29 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/assets/icons/garage_preferences_icon.svg b/assets/icons/garage_preferences_icon.svg new file mode 100644 index 0000000..d0883b0 --- /dev/null +++ b/assets/icons/garage_preferences_icon.svg @@ -0,0 +1,11 @@ + + + + + + + + + + + diff --git a/assets/icons/garage_schedule.svg b/assets/icons/garage_schedule.svg new file mode 100644 index 0000000..04e7763 --- /dev/null +++ b/assets/icons/garage_schedule.svg @@ -0,0 +1,28 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/assets/icons/open_garage_door.svg b/assets/icons/open_garage_door.svg new file mode 100644 index 0000000..d55a690 --- /dev/null +++ b/assets/icons/open_garage_door.svg @@ -0,0 +1,117 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart b/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart new file mode 100644 index 0000000..f6c3d4f --- /dev/null +++ b/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart @@ -0,0 +1,411 @@ +import 'dart:async'; +import 'package:dio/dio.dart'; +import 'package:firebase_database/firebase_database.dart'; +import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_event.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_state.dart'; +import 'package:syncrow_app/features/devices/model/device_control_model.dart'; +import 'package:syncrow_app/features/devices/model/device_report_model.dart'; +import 'package:syncrow_app/features/devices/model/garage_door_model.dart'; +import 'package:syncrow_app/features/devices/model/schedule_model.dart'; +import 'package:syncrow_app/features/devices/model/status_model.dart'; +import 'package:syncrow_app/services/api/devices_api.dart'; +import 'package:syncrow_app/utils/helpers/snack_bar.dart'; + +class GarageDoorBloc extends Bloc { + final String GDId; + GarageDoorBloc({ + required this.GDId, + }) : super(const GarageDoorSensorState()) { + on(_fetchStatus); + on(fetchLogsForLastMonth); + on(_toggleClosingReminder); + on(_toggleDoorAlarm); + on(toggleDaySelection); + on(saveSchedule); + on(getSchedule); + on(toggleChange); + on(toggleCreateSchedule); + on(_onClose); + on(selectSeconds); + on(openCloseGarageDoor); + on(_getCounterValue); + on(_setCounterValue); + on(_onTickTimer); + } + void _onClose(OnClose event, Emitter emit) { + _timer?.cancel(); + } + + Timer? _timer; + bool lowBattery = false; + bool closingReminder = false; + bool doorAlarm = false; + + GarageDoorModel deviceStatus = GarageDoorModel( + tr_timecon: 0, + countdown1: 0, + countdownAlarm: 0, + doorContactState: false, + doorControl1: '', + doorState1: '', + switch1: false, + voiceControl1: false, + batteryPercentage: 0, + ); + + void _fetchStatus( + GarageDoorInitial event, Emitter emit) async { + emit(GarageDoorLoadingState()); + try { + var response = await DevicesAPI.getDeviceStatus(GDId); + List statusModelList = []; + for (var status in response['status']) { + statusModelList.add(StatusModel.fromJson(status)); + } + deviceStatus = GarageDoorModel.fromJson( + statusModelList, + ); + secondSelected = deviceStatus.tr_timecon; + toggleDoor = deviceStatus.switch1; + emit(UpdateState(garageSensor: deviceStatus)); + Future.delayed(const Duration(milliseconds: 500)); + _listenToChanges(); + } catch (e) { + emit(GarageDoorFailedState(errorMessage: e.toString())); + return; + } + } + + void _toggleClosingReminder(ToggleClosingReminderEvent event, + Emitter emit) async { + emit(LoadingNewSate(doorSensor: deviceStatus)); + try { + closingReminder = event.isClosingReminderEnabled; + emit(UpdateState(garageSensor: deviceStatus)); + await DevicesAPI.controlDevice( + DeviceControlModel( + deviceId: GDId, + code: 'closing_reminder', + value: closingReminder, + ), + GDId, + ); + } catch (e) { + emit(GarageDoorFailedState(errorMessage: e.toString())); + } + } + + void _toggleDoorAlarm( + ToggleDoorAlarmEvent event, Emitter emit) async { + emit(LoadingNewSate(doorSensor: deviceStatus)); + try { + doorAlarm = event.isDoorAlarmEnabled; + emit(UpdateState(garageSensor: deviceStatus)); + await DevicesAPI.controlDevice( + DeviceControlModel( + deviceId: GDId, + code: 'door_alarm', + value: doorAlarm, + ), + GDId, + ); + } catch (e) { + emit(GarageDoorFailedState(errorMessage: e.toString())); + } + } + + DeviceReport recordGroups = + DeviceReport(startTime: '0', endTime: '0', data: []); + + Future fetchLogsForLastMonth( + ReportLogsInitial event, Emitter emit) async { + DateTime now = DateTime.now(); + + DateTime lastMonth = DateTime(now.year, now.month - 1, now.day); + int startTime = lastMonth.millisecondsSinceEpoch; + int endTime = now.millisecondsSinceEpoch; + try { + emit(GarageDoorLoadingState()); + var response = await DevicesAPI.getReportLogs( + startTime: startTime.toString(), + endTime: endTime.toString(), + deviceUuid: GDId, + code: 'doorcontact_state', + ); + recordGroups = response; + emit(UpdateState(garageSensor: deviceStatus)); + } on DioException catch (e) { + final errorData = e.response!.data; + String errorMessage = errorData['message']; + emit(GarageDoorFailedState(errorMessage: errorMessage)); + } + } + + _listenToChanges() { + try { + DatabaseReference ref = + FirebaseDatabase.instance.ref('device-status/$GDId'); + Stream stream = ref.onValue; + + stream.listen((DatabaseEvent event) async { + if (_timer != null) { + await Future.delayed(const Duration(seconds: 2)); + } + Map usersMap = + event.snapshot.value as Map; + List statusList = []; + usersMap['status'].forEach((element) { + statusList.add(StatusModel(code: element['code'], value: true)); + }); + + deviceStatus = GarageDoorModel.fromJson(statusList); + if (!isClosed) { + // add( + // DoorSensorSwitch(switchD: deviceStatus.doorContactState), + // ); + } + }); + } catch (_) {} + } + + List> days = [ + {"day": "Sun", "key": "Sun"}, + {"day": "Mon", "key": "Mon"}, + {"day": "Tue", "key": "Tue"}, + {"day": "Wed", "key": "Wed"}, + {"day": "Thu", "key": "Thu"}, + {"day": "Fri", "key": "Fri"}, + {"day": "Sat", "key": "Sat"}, + ]; + + Future toggleDaySelection( + ToggleDaySelectionEvent event, + Emitter emit, + ) async { + emit(GarageDoorLoadingState()); + if (selectedDays.contains(event.key)) { + selectedDays.remove(event.key); + } else { + selectedDays.add(event.key); + } + emit(ChangeTimeState()); + } + + Future saveSchedule( + ScheduleSaveapp event, + Emitter emit, + ) async { + try { + if (selectedDays.isNotEmpty) { + emit(GarageDoorLoadingState()); + await DevicesAPI.postSchedule( + category: 'switch_1', + deviceId: GDId, + time: getTimeStampWithoutSeconds(selectedTime).toString(), + code: 'switch_1', + value: toggleSchedule, + days: selectedDays); + CustomSnackBar.displaySnackBar('Save Successfully'); + add(GetScheduleEvent()); + } else { + CustomSnackBar.displaySnackBar('Please select days'); + } + } catch (e) { + emit(GarageDoorFailedState(errorMessage: e.toString())); + } + } + + Future getSchedule( + GetScheduleEvent event, + Emitter emit, + ) async { + try { + emit(GarageDoorLoadingState()); + final response = await DevicesAPI.getSchedule( + category: 'switch_1', + deviceId: GDId, + ); + List jsonData = response; + listSchedule = + jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); + } on DioException catch (e) { + final errorData = e.response!.data; + String errorMessage = errorData['message']; + emit(GarageDoorFailedState(errorMessage: errorMessage.toString())); + } + } + + int? getTimeStampWithoutSeconds(DateTime? dateTime) { + if (dateTime == null) return null; + DateTime dateTimeWithoutSeconds = DateTime(dateTime.year, dateTime.month, + dateTime.day, dateTime.hour, dateTime.minute); + return dateTimeWithoutSeconds.millisecondsSinceEpoch ~/ 1000; + } + + Future toggleChange( + ToggleScheduleEvent event, Emitter emit) async { + try { + emit(GarageDoorLoadingState()); + final response = await DevicesAPI.changeSchedule( + scheduleId: event.id, deviceUuid: GDId, enable: event.toggle); + if (response == true) { + add(GetScheduleEvent()); + toggleSchedule = event.toggle; + return toggleSchedule; + } + emit(IsToggleState(onOff: toggleSchedule)); + } on DioException catch (e) { + final errorData = e.response!.data; + String errorMessage = errorData['message']; + emit(GarageDoorFailedState(errorMessage: errorMessage.toString())); + } + } + + Future deleteSchedule( + DeleteScheduleEvent event, Emitter emit) async { + try { + emit(GarageDoorLoadingState()); + final response = await DevicesAPI.deleteSchedule( + scheduleId: event.id, + deviceUuid: GDId, + ); + if (response == true) { + add(GetScheduleEvent()); + return toggleSchedule; + } + emit(IsToggleState(onOff: toggleSchedule)); + } on DioException catch (e) { + final errorData = e.response!.data; + String errorMessage = errorData['message']; + emit(GarageDoorFailedState(errorMessage: errorMessage.toString())); + } + } + + void toggleSelectedIndex( + ToggleSelectedEvent event, Emitter emit) { + emit(GarageDoorLoadingState()); + selectedTabIndex = event.index; + emit(ChangeSlidingSegmentState(value: selectedTabIndex)); + } + + void toggleCreateSchedule( + ToggleCreateScheduleEvent event, Emitter emit) { + emit(GarageDoorLoadingState()); + createSchedule = !createSchedule; + selectedDays.clear(); + selectedTime = DateTime.now(); + emit(UpdateCreateScheduleState(createSchedule)); + } + + int selectedTabIndex = 0; + bool toggleSchedule = true; + List selectedDays = []; + bool createSchedule = false; + List listSchedule = []; + DateTime? selectedTime = DateTime.now(); + + int secondSelected = 0; + bool toggleDoor = false; + Future selectSeconds( + SelectSecondsEvent event, Emitter emit) async { + try { + emit(GarageDoorLoadingState()); + secondSelected = event.seconds; + + final response = await DevicesAPI.controlDevice( + DeviceControlModel( + deviceId: GDId, code: 'tr_timecon', value: secondSelected), + GDId); + emit(UpdateState(garageSensor: deviceStatus)); + } on DioException catch (e) { + final errorData = e.response!.data; + String errorMessage = errorData['message']; + emit(GarageDoorFailedState(errorMessage: errorMessage.toString())); + } + } + + openCloseGarageDoor( + ToggleDoorEvent event, Emitter emit) async { + emit(GarageDoorLoadingState()); + try { + toggleDoor = !event.toggle; + final response = await DevicesAPI.controlDevice( + DeviceControlModel( + deviceId: GDId, code: 'switch_1', value: toggleDoor), + GDId); + add(GarageDoorInitial()); + emit(UpdateState(garageSensor: deviceStatus)); + } on DioException catch (e) { + final errorData = e.response!.data; + String errorMessage = errorData['message']; + emit(GarageDoorFailedState(errorMessage: errorMessage.toString())); + } + } + + void _setCounterValue( + SetCounterValue event, Emitter emit) async { + emit(LoadingNewSate(doorSensor: deviceStatus)); + int seconds = 0; + try { + seconds = event.duration.inSeconds; + final response = await DevicesAPI.controlDevice( + DeviceControlModel( + deviceId: GDId, code: 'countdown_1', value: seconds), + GDId); + + if (response['success'] ?? false) { + deviceStatus.countdown1 = seconds; + } else { + emit(GarageDoorFailedState(errorMessage: 'Something went wrong')); + return; + } + } catch (e) { + emit(GarageDoorFailedState(errorMessage: e.toString())); + return; + } + if (seconds > 0) { + _onStartTimer(seconds); + } else { + _timer?.cancel(); + emit(TimerRunComplete()); + } + } + + void _getCounterValue( + GetCounterEvent event, Emitter emit) async { + emit(LoadingInitialState()); + try { + var response = await DevicesAPI.getDeviceStatus(GDId); + List statusModelList = []; + for (var status in response['status']) { + statusModelList.add(StatusModel.fromJson(status)); + } + deviceStatus = GarageDoorModel.fromJson(statusModelList); + if (event.deviceCode == 'countdown_1') { + deviceStatus.countdown1 > 0 + ? _onStartTimer(deviceStatus.countdown1) + : emit(UpdateTimerState(seconds: deviceStatus.countdown1)); + } + } catch (e) { + emit(GarageDoorFailedState(errorMessage: e.toString())); + return; + } + } + + void _onStartTimer(int seconds) { + _timer?.cancel(); + _timer = Timer.periodic(const Duration(seconds: 1), (timer) { + add(TickTimer(remainingTime: seconds - timer.tick)); + }); + } + + void _onTickTimer(TickTimer event, Emitter emit) { + if (event.remainingTime > 0) { + emit(TimerRunInProgress(event.remainingTime)); + } else { + _timer?.cancel(); + emit(TimerRunComplete()); + } + } +} diff --git a/lib/features/devices/bloc/garage_door_bloc/garage_door_event.dart b/lib/features/devices/bloc/garage_door_bloc/garage_door_event.dart new file mode 100644 index 0000000..17ee34a --- /dev/null +++ b/lib/features/devices/bloc/garage_door_bloc/garage_door_event.dart @@ -0,0 +1,162 @@ +import 'package:equatable/equatable.dart'; + +abstract class GarageDoorEvent extends Equatable { + const GarageDoorEvent(); + + @override + List get props => []; +} + +class GarageDoorLoading extends GarageDoorEvent {} + +class GarageDoorSwitch extends GarageDoorEvent { + final bool switchD; + final String deviceId; + final String productId; + const GarageDoorSwitch( + {required this.switchD, this.deviceId = '', this.productId = ''}); + + @override + List get props => [switchD, deviceId, productId]; +} + +class GarageDoorUpdated extends GarageDoorEvent {} + +class GarageDoorInitial extends GarageDoorEvent { + const GarageDoorInitial(); +} + +class ReportLogsInitial extends GarageDoorEvent { + const ReportLogsInitial(); +} + +class GarageDoorChangeStatus extends GarageDoorEvent {} + +class GetCounterEvent extends GarageDoorEvent { + final String deviceCode; + const GetCounterEvent({required this.deviceCode}); + @override + List get props => [deviceCode]; +} + +class ToggleLowBatteryEvent extends GarageDoorEvent { + final bool isLowBatteryEnabled; + + const ToggleLowBatteryEvent(this.isLowBatteryEnabled); + + @override + List get props => [isLowBatteryEnabled]; +} + +class ToggleClosingReminderEvent extends GarageDoorEvent { + final bool isClosingReminderEnabled; + + const ToggleClosingReminderEvent(this.isClosingReminderEnabled); + + @override + List get props => [isClosingReminderEnabled]; +} + +class ToggleDoorAlarmEvent extends GarageDoorEvent { + final bool isDoorAlarmEnabled; + + const ToggleDoorAlarmEvent(this.isDoorAlarmEnabled); + + @override + List get props => [isDoorAlarmEnabled]; +} + +class SetCounterValue extends GarageDoorEvent { + final Duration duration; + final String deviceCode; + const SetCounterValue({required this.duration, required this.deviceCode}); + @override + List get props => [duration, deviceCode]; +} + +class StartTimer extends GarageDoorEvent { + final int duration; + + const StartTimer(this.duration); + + @override + List get props => [duration]; +} + +class TickTimer extends GarageDoorEvent { + final int remainingTime; + + const TickTimer({required this.remainingTime}); + + @override + List get props => [remainingTime]; +} + +class StopTimer extends GarageDoorEvent {} + +class OnClose extends GarageDoorEvent {} + +//------------------- Schedule ----------=--------- +class GetScheduleEvent extends GarageDoorEvent {} + +class ScheduleSaveapp extends GarageDoorEvent {} + +class ToggleScheduleEvent extends GarageDoorEvent { + final String id; + final bool toggle; + const ToggleScheduleEvent({required this.toggle, required this.id}); + @override + List get props => [toggle, id]; +} + +class ToggleDaySelectionEvent extends GarageDoorEvent { + final String key; + + const ToggleDaySelectionEvent({required this.key}); + @override + List get props => [key]; +} + +class DeleteScheduleEvent extends GarageDoorEvent { + final String id; + const DeleteScheduleEvent({required this.id}); + @override + List get props => [id]; +} + +class ToggleSelectedEvent extends GarageDoorEvent { + final int index; + const ToggleSelectedEvent({required this.index}); + @override + List get props => [index]; +} + +class ToggleCreateScheduleEvent extends GarageDoorEvent { + final int index; + const ToggleCreateScheduleEvent({required this.index}); + @override + List get props => [index]; +} + +class ChangeFirstWizardSwitchStatusEvent extends GarageDoorEvent { + final bool value; + final String deviceId; + const ChangeFirstWizardSwitchStatusEvent( + {required this.value, this.deviceId = ''}); + @override + List get props => [value, deviceId]; +} + +class SelectSecondsEvent extends GarageDoorEvent { + final int seconds; + const SelectSecondsEvent({required this.seconds}); + @override + List get props => [seconds]; +} + +class ToggleDoorEvent extends GarageDoorEvent { + final bool toggle; + const ToggleDoorEvent({required this.toggle}); + @override + List get props => [toggle]; +} diff --git a/lib/features/devices/bloc/garage_door_bloc/garage_door_state.dart b/lib/features/devices/bloc/garage_door_bloc/garage_door_state.dart new file mode 100644 index 0000000..4cb4e6a --- /dev/null +++ b/lib/features/devices/bloc/garage_door_bloc/garage_door_state.dart @@ -0,0 +1,82 @@ +import 'package:equatable/equatable.dart'; +import 'package:syncrow_app/features/devices/model/garage_door_model.dart'; + +class GarageDoorSensorState extends Equatable { + const GarageDoorSensorState(); + + @override + List get props => []; +} + +class GarageDoorInitialState extends GarageDoorSensorState {} + +class GarageDoorLoadingState extends GarageDoorSensorState {} + +class GarageDoorFailedState extends GarageDoorSensorState { + final String errorMessage; + + const GarageDoorFailedState({required this.errorMessage}); + + @override + List get props => [errorMessage]; +} + +class UpdateState extends GarageDoorSensorState { + final GarageDoorModel garageSensor; + const UpdateState({required this.garageSensor}); + + @override + List get props => [garageSensor]; +} + +class LoadingNewSate extends GarageDoorSensorState { + final GarageDoorModel doorSensor; + const LoadingNewSate({required this.doorSensor}); + + @override + List get props => [doorSensor]; +} + +class ChangeSlidingSegmentState extends GarageDoorSensorState { + final int value; + + const ChangeSlidingSegmentState({required this.value}); + + @override + List get props => [value]; +} + +class UpdateTimerState extends GarageDoorSensorState { + final int seconds; + const UpdateTimerState({required this.seconds}); + + @override + List get props => [seconds]; +} + +class TimerRunInProgress extends GarageDoorSensorState { + final int remainingTime; + + const TimerRunInProgress(this.remainingTime); + + @override + List get props => [remainingTime]; +} + +class TimerRunComplete extends GarageDoorSensorState {} + +class SaveSchedule extends GarageDoorSensorState {} + +class IsToggleState extends GarageDoorSensorState { + final bool? onOff; + const IsToggleState({this.onOff}); +} + +class ChangeTimeState extends GarageDoorSensorState {} + +class LoadingInitialState extends GarageDoorSensorState {} + +class UpdateCreateScheduleState extends GarageDoorSensorState { + final bool createSchedule; + UpdateCreateScheduleState(this.createSchedule); +} diff --git a/lib/features/devices/bloc/one_touch_bloc/one_touch_bloc.dart b/lib/features/devices/bloc/one_touch_bloc/one_touch_bloc.dart index 14d85f3..3d6512f 100644 --- a/lib/features/devices/bloc/one_touch_bloc/one_touch_bloc.dart +++ b/lib/features/devices/bloc/one_touch_bloc/one_touch_bloc.dart @@ -1,7 +1,6 @@ import 'dart:async'; import 'package:dio/dio.dart'; import 'package:firebase_database/firebase_database.dart'; -import 'package:flutter/material.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; import 'package:syncrow_app/features/app_layout/bloc/home_cubit.dart'; import 'package:syncrow_app/features/devices/bloc/one_touch_bloc/one_touch_state.dart'; diff --git a/lib/features/devices/bloc/three_gang_bloc/three_gang_bloc.dart b/lib/features/devices/bloc/three_gang_bloc/three_gang_bloc.dart index 087d569..242f2c5 100644 --- a/lib/features/devices/bloc/three_gang_bloc/three_gang_bloc.dart +++ b/lib/features/devices/bloc/three_gang_bloc/three_gang_bloc.dart @@ -31,7 +31,8 @@ class ThreeGangBloc extends Bloc { List groupThreeGangList = []; bool allSwitchesOn = true; - ThreeGangBloc({required this.threeGangId, required this.switchCode}) : super(InitialState()) { + ThreeGangBloc({required this.threeGangId, required this.switchCode}) + : super(InitialState()) { on(_fetchThreeGangStatus); on(_threeGangUpdated); on(_changeFirstSwitch); @@ -57,7 +58,8 @@ class ThreeGangBloc extends Bloc { on(toggleCreateSchedule); } - void _fetchThreeGangStatus(InitialEvent event, Emitter emit) async { + void _fetchThreeGangStatus( + InitialEvent event, Emitter emit) async { emit(LoadingInitialState()); try { threeGangGroup = event.groupScreen; @@ -69,7 +71,8 @@ class ThreeGangBloc extends Bloc { HomeCubit.getInstance().selectedSpace?.id ?? '', '3G'); for (int i = 0; i < devicesList.length; i++) { - var response = await DevicesAPI.getDeviceStatus(devicesList[i].uuid ?? ''); + var response = + await DevicesAPI.getDeviceStatus(devicesList[i].uuid ?? ''); List statusModelList = []; for (var status in response['status']) { statusModelList.add(StatusModel.fromJson(status)); @@ -86,13 +89,16 @@ class ThreeGangBloc extends Bloc { if (groupThreeGangList.isNotEmpty) { groupThreeGangList.firstWhere((element) { - if (!element.firstSwitch || !element.secondSwitch || !element.thirdSwitch) { + if (!element.firstSwitch || + !element.secondSwitch || + !element.thirdSwitch) { allSwitchesOn = false; } return true; }); } - emit(UpdateGroupState(threeGangList: groupThreeGangList, allSwitches: allSwitchesOn)); + emit(UpdateGroupState( + threeGangList: groupThreeGangList, allSwitches: allSwitchesOn)); } else { var response = await DevicesAPI.getDeviceStatus(threeGangId); List statusModelList = []; @@ -111,18 +117,21 @@ class ThreeGangBloc extends Bloc { _listenToChanges() { try { - DatabaseReference ref = FirebaseDatabase.instance.ref('device-status/$threeGangId'); + DatabaseReference ref = + FirebaseDatabase.instance.ref('device-status/$threeGangId'); Stream stream = ref.onValue; - stream.listen((DatabaseEvent event) async { + stream.listen((DatabaseEvent event) async { if (_timer != null) { await Future.delayed(const Duration(seconds: 2)); } - Map usersMap = event.snapshot.value as Map; + Map usersMap = + event.snapshot.value as Map; List statusList = []; usersMap['status'].forEach((element) { - statusList.add(StatusModel(code: element['code'], value: element['value'])); + statusList + .add(StatusModel(code: element['code'], value: element['value'])); }); deviceStatus = ThreeGangModel.fromJson(statusList); @@ -137,7 +146,8 @@ class ThreeGangBloc extends Bloc { emit(UpdateState(threeGangModel: deviceStatus)); } - void _changeFirstSwitch(ChangeFirstSwitchStatusEvent event, Emitter emit) async { + void _changeFirstSwitch( + ChangeFirstSwitchStatusEvent event, Emitter emit) async { emit(LoadingNewSate(threeGangModel: deviceStatus)); try { if (threeGangGroup) { @@ -146,11 +156,14 @@ class ThreeGangBloc extends Bloc { if (element.deviceId == event.deviceId) { element.firstSwitch = !event.value; } - if (!element.firstSwitch || !element.secondSwitch || !element.thirdSwitch) { + if (!element.firstSwitch || + !element.secondSwitch || + !element.thirdSwitch) { allSwitchesValue = false; } }); - emit(UpdateGroupState(threeGangList: groupThreeGangList, allSwitches: allSwitchesValue)); + emit(UpdateGroupState( + threeGangList: groupThreeGangList, allSwitches: allSwitchesValue)); } else { deviceStatus.firstSwitch = !event.value; emit(UpdateState(threeGangModel: deviceStatus)); @@ -187,11 +200,14 @@ class ThreeGangBloc extends Bloc { if (element.deviceId == event.deviceId) { element.secondSwitch = !event.value; } - if (!element.firstSwitch || !element.secondSwitch || !element.thirdSwitch) { + if (!element.firstSwitch || + !element.secondSwitch || + !element.thirdSwitch) { allSwitchesValue = false; } }); - emit(UpdateGroupState(threeGangList: groupThreeGangList, allSwitches: allSwitchesValue)); + emit(UpdateGroupState( + threeGangList: groupThreeGangList, allSwitches: allSwitchesValue)); } else { deviceStatus.secondSwitch = !event.value; emit(UpdateState(threeGangModel: deviceStatus)); @@ -217,7 +233,8 @@ class ThreeGangBloc extends Bloc { } } - void _changeThirdSwitch(ChangeThirdSwitchStatusEvent event, Emitter emit) async { + void _changeThirdSwitch( + ChangeThirdSwitchStatusEvent event, Emitter emit) async { emit(LoadingNewSate(threeGangModel: deviceStatus)); try { if (threeGangGroup) { @@ -226,11 +243,14 @@ class ThreeGangBloc extends Bloc { if (element.deviceId == event.deviceId) { element.thirdSwitch = !event.value; } - if (!element.firstSwitch || !element.secondSwitch || !element.thirdSwitch) { + if (!element.firstSwitch || + !element.secondSwitch || + !element.thirdSwitch) { allSwitchesValue = false; } }); - emit(UpdateGroupState(threeGangList: groupThreeGangList, allSwitches: allSwitchesValue)); + emit(UpdateGroupState( + threeGangList: groupThreeGangList, allSwitches: allSwitchesValue)); } else { deviceStatus.thirdSwitch = !event.value; emit(UpdateState(threeGangModel: deviceStatus)); @@ -269,15 +289,21 @@ class ThreeGangBloc extends Bloc { final response = await Future.wait([ DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeGangId, code: 'switch_1', value: deviceStatus.firstSwitch), + deviceId: threeGangId, + code: 'switch_1', + value: deviceStatus.firstSwitch), threeGangId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeGangId, code: 'switch_2', value: deviceStatus.secondSwitch), + deviceId: threeGangId, + code: 'switch_2', + value: deviceStatus.secondSwitch), threeGangId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeGangId, code: 'switch_3', value: deviceStatus.thirdSwitch), + deviceId: threeGangId, + code: 'switch_3', + value: deviceStatus.thirdSwitch), threeGangId), ]); @@ -303,15 +329,21 @@ class ThreeGangBloc extends Bloc { final response = await Future.wait([ DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeGangId, code: 'switch_1', value: deviceStatus.firstSwitch), + deviceId: threeGangId, + code: 'switch_1', + value: deviceStatus.firstSwitch), threeGangId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeGangId, code: 'switch_2', value: deviceStatus.secondSwitch), + deviceId: threeGangId, + code: 'switch_2', + value: deviceStatus.secondSwitch), threeGangId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeGangId, code: 'switch_3', value: deviceStatus.thirdSwitch), + deviceId: threeGangId, + code: 'switch_3', + value: deviceStatus.thirdSwitch), threeGangId), ]); @@ -333,21 +365,28 @@ class ThreeGangBloc extends Bloc { groupThreeGangList[i].secondSwitch = true; groupThreeGangList[i].thirdSwitch = true; } - emit(UpdateGroupState(threeGangList: groupThreeGangList, allSwitches: true)); + emit(UpdateGroupState( + threeGangList: groupThreeGangList, allSwitches: true)); for (int i = 0; i < groupThreeGangList.length; i++) { final response = await Future.wait([ DevicesAPI.controlDevice( DeviceControlModel( - deviceId: groupThreeGangList[i].deviceId, code: 'switch_1', value: true), + deviceId: groupThreeGangList[i].deviceId, + code: 'switch_1', + value: true), groupThreeGangList[i].deviceId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: groupThreeGangList[i].deviceId, code: 'switch_2', value: true), + deviceId: groupThreeGangList[i].deviceId, + code: 'switch_2', + value: true), groupThreeGangList[i].deviceId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: groupThreeGangList[i].deviceId, code: 'switch_3', value: true), + deviceId: groupThreeGangList[i].deviceId, + code: 'switch_3', + value: true), groupThreeGangList[i].deviceId), ]); @@ -363,7 +402,8 @@ class ThreeGangBloc extends Bloc { } } - void _groupAllOff(GroupAllOffEvent event, Emitter emit) async { + void _groupAllOff( + GroupAllOffEvent event, Emitter emit) async { emit(LoadingNewSate(threeGangModel: deviceStatus)); try { for (int i = 0; i < groupThreeGangList.length; i++) { @@ -371,21 +411,28 @@ class ThreeGangBloc extends Bloc { groupThreeGangList[i].secondSwitch = false; groupThreeGangList[i].thirdSwitch = false; } - emit(UpdateGroupState(threeGangList: groupThreeGangList, allSwitches: false)); + emit(UpdateGroupState( + threeGangList: groupThreeGangList, allSwitches: false)); for (int i = 0; i < groupThreeGangList.length; i++) { final response = await Future.wait([ DevicesAPI.controlDevice( DeviceControlModel( - deviceId: groupThreeGangList[i].deviceId, code: 'switch_1', value: false), + deviceId: groupThreeGangList[i].deviceId, + code: 'switch_1', + value: false), groupThreeGangList[i].deviceId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: groupThreeGangList[i].deviceId, code: 'switch_2', value: false), + deviceId: groupThreeGangList[i].deviceId, + code: 'switch_2', + value: false), groupThreeGangList[i].deviceId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: groupThreeGangList[i].deviceId, code: 'switch_3', value: false), + deviceId: groupThreeGangList[i].deviceId, + code: 'switch_3', + value: false), groupThreeGangList[i].deviceId), ]); @@ -401,17 +448,20 @@ class ThreeGangBloc extends Bloc { } } - void _changeSliding(ChangeSlidingSegment event, Emitter emit) async { + void _changeSliding( + ChangeSlidingSegment event, Emitter emit) async { emit(ChangeSlidingSegmentState(value: event.value)); } - void _setCounterValue(SetCounterValue event, Emitter emit) async { + void _setCounterValue( + SetCounterValue event, Emitter emit) async { emit(LoadingNewSate(threeGangModel: deviceStatus)); int seconds = 0; try { seconds = event.duration.inSeconds; final response = await DevicesAPI.controlDevice( - DeviceControlModel(deviceId: threeGangId, code: event.deviceCode, value: seconds), + DeviceControlModel( + deviceId: threeGangId, code: event.deviceCode, value: seconds), threeGangId); if (response['success'] ?? false) { @@ -438,7 +488,8 @@ class ThreeGangBloc extends Bloc { } } - void _getCounterValue(GetCounterEvent event, Emitter emit) async { + void _getCounterValue( + GetCounterEvent event, Emitter emit) async { emit(LoadingInitialState()); try { var response = await DevicesAPI.getDeviceStatus(threeGangId); @@ -541,6 +592,8 @@ class ThreeGangBloc extends Bloc { GetScheduleEvent event, Emitter emit, ) async { + print('getSchedule=${switchCode}'); + try { emit(LoadingInitialState()); final response = await DevicesAPI.getSchedule( @@ -548,7 +601,8 @@ class ThreeGangBloc extends Bloc { deviceId: threeGangId, ); List jsonData = response; - listSchedule = jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); + listSchedule = + jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); emit(InitialState()); } on DioException catch (e) { final errorData = e.response!.data; @@ -559,12 +613,13 @@ class ThreeGangBloc extends Bloc { int? getTimeStampWithoutSeconds(DateTime? dateTime) { if (dateTime == null) return null; - DateTime dateTimeWithoutSeconds = - DateTime(dateTime.year, dateTime.month, dateTime.day, dateTime.hour, dateTime.minute); + DateTime dateTimeWithoutSeconds = DateTime(dateTime.year, dateTime.month, + dateTime.day, dateTime.hour, dateTime.minute); return dateTimeWithoutSeconds.millisecondsSinceEpoch ~/ 1000; } - Future toggleChange(ToggleScheduleEvent event, Emitter emit) async { + Future toggleChange( + ToggleScheduleEvent event, Emitter emit) async { try { emit(LoadingInitialState()); final response = await DevicesAPI.changeSchedule( @@ -583,7 +638,8 @@ class ThreeGangBloc extends Bloc { } } - Future deleteSchedule(DeleteScheduleEvent event, Emitter emit) async { + Future deleteSchedule( + DeleteScheduleEvent event, Emitter emit) async { try { emit(LoadingInitialState()); final response = await DevicesAPI.deleteSchedule( @@ -603,13 +659,15 @@ class ThreeGangBloc extends Bloc { } } - void toggleSelectedIndex(ToggleSelectedEvent event, Emitter emit) { + void toggleSelectedIndex( + ToggleSelectedEvent event, Emitter emit) { emit(LoadingInitialState()); selectedTabIndex = event.index; emit(ChangeSlidingSegmentState(value: selectedTabIndex)); } - void toggleCreateSchedule(ToggleCreateScheduleEvent event, Emitter emit) { + void toggleCreateSchedule( + ToggleCreateScheduleEvent event, Emitter emit) { emit(LoadingInitialState()); createSchedule = !createSchedule; selectedDays.clear(); diff --git a/lib/features/devices/model/garage_door_model.dart b/lib/features/devices/model/garage_door_model.dart new file mode 100644 index 0000000..146523a --- /dev/null +++ b/lib/features/devices/model/garage_door_model.dart @@ -0,0 +1,81 @@ +import 'package:syncrow_app/features/devices/model/status_model.dart'; + +class GarageDoorModel { + bool switch1; + bool doorContactState; + int countdown1; + int countdownAlarm; + String doorControl1; + bool voiceControl1; + String doorState1; + int batteryPercentage; + int tr_timecon; + + GarageDoorModel({ + required this.switch1, + required this.doorContactState, + required this.countdown1, + required this.countdownAlarm, + required this.doorControl1, + required this.voiceControl1, + required this.doorState1, + required this.batteryPercentage, + required this.tr_timecon, + }); + + factory GarageDoorModel.fromJson(List jsonList) { + late bool _switch1 = false; + late bool _doorContactState = false; + late int _countdown1 = 0; + late int _countdownAlarm = 0; + late String _doorControl1 = "closed"; + late bool _voiceControl1 = false; + late String _doorState1 = "closed"; + late int _batteryPercentage = 0; + late int _tr_timecon = 0; + + for (var status in jsonList) { + switch (status.code) { + case 'tr_timecon': + _tr_timecon = status.value ?? "closed"; + break; + case 'switch_1': + _switch1 = status.value ?? false; + break; + case 'doorcontact_state': + _doorContactState = status.value ?? false; + break; + case 'countdown_1': + _countdown1 = status.value ?? 0; + break; + case 'countdown_alarm': + _countdownAlarm = status.value ?? 0; + break; + case 'door_control_1': + _doorControl1 = status.value ?? "closed"; + break; + + case 'voice_control_1': + _voiceControl1 = status.value ?? false; + break; + case 'door_state_1': + _doorState1 = status.value ?? "closed"; + break; + case 'battery_percentage': + _batteryPercentage = status.value ?? 0; + break; + } + } + + return GarageDoorModel( + switch1: _switch1, + doorContactState: _doorContactState, + countdown1: _countdown1, + countdownAlarm: _countdownAlarm, + doorControl1: _doorControl1, + voiceControl1: _voiceControl1, + doorState1: _doorState1, + batteryPercentage: _batteryPercentage, + tr_timecon: _tr_timecon); + } +} diff --git a/lib/features/devices/view/widgets/garage_door/create_schedule_garage.dart b/lib/features/devices/view/widgets/garage_door/create_schedule_garage.dart new file mode 100644 index 0000000..9410935 --- /dev/null +++ b/lib/features/devices/view/widgets/garage_door/create_schedule_garage.dart @@ -0,0 +1,204 @@ +import 'package:flutter/cupertino.dart'; +import 'package:flutter/material.dart'; +import 'package:syncrow_app/features/devices/view/widgets/garage_door/garagedialog.dart'; +import 'package:syncrow_app/features/shared_widgets/default_container.dart'; +import 'package:syncrow_app/features/shared_widgets/text_widgets/body_medium.dart'; +import 'package:syncrow_app/utils/resource_manager/color_manager.dart'; + +class CreateGarageSchedule extends StatefulWidget { + final List> days; + final void Function(List selectedDays)? + selectDays; + final Function(DateTime) onDateTimeChanged; + final void Function(bool isOn)? onToggleChanged; + + const CreateGarageSchedule({ + Key? key, + required this.days, + required this.selectDays, + required this.onDateTimeChanged, + this.onToggleChanged, + }) : super(key: key); + + @override + _CreateGarageScheduleState createState() => _CreateGarageScheduleState(); +} + +class _CreateGarageScheduleState extends State { + List selectedDays = []; + bool isOn = true; + String selectedControlOption = 'Open'; + + @override + Widget build(BuildContext context) { + return Container( + padding: const EdgeInsets.symmetric(horizontal: 5, vertical: 5), + child: Column( + children: [ + const Divider( + color: ColorsManager.greyColor, + ), + SizedBox( + height: 110, + child: CupertinoDatePicker( + mode: CupertinoDatePickerMode.time, + initialDateTime: DateTime.now(), + onDateTimeChanged: widget.onDateTimeChanged, + ), + ), + const Divider( + color: ColorsManager.greyColor, + ), + const SizedBox(height: 20), + SizedBox( + height: MediaQuery.of(context).size.height * 0.08, + child: ListView( + scrollDirection: Axis.horizontal, + children: widget.days.map((day) { + bool isSelected = selectedDays.contains(day['day']); + return Padding( + padding: const EdgeInsets.all(8.0), + child: InkWell( + onTap: () { + setState(() { + if (isSelected) { + selectedDays.remove(day['day']); + } else { + selectedDays.add(day['day']!); + } + if (widget.selectDays != null) { + widget.selectDays!(selectedDays); + } + }); + }, + child: Container( + width: 50, + padding: const EdgeInsets.symmetric( + vertical: 8, horizontal: 8), + decoration: BoxDecoration( + border: Border.all( + color: isSelected + ? Colors.black + : ColorsManager.grayColor, + ), + color: Colors.transparent, + borderRadius: BorderRadius.circular(30), + ), + child: Center( + child: Text( + day['day']!, + style: TextStyle( + fontSize: 13, + color: isSelected + ? Colors.black + : ColorsManager.grayColor, + ), + ), + ), + ), + ), + ); + }).toList(), + ), + ), + const SizedBox(height: 20), + DefaultContainer( + child: Column( + mainAxisAlignment: MainAxisAlignment.start, + mainAxisSize: MainAxisSize.min, + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + SizedBox( + height: 50, + child: ListTile( + contentPadding: EdgeInsets.zero, + leading: const BodyMedium( + text: 'Notification', + fontWeight: FontWeight.normal, + ), + trailing: Transform.scale( + scale: .8, + child: CupertinoSwitch( + value: true, + onChanged: (value) { + }, + applyTheme: true, + )), + ), + ), + const Divider( + color: ColorsManager.graysColor, + ), + SizedBox( + height: 50, + child: InkWell( + onTap: () { + showDialog( + context: context, + builder: (context) { + return GarageDialog( + label2: 'Close', + initialSelectedLabel: selectedControlOption, + cancelTab: () { + Navigator.of(context).pop(); + }, + confirmTab: () { + setState(() {}); + if (selectedControlOption == "Open") { + widget.onToggleChanged!(true); + } else if (selectedControlOption == 'Close') { + widget.onToggleChanged!(false); + } + + Navigator.of(context).pop(); + }, + title: 'Control', + label1: 'Open', + onTapLabel1: (selected) { + setState(() { + selectedControlOption = 'Open'; + }); + }, + onTapLabel2: (selected) { + setState(() { + selectedControlOption = 'Close'; + }); + }, + ); + }, + ); + }, + child: ListTile( + contentPadding: EdgeInsets.zero, + leading: const BodyMedium( + text: 'Control', + fontWeight: FontWeight.normal, + ), + trailing: SizedBox( + width: 70, + child: Row( + mainAxisAlignment: MainAxisAlignment.spaceBetween, + children: [ + BodyMedium( + fontColor: ColorsManager.textGray, + text: selectedControlOption, + fontWeight: FontWeight.normal, + ), + const Icon( + Icons.arrow_forward_ios, + color: ColorsManager.textGray, + size: 17, + ) + ], + ), + )), + ), + ), + ], + ), + ), + ], + ), + ); + } +} diff --git a/lib/features/devices/view/widgets/garage_door/garage_door_screen.dart b/lib/features/devices/view/widgets/garage_door/garage_door_screen.dart new file mode 100644 index 0000000..8fb6a9f --- /dev/null +++ b/lib/features/devices/view/widgets/garage_door/garage_door_screen.dart @@ -0,0 +1,428 @@ +import 'package:flutter/material.dart'; +import 'package:flutter/widgets.dart'; +import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:flutter_svg/flutter_svg.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_event.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_state.dart'; +import 'package:syncrow_app/features/devices/model/device_model.dart'; +import 'package:syncrow_app/features/devices/model/garage_door_model.dart'; +import 'package:syncrow_app/features/devices/view/widgets/garage_door/garage_preferences_settings.dart'; +import 'package:syncrow_app/features/devices/view/widgets/garage_door/garage_records_screen.dart'; +import 'package:syncrow_app/features/devices/view/widgets/garage_door/schedule_garage_screen.dart'; +import 'package:syncrow_app/features/devices/view/widgets/garage_door/timer_page.dart'; +import 'package:syncrow_app/features/shared_widgets/default_container.dart'; +import 'package:syncrow_app/features/shared_widgets/default_scaffold.dart'; +import 'package:syncrow_app/features/shared_widgets/text_widgets/body_small.dart'; +import 'package:syncrow_app/generated/assets.dart'; + +class GarageDoorScreen extends StatelessWidget { + final DeviceModel? device; + + const GarageDoorScreen({super.key, this.device}); + + @override + Widget build(BuildContext context) { + return DefaultScaffold( + title: 'Garage Door Opener', + child: BlocProvider( + create: (context) => GarageDoorBloc(GDId: device?.uuid ?? '') + ..add(const GarageDoorInitial()), + child: BlocBuilder( + builder: (context, state) { + final garageBloc = BlocProvider.of(context); + GarageDoorModel model = GarageDoorModel( + tr_timecon: 0, + countdown1: 0, + countdownAlarm: 0, + doorContactState: false, + doorControl1: '', + doorState1: '', + switch1: false, + voiceControl1: false, + batteryPercentage: 0, + ); + + if (state is LoadingNewSate) { + model = state.doorSensor; + } else if (state is UpdateState) { + model = state.garageSensor; + } + return state is GarageDoorLoadingState + ? const Center( + child: DefaultContainer( + width: 50, + height: 50, + child: CircularProgressIndicator()), + ) + : RefreshIndicator( + onRefresh: () async { + garageBloc.add(const GarageDoorInitial()); + }, + child: ListView( + children: [ + SizedBox( + height: MediaQuery.sizeOf(context).height * 0.8, + child: Column( + children: [ + Expanded( + flex: 4, + child: InkWell( + overlayColor: WidgetStateProperty.all( + Colors.transparent), + onTap: () {}, + child: Row( + mainAxisAlignment: MainAxisAlignment.center, + crossAxisAlignment: + CrossAxisAlignment.center, + children: [ + Container( + decoration: BoxDecoration( + borderRadius: + BorderRadius.circular(890), + boxShadow: [ + BoxShadow( + color: Colors.white + .withOpacity(0.1), + blurRadius: 24, + offset: const Offset(-5, -5), + blurStyle: BlurStyle.outer, + ), + BoxShadow( + color: Colors.black + .withOpacity(0.11), + blurRadius: 25, + offset: const Offset(5, 5), + blurStyle: BlurStyle.outer, + ), + BoxShadow( + color: Colors.black + .withOpacity(0.13), + blurRadius: 30, + offset: const Offset(5, 5), + blurStyle: BlurStyle.inner, + ), + ], + ), + child: InkWell( + onTap: () { + garageBloc.add(ToggleDoorEvent( + toggle: + garageBloc.toggleDoor)); + }, + child: GradientWidget( + doorStatus: garageBloc.toggleDoor, + seconds: + garageBloc.secondSelected, + ), + )), + ], + ), + ), + ), + Flexible( + child: Row( + children: [ + Expanded( + child: DefaultContainer( + onTap: () { + Navigator.of(context).push( + MaterialPageRoute( + builder: (context) => + TimerScheduleScreen( + device: device!, + switchCode: 'switch_1', + deviceCode: 'countdown_1', + )), + ); + }, + child: Column( + crossAxisAlignment: + CrossAxisAlignment.center, + mainAxisAlignment: + MainAxisAlignment.center, + children: [ + ConstrainedBox( + constraints: const BoxConstraints( + maxHeight: 46, maxWidth: 50), + child: SvgPicture.asset( + Assets.garageSchedule), + ), + const SizedBox( + height: 15, + ), + const Flexible( + child: FittedBox( + child: BodySmall( + text: 'Schedule', + textAlign: TextAlign.center, + ), + ), + ), + ], + ), + ), + ), + const SizedBox( + width: 10, + ), + Expanded( + child: DefaultContainer( + onTap: () { + Navigator.of(context).push( + MaterialPageRoute( + builder: (context) => TimerPage( + device: device!, + switchCode: 'switch_1', + deviceCode: 'countdown_1', + )), + ); + }, + child: Column( + crossAxisAlignment: + CrossAxisAlignment.center, + mainAxisAlignment: + MainAxisAlignment.center, + children: [ + ConstrainedBox( + constraints: const BoxConstraints( + maxHeight: 46, maxWidth: 50), + child: SvgPicture.asset( + Assets.garageCountdown), + ), + const SizedBox( + height: 15, + ), + const Flexible( + child: FittedBox( + child: BodySmall( + text: 'Countdown', + textAlign: TextAlign.center, + ), + ), + ), + ], + ), + ), + ), + ], + ), + ), + const SizedBox( + height: 10, + ), + Flexible( + child: Row( + children: [ + Expanded( + child: DefaultContainer( + onTap: () { + Navigator.of(context).push( + MaterialPageRoute( + builder: (context) => + GarageRecordsScreen( + GDId: device!.uuid!)), + ); + }, + child: Column( + crossAxisAlignment: + CrossAxisAlignment.center, + mainAxisAlignment: + MainAxisAlignment.center, + children: [ + ConstrainedBox( + constraints: const BoxConstraints( + maxHeight: 46, maxWidth: 50), + child: SvgPicture.asset( + Assets.doorRecordsIcon), + ), + const SizedBox( + height: 15, + ), + const Flexible( + child: FittedBox( + child: BodySmall( + text: 'Records', + textAlign: TextAlign.center, + ), + ), + ), + ], + ), + ), + ), + const SizedBox( + width: 10, + ), + Expanded( + child: DefaultContainer( + onTap: () { + Navigator.of(context).push( + MaterialPageRoute( + builder: (context) => + PreferencesPage( + GDId: device!.uuid!)), + ); + }, + child: Column( + crossAxisAlignment: + CrossAxisAlignment.center, + mainAxisAlignment: + MainAxisAlignment.center, + children: [ + ConstrainedBox( + constraints: const BoxConstraints( + maxHeight: 46, maxWidth: 50), + child: SvgPicture.asset( + Assets.garagePreferencesIcon), + ), + const SizedBox( + height: 15, + ), + const Flexible( + child: FittedBox( + child: BodySmall( + text: 'Preferences', + textAlign: TextAlign.center, + ), + ), + ), + ], + ), + ), + ), + ], + ), + ) + ], + ), + ), + ], + ), + ); + }, + ), + ), + ); + } +} + +class GradientWidget extends StatefulWidget { + const GradientWidget({required this.seconds, required this.doorStatus}); + final int seconds; + final bool doorStatus; + + @override + State createState() => _GradientWidgetState(); +} + +class _GradientWidgetState extends State + with SingleTickerProviderStateMixin { + late ScrollController _scrollController; + late AnimationController _animationController; + late Animation _itemExtentAnimation; + + @override + void initState() { + super.initState(); + _scrollController = ScrollController(); + _animationController = AnimationController( + vsync: this, + duration: Duration(seconds: widget.seconds), + ); + _itemExtentAnimation = Tween( + begin: widget.doorStatus ? 0 : 15, end: widget.doorStatus ? 15 : 0) + .animate( + CurvedAnimation( + parent: _animationController, + curve: Curves.easeInOut, + ), + )..addListener(() { + setState(() {}); + }); + + WidgetsBinding.instance.addPostFrameCallback((_) { + if (widget.doorStatus) { + _openAnimation(); + } else { + _closeAnimation(); + } + }); + } + + void _openAnimation() { + _animationController.forward(); + } + + void _closeAnimation() { + _animationController.reverse(); + } + + @override + void dispose() { + _scrollController.dispose(); + _animationController.dispose(); + super.dispose(); + } + + @override + Widget build(BuildContext context) { + return Container( + width: 300, + height: 300, + padding: EdgeInsets.only(right: 10), + child: Stack( + children: [ + SvgPicture.asset( + Assets.openGarageIcon, + fit: BoxFit.fill, + ), + Column( + crossAxisAlignment: CrossAxisAlignment.center, + mainAxisAlignment: MainAxisAlignment.center, + children: [ + Expanded(child: Container()), + Expanded( + flex: 2, + child: Center( + child: Container( + height: 104, + child: ListView.builder( + itemExtent: _itemExtentAnimation.value, + controller: _scrollController, + itemCount: 4, + itemBuilder: (context, index) { + return Center(child: GradientWidget1()); + }, + ), + ), + ), + ), + ], + ), + ], + ), + ); + } +} + +class GradientWidget1 extends StatelessWidget { + @override + Widget build(BuildContext context) { + return Container( + width: 97, + height: 15, + decoration: const BoxDecoration( + gradient: LinearGradient( + begin: Alignment.topCenter, + end: Alignment.bottomCenter, + colors: [ + Color(0xFF017297), + Color(0xFF024C67), + ], + stops: [0.0, 1.0], + ), + ), + ); + } +} diff --git a/lib/features/devices/view/widgets/garage_door/garage_preferences_settings.dart b/lib/features/devices/view/widgets/garage_door/garage_preferences_settings.dart new file mode 100644 index 0000000..e591b33 --- /dev/null +++ b/lib/features/devices/view/widgets/garage_door/garage_preferences_settings.dart @@ -0,0 +1,341 @@ +import 'package:flutter/cupertino.dart'; +import 'package:flutter/material.dart'; +import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_event.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_state.dart'; +import 'package:syncrow_app/features/shared_widgets/default_container.dart'; +import 'package:syncrow_app/features/shared_widgets/default_scaffold.dart'; +import 'package:syncrow_app/features/shared_widgets/text_widgets/body_large.dart'; +import 'package:syncrow_app/features/shared_widgets/text_widgets/body_medium.dart'; +import 'package:syncrow_app/features/shared_widgets/text_widgets/body_small.dart'; +import 'package:syncrow_app/utils/resource_manager/color_manager.dart'; + +class PreferencesPage extends StatelessWidget { + final String GDId; + const PreferencesPage({super.key, required this.GDId}); + @override + Widget build(BuildContext context) { + return DefaultScaffold( + title: 'Preferences', + child: BlocProvider( + create: (context) => + GarageDoorBloc(GDId: GDId)..add(const GarageDoorInitial()), + child: BlocBuilder( + builder: (context, state) { + final garageDoorBloc = BlocProvider.of(context); + + return state is GarageDoorLoadingState + ? const Center( + child: DefaultContainer( + width: 50, + height: 50, + child: CircularProgressIndicator()), + ) + : Column( + children: [ + const Row( + children: [ + BodyMedium( + text: 'Warnings', + fontColor: ColorsManager.grayColor, + fontWeight: FontWeight.w700, + ), + ], + ), + DefaultContainer( + child: Column( + mainAxisAlignment: MainAxisAlignment.start, + mainAxisSize: MainAxisSize.min, + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + SizedBox( + height: 50, + child: ListTile( + contentPadding: EdgeInsets.zero, + leading: const BodyMedium( + text: 'Alarm when door is open', + fontWeight: FontWeight.normal, + ), + trailing: Container( + width: 100, + child: Row( + mainAxisAlignment: + MainAxisAlignment.end, + children: [ + Container( + height: 30, + width: 1, + color: ColorsManager.graysColor, + ), + Transform.scale( + scale: .8, + child: CupertinoSwitch( + value: + garageDoorBloc.lowBattery, + onChanged: (value) { + // context + // .read() + // .add( + // ToggleLowBatteryEvent( + // value)); + }, + applyTheme: true, + )), + ], + ), + )), + ), + ], + ), + ), + const SizedBox( + height: 10, + ), + const Row( + children: [ + BodyMedium( + text: 'Other Settings', + fontColor: ColorsManager.grayColor, + fontWeight: FontWeight.w700, + ), + ], + ), + DefaultContainer( + child: InkWell( + onTap: () { + showDialog( + context: context, + builder: (context) { + return SecondDialog( + label2: 'Close', + initialSelectedLabel: garageDoorBloc + .secondSelected + .toString(), + cancelTab: () { + Navigator.of(context).pop(); + }, + confirmTab: (v) { + garageDoorBloc + .add(SelectSecondsEvent(seconds: v)); + Navigator.of(context).pop(); + }, + title: 'Control', + label1: 'Open', + onTapLabel1: (selected) {}, + ); + }, + ); + }, + child: SizedBox( + child: ListTile( + contentPadding: EdgeInsets.zero, + leading: const BodyMedium( + text: 'Opening and Closing Time', + fontWeight: FontWeight.normal, + ), + trailing: Container( + height: 90, + width: 120, + child: Row( + crossAxisAlignment: + CrossAxisAlignment.center, + mainAxisAlignment: + MainAxisAlignment.spaceBetween, + children: [ + BodyMedium( + fontColor: ColorsManager.textGray, + text: + '${garageDoorBloc.secondSelected.toString()} Seconds', + fontWeight: FontWeight.normal, + ), + const Icon( + Icons.arrow_forward_ios, + size: 15, + color: ColorsManager.textGray, + ) + ], + ), + )), + ), + ), + ) + ], + ); + }, + ), + )); + } +} + +class SecondDialog extends StatefulWidget { + final String label1; + final String label2; + final String title; + + final Function(String)? onTapLabel1; + final Function()? cancelTab; + final Function(int selectedSecond)? confirmTab; + + final String? initialSelectedLabel; + + SecondDialog({ + required this.label1, + required this.label2, + required this.title, + this.onTapLabel1, + required this.cancelTab, + required this.confirmTab, + this.initialSelectedLabel, + }); + + @override + _SecondDialogState createState() => _SecondDialogState(); +} + +class _SecondDialogState extends State { + late String _selectedOption; + late int selectedSecond; + + @override + void initState() { + super.initState(); + // Parse the initialSelectedLabel as an integer. Default to 10 if invalid or not provided. + selectedSecond = int.tryParse(widget.initialSelectedLabel ?? '10') ?? 10; + _selectedOption = widget.initialSelectedLabel ?? ''; + } + + @override + Widget build(BuildContext context) { + return AlertDialog( + contentPadding: EdgeInsets.zero, + content: Column( + mainAxisSize: MainAxisSize.min, + children: [ + const SizedBox( + height: 10, + ), + BodyLarge( + text: widget.title, + fontWeight: FontWeight.w700, + fontColor: ColorsManager.primaryColor, + fontSize: 16, + ), + const Padding( + padding: EdgeInsets.only(left: 15, right: 15), + child: Divider( + color: ColorsManager.textGray, + ), + ), + Padding( + padding: const EdgeInsets.only(left: 15, right: 15, bottom: 10), + child: Column( + children: [ + Center( + child: Row( + mainAxisAlignment: MainAxisAlignment.center, + children: [ + Container( + width: 100, + child: CupertinoPicker( + itemExtent: 40.0, + scrollController: FixedExtentScrollController( + // Set the initial position based on selectedSecond + initialItem: selectedSecond - 10, + ), + onSelectedItemChanged: (int index) { + setState(() { + selectedSecond = index + 10; + }); + }, + children: List.generate(111, (int index) { + return Center( + child: BodyLarge( + text: (index + 10).toString().padLeft(2, '0'), + style: const TextStyle( + fontWeight: FontWeight.w400, + fontSize: 30, + color: Colors.blue), + ), + ); + }), + ), + ), + const Text('Sec'), + ], + ), + ) + ], + ), + ), + Row( + children: [ + Expanded( + child: Container( + decoration: const BoxDecoration( + border: Border( + right: BorderSide( + color: ColorsManager.textGray, + width: 0.5, + ), + top: BorderSide( + color: ColorsManager.textGray, + width: 1.0, + ), + )), + child: SizedBox( + child: InkWell( + onTap: widget.cancelTab, + child: const Padding( + padding: EdgeInsets.all(15), + child: Center( + child: Text( + 'Cancel', + style: TextStyle( + color: ColorsManager.textGray, + fontSize: 14, + fontWeight: FontWeight.w400), + ), + ), + ), + ), + ), + ), + ), + Expanded( + child: Container( + decoration: const BoxDecoration( + border: Border( + left: BorderSide( + color: ColorsManager.textGray, + width: 0.5, + ), + top: BorderSide( + color: ColorsManager.textGray, + width: 1.0, + ), + )), + child: InkWell( + onTap: () { + widget.confirmTab?.call(selectedSecond); + }, + child: const Padding( + padding: EdgeInsets.all(15), + child: Center( + child: Text( + 'Confirm', + style: TextStyle( + color: ColorsManager.primaryColor, + fontSize: 14, + fontWeight: FontWeight.w400), + ), + ), + )), + )) + ], + ) + ], + ), + ); + } +} diff --git a/lib/features/devices/view/widgets/garage_door/garage_records_screen.dart b/lib/features/devices/view/widgets/garage_door/garage_records_screen.dart new file mode 100644 index 0000000..f2389e1 --- /dev/null +++ b/lib/features/devices/view/widgets/garage_door/garage_records_screen.dart @@ -0,0 +1,122 @@ +import 'package:flutter/material.dart'; +import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:intl/intl.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_event.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_state.dart'; +import 'package:syncrow_app/features/devices/model/device_report_model.dart'; +import 'package:syncrow_app/features/shared_widgets/default_container.dart'; +import 'package:syncrow_app/features/shared_widgets/default_scaffold.dart'; +import 'package:syncrow_app/utils/resource_manager/color_manager.dart'; + +class GarageRecordsScreen extends StatelessWidget { + final String GDId; + const GarageRecordsScreen({super.key, required this.GDId}); + + @override + Widget build(BuildContext context) { + return DefaultScaffold( + title: 'Records', + child: BlocProvider( + create: (context) => + GarageDoorBloc(GDId: GDId)..add(const ReportLogsInitial()), + child: BlocBuilder( + builder: (context, state) { + final garageDoorBloc = BlocProvider.of(context); + final Map> groupedRecords = {}; + + if (state is GarageDoorLoadingState) { + return const Center( + child: DefaultContainer( + width: 50, height: 50, child: CircularProgressIndicator()), + ); + } else if (state is UpdateState) { + for (var record in garageDoorBloc.recordGroups.data!) { + final DateTime eventDateTime = + DateTime.fromMillisecondsSinceEpoch(record.eventTime!); + final String formattedDate = + DateFormat('EEEE, dd/MM/yyyy').format(eventDateTime); + + // Group by formatted date + if (groupedRecords.containsKey(formattedDate)) { + groupedRecords[formattedDate]!.add(record); + } else { + groupedRecords[formattedDate] = [record]; + } + } + } + return ListView.builder( + itemCount: groupedRecords.length, + itemBuilder: (context, index) { + final String date = groupedRecords.keys.elementAt(index); + final List recordsForDate = groupedRecords[date]!; + + return Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + Padding( + padding: const EdgeInsets.only(bottom: 5, top: 10), + child: Text( + date, + style: const TextStyle( + color: ColorsManager.grayColor, + fontSize: 13, + fontWeight: FontWeight.w700, + ), + ), + ), + DefaultContainer( + child: Column( + children: [ + ...recordsForDate.asMap().entries.map((entry) { + final int idx = entry.key; + final DeviceEvent record = entry.value; + final DateTime eventDateTime = + DateTime.fromMillisecondsSinceEpoch( + record.eventTime!); + final String formattedTime = + DateFormat('HH:mm:ss').format(eventDateTime); + + return Column( + children: [ + Container( + child: ListTile( + leading: Icon( + record.value == 'true' + ? Icons.radio_button_checked + : Icons.radio_button_unchecked, + color: record.value == 'true' + ? Colors.blue + : Colors.grey, + ), + title: Text( + record.value == 'true' + ? "Opened" + : "Closed", + style: const TextStyle( + fontWeight: FontWeight.bold, + fontSize: 18, + ), + ), + subtitle: Text('$formattedTime'), + ), + ), + if (idx != recordsForDate.length - 1) + const Divider( + color: ColorsManager.graysColor, + ), + ], + ); + }).toList(), + ], + ), + ), + ], + ); + }, + ); + }), + ), + ); + } +} diff --git a/lib/features/devices/view/widgets/garage_door/garagedialog.dart b/lib/features/devices/view/widgets/garage_door/garagedialog.dart new file mode 100644 index 0000000..d002d0b --- /dev/null +++ b/lib/features/devices/view/widgets/garage_door/garagedialog.dart @@ -0,0 +1,221 @@ +import 'package:flutter/material.dart'; +import 'package:syncrow_app/features/shared_widgets/text_widgets/body_large.dart'; +import 'package:syncrow_app/features/shared_widgets/text_widgets/body_medium.dart'; +import 'package:syncrow_app/utils/resource_manager/color_manager.dart'; + +class GarageDialog extends StatefulWidget { + final String label1; + final String label2; + final String title; + + final Function(String)? onTapLabel1; + final Function(String)? onTapLabel2; + final Function()? cancelTab; + final Function()? confirmTab; + + final String? initialSelectedLabel; + + GarageDialog({ + required this.label1, + required this.label2, + required this.title, + this.onTapLabel1, + this.onTapLabel2, + required this.cancelTab, + required this.confirmTab, + this.initialSelectedLabel, + }); + + @override + _GarageDialogState createState() => _GarageDialogState(); +} + +class _GarageDialogState extends State { + late String _selectedOption; + + @override + void initState() { + super.initState(); + + _selectedOption = widget.initialSelectedLabel ?? ''; + } + + @override + Widget build(BuildContext context) { + return AlertDialog( + contentPadding: EdgeInsets.zero, + content: Column( + mainAxisSize: MainAxisSize.min, + children: [ + const SizedBox( + height: 10, + ), + BodyLarge( + text: widget.title, + fontWeight: FontWeight.w700, + fontColor: ColorsManager.primaryColor, + fontSize: 16, + ), + const Padding( + padding: EdgeInsets.only(left: 15, right: 15), + child: Divider( + color: ColorsManager.textGray, + ), + ), + Padding( + padding: const EdgeInsets.only(left: 15, right: 15), + child: Column( + children: [ + _buildCheckboxOption( + label: widget.label1, + onTap: widget.onTapLabel1, + ), + _buildCheckboxOption( + label: widget.label2, + onTap: widget.onTapLabel2, + ), + ], + ), + ), + Row( + children: [ + Expanded( + child: Container( + decoration: const BoxDecoration( + border: Border( + right: BorderSide( + color: ColorsManager.textGray, + width: 0.5, + ), + top: BorderSide( + color: ColorsManager.textGray, + width: 1.0, + ), + )), + child: SizedBox( + child: InkWell( + onTap: widget.cancelTab, + child: const Padding( + padding: EdgeInsets.all(15), + child: Center( + child: Text( + 'Cancel', + style: TextStyle( + color: ColorsManager.textGray, + fontSize: 14, + fontWeight: FontWeight.w400), + ), + ), + ), + ), + ), + ), + ), + Expanded( + child: Container( + decoration: const BoxDecoration( + border: Border( + left: BorderSide( + color: ColorsManager.textGray, + width: 0.5, + ), + top: BorderSide( + color: ColorsManager.textGray, + width: 1.0, + ), + )), + child: InkWell( + onTap: widget.confirmTab, + child: const Padding( + padding: EdgeInsets.all(15), + child: Center( + child: Text( + 'Confirm', + style: TextStyle( + color: ColorsManager.primaryColor, + fontSize: 14, + fontWeight: FontWeight.w400), + ), + ), + )), + )) + ], + ) + ], + ), + ); + } + + Widget _buildCheckboxOption( + {required String label, Function(String)? onTap}) { + return Padding( + padding: const EdgeInsets.only(bottom: 10, top: 10), + child: Row( + mainAxisAlignment: MainAxisAlignment.spaceBetween, + children: [ + BodyMedium( + text: label, + style: const TextStyle(fontSize: 15, fontWeight: FontWeight.w400), + ), + CircularCheckbox( + value: _selectedOption == label, + onChanged: (bool? value) { + if (value == true) { + setState(() { + _selectedOption = label; + }); + if (onTap != null) { + onTap(label); + } + } + }, + ), + ], + ), + ); + } +} + +class CircularCheckbox extends StatefulWidget { + final bool value; + final ValueChanged onChanged; + + CircularCheckbox({required this.value, required this.onChanged}); + + @override + _CircularCheckboxState createState() => _CircularCheckboxState(); +} + +class _CircularCheckboxState extends State { + @override + Widget build(BuildContext context) { + return GestureDetector( + onTap: () { + widget.onChanged(!widget.value); + }, + child: Container( + decoration: BoxDecoration( + shape: BoxShape.circle, + border: Border.all( + color: widget.value + ? ColorsManager.primaryColorWithOpacity.withOpacity(0.01) + : Colors.grey, + width: 2.0, + ), + color: widget.value + ? ColorsManager.primaryColorWithOpacity + : Colors.transparent, + ), + width: 24.0, + height: 24.0, + child: widget.value + ? const Icon( + Icons.check, + color: Colors.white, + size: 16.0, + ) + : null, + ), + ); + } +} diff --git a/lib/features/devices/view/widgets/garage_door/schedule_garage_screen.dart b/lib/features/devices/view/widgets/garage_door/schedule_garage_screen.dart new file mode 100644 index 0000000..ba56a98 --- /dev/null +++ b/lib/features/devices/view/widgets/garage_door/schedule_garage_screen.dart @@ -0,0 +1,163 @@ +import 'package:flutter/cupertino.dart'; +import 'package:flutter/material.dart'; +import 'package:flutter/services.dart'; +import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_event.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_state.dart'; +import 'package:syncrow_app/features/devices/model/device_model.dart'; +import 'package:syncrow_app/features/devices/view/widgets/garage_door/create_schedule_garage.dart'; +import 'package:syncrow_app/features/shared_widgets/default_scaffold.dart'; +import 'package:syncrow_app/features/shared_widgets/schedule_list.dart'; +import 'package:syncrow_app/features/shared_widgets/text_widgets/body_large.dart'; + +import 'package:syncrow_app/utils/resource_manager/color_manager.dart'; +import 'package:syncrow_app/utils/resource_manager/font_manager.dart'; + +class TimerScheduleScreen extends StatelessWidget { + final DeviceModel device; + final String deviceCode; + final String switchCode; + const TimerScheduleScreen( + {required this.device, + required this.deviceCode, + required this.switchCode, + super.key}); + + @override + Widget build(BuildContext context) { + return AnnotatedRegion( + value: SystemUiOverlayStyle( + statusBarColor: ColorsManager.primaryColor.withOpacity(0.5), + statusBarIconBrightness: Brightness.light, + ), + child: BlocProvider( + create: (context) => + GarageDoorBloc(GDId: device.uuid ?? '')..add(GetScheduleEvent()), + child: BlocBuilder( + builder: (context, state) { + final garageBloc = BlocProvider.of(context); + Duration duration = Duration.zero; + int countNum = 0; + if (state is UpdateTimerState) { + countNum = state.seconds; + } else if (state is TimerRunInProgress) { + countNum = state.remainingTime; + } else if (state is TimerRunComplete) { + countNum = 0; + } else if (state is LoadingNewSate) { + countNum = 0; + } + return PopScope( + canPop: false, + onPopInvoked: (didPop) { + if (!didPop) { + garageBloc.add(OnClose()); + Navigator.pop(context); + } + }, + child: DefaultTabController( + length: 2, + child: DefaultScaffold( + appBar: AppBar( + backgroundColor: Colors.transparent, + centerTitle: true, + title: const BodyLarge( + text: 'Schedule', + fontColor: ColorsManager.primaryColor, + fontWeight: FontsManager.bold, + ), + actions: [ + garageBloc.createSchedule == true + ? TextButton( + onPressed: () { + garageBloc.add(ScheduleSaveapp()); + }, + child: const Text('Save')) + : IconButton( + onPressed: () { + garageBloc.add( + const ToggleCreateScheduleEvent( + index: 1)); + }, + icon: const Icon(Icons.add), + ) + ], + ), + child: state is GarageDoorLoading + ? const Center(child: CircularProgressIndicator()) + : Column( + children: [ + Container( + width: MediaQuery.of(context).size.width, + decoration: const ShapeDecoration( + color: ColorsManager.onPrimaryColor, + shape: RoundedRectangleBorder( + borderRadius: + BorderRadius.all(Radius.circular(30)), + ), + ), + ), + Expanded( + child: SizedBox( + child: garageBloc.createSchedule == true + ? CreateGarageSchedule( + + onToggleChanged: (bool value) { + garageBloc.toggleSchedule = value; + }, + onDateTimeChanged: + (DateTime dateTime) { + garageBloc.selectedTime = + dateTime; + }, + days: garageBloc.days, + selectDays: + (List selectedDays) { + garageBloc.selectedDays = + selectedDays; + }, + ) + : Padding( + padding: + const EdgeInsets.only(top: 10), + child: ScheduleListView( + listSchedule: + garageBloc.listSchedule, + onDismissed: (scheduleId) { + garageBloc.listSchedule + .removeWhere((schedule) => + schedule.scheduleId == + scheduleId); + garageBloc.add( + DeleteScheduleEvent( + id: scheduleId)); + }, + onToggleSchedule: + (scheduleId, isEnabled) { + garageBloc + .add(ToggleScheduleEvent( + id: scheduleId, + toggle: isEnabled, + )); + }, + ), + ), + ), + ), + ], + ), + ))); + }, + ), + ), + ); + } + + String _formatDuration(int seconds) { + final hours = (seconds ~/ 3600).toString().padLeft(2, '0'); + final minutes = ((seconds % 3600) ~/ 60).toString().padLeft(2, '0'); + final secs = (seconds % 60).toString().padLeft(2, '0'); + return '$hours:$minutes:$secs'; + } +} diff --git a/lib/features/devices/view/widgets/garage_door/timer_page.dart b/lib/features/devices/view/widgets/garage_door/timer_page.dart new file mode 100644 index 0000000..47c1b37 --- /dev/null +++ b/lib/features/devices/view/widgets/garage_door/timer_page.dart @@ -0,0 +1,148 @@ +import 'package:flutter/cupertino.dart'; +import 'package:flutter/material.dart'; +import 'package:flutter/services.dart'; +import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:flutter_svg/svg.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_event.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_state.dart'; +import 'package:syncrow_app/features/devices/model/device_model.dart'; +import 'package:syncrow_app/features/shared_widgets/default_scaffold.dart'; +import 'package:syncrow_app/features/shared_widgets/text_widgets/body_large.dart'; +import 'package:syncrow_app/generated/assets.dart'; +import 'package:syncrow_app/utils/resource_manager/color_manager.dart'; +import 'package:syncrow_app/utils/resource_manager/font_manager.dart'; + +class TimerPage extends StatelessWidget { + final DeviceModel device; + final String deviceCode; + final String switchCode; + const TimerPage( + {required this.device, + required this.deviceCode, + required this.switchCode, + super.key}); + + @override + Widget build(BuildContext context) { + return AnnotatedRegion( + value: SystemUiOverlayStyle( + statusBarColor: ColorsManager.primaryColor.withOpacity(0.5), + statusBarIconBrightness: Brightness.light, + ), + child: BlocProvider( + create: (context) => GarageDoorBloc(GDId: device.uuid ?? '') + ..add(GetCounterEvent(deviceCode: deviceCode)), + child: BlocBuilder( + builder: (context, state) { + final oneGangBloc = BlocProvider.of(context); + Duration duration = Duration.zero; + int countNum = 0; + if (state is UpdateTimerState) { + countNum = state.seconds; + } else if (state is TimerRunInProgress) { + countNum = state.remainingTime; + } else if (state is TimerRunComplete) { + countNum = 0; + } else if (state is LoadingNewSate) { + countNum = 0; + } + return PopScope( + canPop: false, + onPopInvoked: (didPop) { + if (!didPop) { + oneGangBloc.add(OnClose()); + Navigator.pop(context); + } + }, + child: DefaultTabController( + length: 2, + child: DefaultScaffold( + appBar: AppBar( + backgroundColor: Colors.transparent, + centerTitle: true, + title: const BodyLarge( + text: 'Countdown', + fontColor: ColorsManager.primaryColor, + fontWeight: FontsManager.bold, + ), + ), + child: state is GarageDoorLoadingState + ? const Center(child: CircularProgressIndicator()) + : Column( + crossAxisAlignment: CrossAxisAlignment.center, + mainAxisAlignment: MainAxisAlignment.center, + children: [ + Container( + width: MediaQuery.of(context).size.width, + decoration: const ShapeDecoration( + color: ColorsManager.onPrimaryColor, + shape: RoundedRectangleBorder( + borderRadius: + BorderRadius.all(Radius.circular(30)), + ), + ), + ), + Center( + child: Container( + child: Column( + mainAxisAlignment: + MainAxisAlignment.center, + children: [ + countNum > 0 + ? BodyLarge( + text: _formatDuration(countNum), + fontColor: ColorsManager + .slidingBlueColor, + fontSize: 40, + ) + : CupertinoTimerPicker( + mode: + CupertinoTimerPickerMode.hm, + onTimerDurationChanged: + (Duration newDuration) { + duration = newDuration; + }, + ), + GestureDetector( + onTap: () { + if (state is LoadingNewSate) { + return; + } + if (countNum > 0) { + oneGangBloc.add( + const SetCounterValue( + deviceCode: + 'countdown_1', + duration: + Duration.zero)); + } else if (duration != + Duration.zero) { + oneGangBloc.add(SetCounterValue( + deviceCode: 'countdown_1', + duration: duration)); + } + }, + child: SvgPicture.asset(countNum > 0 + ? Assets.pauseIcon + : Assets.playIcon)), + ], + ), + ), + ), + ], + ), + ))); + }, + ), + ), + ); + } + + String _formatDuration(int seconds) { + final hours = (seconds ~/ 3600).toString().padLeft(2, '0'); + final minutes = ((seconds % 3600) ~/ 60).toString().padLeft(2, '0'); + final secs = (seconds % 60).toString().padLeft(2, '0'); + return '$hours:$minutes:$secs'; + } +} diff --git a/lib/features/devices/view/widgets/one_touch/one_touch_setting.dart b/lib/features/devices/view/widgets/one_touch/one_touch_setting.dart index 52be48f..38eda41 100644 --- a/lib/features/devices/view/widgets/one_touch/one_touch_setting.dart +++ b/lib/features/devices/view/widgets/one_touch/one_touch_setting.dart @@ -142,8 +142,7 @@ class OneTouchSetting extends StatelessWidget { bottom: 10, top: 10), child: InkWell( onTap: () async { - oneTouchBloc.optionSelected = - 'light_mode'; + oneTouchBloc.optionSelected = 'light_mode'; final result = await showDialog( context: context, builder: (context) { diff --git a/lib/features/devices/view/widgets/room_page_switch.dart b/lib/features/devices/view/widgets/room_page_switch.dart index 851aabf..3eb0d6c 100644 --- a/lib/features/devices/view/widgets/room_page_switch.dart +++ b/lib/features/devices/view/widgets/room_page_switch.dart @@ -10,6 +10,7 @@ import 'package:syncrow_app/features/devices/model/device_model.dart'; import 'package:syncrow_app/features/devices/view/widgets/ACs/acs_view.dart'; import 'package:syncrow_app/features/devices/view/widgets/curtains/curtain_view.dart'; import 'package:syncrow_app/features/devices/view/widgets/door_sensor/door_sensor_screen.dart'; +import 'package:syncrow_app/features/devices/view/widgets/garage_door/garage_door_screen.dart'; import 'package:syncrow_app/features/devices/view/widgets/gateway/gateway_view.dart'; import 'package:syncrow_app/features/devices/view/widgets/lights/light_interface.dart'; import 'package:syncrow_app/features/devices/view/widgets/one_gang/one_gang_Interface.dart'; @@ -187,6 +188,14 @@ void showDeviceInterface(DeviceModel device, BuildContext context) { PageRouteBuilder( pageBuilder: (context, animation1, animation2) => ThreeTouchInterface(touchSwitch: device))); + + case DeviceType.GarageDoor: + Navigator.push( + context, + PageRouteBuilder( + pageBuilder: (context, animation1, animation2) => + GarageDoorScreen(device: device))); + break; default: } diff --git a/lib/features/shared_widgets/create_schedule.dart b/lib/features/shared_widgets/create_schedule.dart index c8b298a..310b97d 100644 --- a/lib/features/shared_widgets/create_schedule.dart +++ b/lib/features/shared_widgets/create_schedule.dart @@ -137,3 +137,5 @@ class _CreateScheduleState extends State { ); } } + + diff --git a/lib/generated/assets.dart b/lib/generated/assets.dart index 2699f62..753e527 100644 --- a/lib/generated/assets.dart +++ b/lib/generated/assets.dart @@ -1059,4 +1059,10 @@ class Assets { "assets/icons/door_notification_setting_icon.svg"; static const String doorRecordsIcon = "assets/icons/door_records_icon.svg"; static const String doorSensorIcon = "assets/icons/door_sensor_icon.svg"; + static const String closedGarageIcon = "assets/icons/closed_garage_door.svg"; + static const String openGarageIcon = "assets/icons/open_garage_door.svg"; + static const String garageCountdown = "assets/icons/garage_countdown.svg"; + static const String garagePreferencesIcon = "assets/icons/garage_preferences_icon.svg"; + static const String garageSchedule = "assets/icons/garage_schedule.svg"; + //open_garage_door.svg } diff --git a/lib/utils/resource_manager/constants.dart b/lib/utils/resource_manager/constants.dart index 7b7114d..5bd1667 100644 --- a/lib/utils/resource_manager/constants.dart +++ b/lib/utils/resource_manager/constants.dart @@ -53,6 +53,7 @@ enum DeviceType { OneTouch, TowTouch, ThreeTouch, + GarageDoor, Other, } @@ -83,6 +84,7 @@ Map devicesTypesMap = { "1GT": DeviceType.OneTouch, "2GT": DeviceType.TowTouch, "3GT": DeviceType.ThreeTouch, + "GD": DeviceType.GarageDoor, }; Map> devicesFunctionsMap = { DeviceType.AC: [ @@ -370,7 +372,6 @@ Map> devicesFunctionsMap = { "range": ['power_off', 'power_on', 'last'] })), ], - DeviceType.ThreeTouch: [ FunctionModel( code: 'switch_1', @@ -430,6 +431,43 @@ Map> devicesFunctionsMap = { "range": ['power_off', 'power_on', 'last'] })), ], + DeviceType.GarageDoor: [ + FunctionModel( + code: 'switch_1', + type: functionTypesMap['Boolean'], + values: ValueModel.fromJson({})), + FunctionModel( + code: 'countdown_1', + type: functionTypesMap['Integer'], + values: ValueModel.fromJson( + {"unit": "s", "min": 0, "max": 86400, "scale": 0, "step": 1})), + FunctionModel( + code: 'tr_timecon', + type: functionTypesMap['Integer'], + values: ValueModel.fromJson( + {"unit": "s", "min": 0, "max": 120, "scale": 0, "step": 1})), + FunctionModel( + code: 'countdown_alarm', + type: functionTypesMap['Integer'], + values: ValueModel.fromJson( + {"unit": "s", "min": 0, "max": 86400, "scale": 0, "step": 1})), + FunctionModel( + code: 'door_control_1', + type: functionTypesMap['Enum'], + values: ValueModel.fromJson({ + "range": ['open', 'open'] + })), + FunctionModel( + code: 'voice_control_1', + type: functionTypesMap['Boolean'], + values: ValueModel.fromJson({})), + FunctionModel( + code: 'door_state_1', + type: functionTypesMap['Enum'], + values: ValueModel.fromJson({ + "range": ["unclosed_time", "close_time_alarm", "none"] + })), + ], }; enum TempModes { hot, cold, wind } diff --git a/pubspec.yaml b/pubspec.yaml index d2fab73..1a9b3e5 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -5,7 +5,7 @@ description: This is the mobile application project, developed with Flutter for # pub.dev using `flutter pub publish`. This is preferred for private packages. publish_to: "none" # Remove this line if you wish to publish to pub.dev -version: 1.0.3+22 +version: 1.0.3+25 environment: sdk: ">=3.0.6 <4.0.0" From 8476b51049d0bbca29ba9c580922889faedf7639 Mon Sep 17 00:00:00 2001 From: mohammad Date: Sun, 6 Oct 2024 16:49:36 +0300 Subject: [PATCH 2/8] garage door --- .../view/widgets/garage_door/garage_preferences_settings.dart | 1 - .../view/widgets/garage_door/schedule_garage_screen.dart | 2 -- 2 files changed, 3 deletions(-) diff --git a/lib/features/devices/view/widgets/garage_door/garage_preferences_settings.dart b/lib/features/devices/view/widgets/garage_door/garage_preferences_settings.dart index e591b33..b0bb6db 100644 --- a/lib/features/devices/view/widgets/garage_door/garage_preferences_settings.dart +++ b/lib/features/devices/view/widgets/garage_door/garage_preferences_settings.dart @@ -8,7 +8,6 @@ import 'package:syncrow_app/features/shared_widgets/default_container.dart'; import 'package:syncrow_app/features/shared_widgets/default_scaffold.dart'; import 'package:syncrow_app/features/shared_widgets/text_widgets/body_large.dart'; import 'package:syncrow_app/features/shared_widgets/text_widgets/body_medium.dart'; -import 'package:syncrow_app/features/shared_widgets/text_widgets/body_small.dart'; import 'package:syncrow_app/utils/resource_manager/color_manager.dart'; class PreferencesPage extends StatelessWidget { diff --git a/lib/features/devices/view/widgets/garage_door/schedule_garage_screen.dart b/lib/features/devices/view/widgets/garage_door/schedule_garage_screen.dart index ba56a98..19ce643 100644 --- a/lib/features/devices/view/widgets/garage_door/schedule_garage_screen.dart +++ b/lib/features/devices/view/widgets/garage_door/schedule_garage_screen.dart @@ -10,7 +10,6 @@ import 'package:syncrow_app/features/devices/view/widgets/garage_door/create_sch import 'package:syncrow_app/features/shared_widgets/default_scaffold.dart'; import 'package:syncrow_app/features/shared_widgets/schedule_list.dart'; import 'package:syncrow_app/features/shared_widgets/text_widgets/body_large.dart'; - import 'package:syncrow_app/utils/resource_manager/color_manager.dart'; import 'package:syncrow_app/utils/resource_manager/font_manager.dart'; @@ -102,7 +101,6 @@ class TimerScheduleScreen extends StatelessWidget { child: SizedBox( child: garageBloc.createSchedule == true ? CreateGarageSchedule( - onToggleChanged: (bool value) { garageBloc.toggleSchedule = value; }, From 4b45257aff84425dbe8032784db5133ac631e63d Mon Sep 17 00:00:00 2001 From: mohammad Date: Sun, 6 Oct 2024 16:59:28 +0300 Subject: [PATCH 3/8] garage door --- assets/icons/garageIcon.svg | 135 +++++++++++++++++++ lib/features/devices/model/device_model.dart | 5 +- lib/generated/assets.dart | 4 +- 3 files changed, 142 insertions(+), 2 deletions(-) create mode 100644 assets/icons/garageIcon.svg diff --git a/assets/icons/garageIcon.svg b/assets/icons/garageIcon.svg new file mode 100644 index 0000000..0b044eb --- /dev/null +++ b/assets/icons/garageIcon.svg @@ -0,0 +1,135 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/lib/features/devices/model/device_model.dart b/lib/features/devices/model/device_model.dart index 2374198..44899e6 100644 --- a/lib/features/devices/model/device_model.dart +++ b/lib/features/devices/model/device_model.dart @@ -70,9 +70,12 @@ class DeviceModel { tempIcon = Assets.oneGang; } else if (type == DeviceType.TowTouch) { tempIcon = Assets.twoGang; + } else if (type == DeviceType.GarageDoor) { + tempIcon = Assets.garageIcon; } else if (type == DeviceType.ThreeTouch) { tempIcon = Assets.assetsIcons3GangSwitch; - } else { + } + else { tempIcon = Assets.assetsIconsLogo; } diff --git a/lib/generated/assets.dart b/lib/generated/assets.dart index 753e527..c94ff82 100644 --- a/lib/generated/assets.dart +++ b/lib/generated/assets.dart @@ -1064,5 +1064,7 @@ class Assets { static const String garageCountdown = "assets/icons/garage_countdown.svg"; static const String garagePreferencesIcon = "assets/icons/garage_preferences_icon.svg"; static const String garageSchedule = "assets/icons/garage_schedule.svg"; - //open_garage_door.svg + + static const String garageIcon = "assets/icons/garageIcon.svg"; + } From 2d54d52061a72a0087e3784bd908b9347f071b25 Mon Sep 17 00:00:00 2001 From: Abdullah Alassaf Date: Sun, 6 Oct 2024 22:30:28 +0300 Subject: [PATCH 4/8] Updated the curtain desgin and removed unused code --- ...ticalBlade.svg => left_vertical_blade.svg} | 0 .../curtainsIcon/right_vertical_blade.svg | 32 +++ .../bloc/curtain_bloc/curtain_bloc.dart | 25 +- .../garage_door_bloc/garage_door_bloc.dart | 70 ++--- .../bloc/one_touch_bloc/one_touch_bloc.dart | 137 ++++------ .../three_touch_bloc/three_touch_bloc.dart | 156 ++++------- .../view/widgets/curtains/curtain_view.dart | 115 +++++--- .../garage_door/garage_door_screen.dart | 143 ++++------ .../garage_preferences_settings.dart | 34 +-- .../garage_door/schedule_garage_screen.dart | 71 ++--- .../widgets/one_touch/one_touch_screen.dart | 86 +++--- .../three_touch/three_touch_setting.dart | 250 ++++++------------ .../view/widgets/water_heater/wh_wizard.dart | 43 +-- lib/features/menu/view/menu_view.dart | 4 +- lib/generated/assets.dart | 232 ++++++---------- lib/main.dart | 2 +- lib/main_dev.dart | 2 +- lib/services/locator.dart | 3 +- 18 files changed, 556 insertions(+), 849 deletions(-) rename assets/icons/curtainsIcon/{verticalBlade.svg => left_vertical_blade.svg} (100%) create mode 100644 assets/icons/curtainsIcon/right_vertical_blade.svg diff --git a/assets/icons/curtainsIcon/verticalBlade.svg b/assets/icons/curtainsIcon/left_vertical_blade.svg similarity index 100% rename from assets/icons/curtainsIcon/verticalBlade.svg rename to assets/icons/curtainsIcon/left_vertical_blade.svg diff --git a/assets/icons/curtainsIcon/right_vertical_blade.svg b/assets/icons/curtainsIcon/right_vertical_blade.svg new file mode 100644 index 0000000..d7675aa --- /dev/null +++ b/assets/icons/curtainsIcon/right_vertical_blade.svg @@ -0,0 +1,32 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/lib/features/devices/bloc/curtain_bloc/curtain_bloc.dart b/lib/features/devices/bloc/curtain_bloc/curtain_bloc.dart index 1dea664..7e0ac56 100644 --- a/lib/features/devices/bloc/curtain_bloc/curtain_bloc.dart +++ b/lib/features/devices/bloc/curtain_bloc/curtain_bloc.dart @@ -24,9 +24,7 @@ class CurtainBloc extends Bloc { on(_onPauseCurtain); } - Future _onOpenCurtain( - OpenCurtain event, - Emitter emit) async { + Future _onOpenCurtain(OpenCurtain event, Emitter emit) async { isMoving = true; while (openPercentage < 100.0) { if (state is CurtainsClosing) { @@ -48,7 +46,7 @@ class CurtainBloc extends Bloc { _pauseCurtain(emit); } }); - if (openPercentage >=100.0) { + if (openPercentage >= 100.0) { await DevicesAPI.controlDevice( DeviceControlModel( deviceId: curtainId, @@ -73,8 +71,7 @@ class CurtainBloc extends Bloc { } } - Future _onCloseCurtain( - CloseCurtain event, Emitter emit) async { + Future _onCloseCurtain(CloseCurtain event, Emitter emit) async { isMoving = true; while (openPercentage > 0.0) { if (state is CurtainsOpening) { @@ -121,8 +118,7 @@ class CurtainBloc extends Bloc { } } - Future _onPauseCurtain( - PauseCurtain event, Emitter emit) async { + Future _onPauseCurtain(PauseCurtain event, Emitter emit) async { _pauseCurtain(emit); await DevicesAPI.controlDevice( DeviceControlModel( @@ -132,7 +128,7 @@ class CurtainBloc extends Bloc { ), curtainId, ); - await DevicesAPI.controlDevice( + await DevicesAPI.controlDevice( DeviceControlModel( deviceId: curtainId, code: 'percent_control', @@ -151,9 +147,6 @@ class CurtainBloc extends Bloc { )); } - - - void _fetchStatus(InitCurtain event, Emitter emit) async { try { emit(CurtainLoadingState()); @@ -166,10 +159,9 @@ class CurtainBloc extends Bloc { // Get the open percentage from the response openPercentage = double.tryParse(statusModelList[1].value.toString())!; // Calculate curtain width and blind height based on the open percentage - if (openPercentage != null) { - curtainWidth = 270 - (openPercentage / 100) * curtainOpeningSpace; - blindHeight = 310 - (openPercentage / 100) * blindOpeningSpace; - } + curtainWidth = 270 - (openPercentage / 100) * curtainOpeningSpace; + blindHeight = 310 - (openPercentage / 100) * blindOpeningSpace; + emit(CurtainsOpening( curtainWidth: curtainWidth, blindHeight: blindHeight, @@ -180,5 +172,4 @@ class CurtainBloc extends Bloc { return; } } - } diff --git a/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart b/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart index f6c3d4f..a8cb8a4 100644 --- a/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart +++ b/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart @@ -54,8 +54,7 @@ class GarageDoorBloc extends Bloc { batteryPercentage: 0, ); - void _fetchStatus( - GarageDoorInitial event, Emitter emit) async { + void _fetchStatus(GarageDoorInitial event, Emitter emit) async { emit(GarageDoorLoadingState()); try { var response = await DevicesAPI.getDeviceStatus(GDId); @@ -77,8 +76,8 @@ class GarageDoorBloc extends Bloc { } } - void _toggleClosingReminder(ToggleClosingReminderEvent event, - Emitter emit) async { + void _toggleClosingReminder( + ToggleClosingReminderEvent event, Emitter emit) async { emit(LoadingNewSate(doorSensor: deviceStatus)); try { closingReminder = event.isClosingReminderEnabled; @@ -96,8 +95,7 @@ class GarageDoorBloc extends Bloc { } } - void _toggleDoorAlarm( - ToggleDoorAlarmEvent event, Emitter emit) async { + void _toggleDoorAlarm(ToggleDoorAlarmEvent event, Emitter emit) async { emit(LoadingNewSate(doorSensor: deviceStatus)); try { doorAlarm = event.isDoorAlarmEnabled; @@ -115,8 +113,7 @@ class GarageDoorBloc extends Bloc { } } - DeviceReport recordGroups = - DeviceReport(startTime: '0', endTime: '0', data: []); + DeviceReport recordGroups = DeviceReport(startTime: '0', endTime: '0', data: []); Future fetchLogsForLastMonth( ReportLogsInitial event, Emitter emit) async { @@ -144,16 +141,14 @@ class GarageDoorBloc extends Bloc { _listenToChanges() { try { - DatabaseReference ref = - FirebaseDatabase.instance.ref('device-status/$GDId'); + DatabaseReference ref = FirebaseDatabase.instance.ref('device-status/$GDId'); Stream stream = ref.onValue; stream.listen((DatabaseEvent event) async { if (_timer != null) { await Future.delayed(const Duration(seconds: 2)); } - Map usersMap = - event.snapshot.value as Map; + Map usersMap = event.snapshot.value as Map; List statusList = []; usersMap['status'].forEach((element) { statusList.add(StatusModel(code: element['code'], value: true)); @@ -227,8 +222,7 @@ class GarageDoorBloc extends Bloc { deviceId: GDId, ); List jsonData = response; - listSchedule = - jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); + listSchedule = jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); } on DioException catch (e) { final errorData = e.response!.data; String errorMessage = errorData['message']; @@ -238,13 +232,12 @@ class GarageDoorBloc extends Bloc { int? getTimeStampWithoutSeconds(DateTime? dateTime) { if (dateTime == null) return null; - DateTime dateTimeWithoutSeconds = DateTime(dateTime.year, dateTime.month, - dateTime.day, dateTime.hour, dateTime.minute); + DateTime dateTimeWithoutSeconds = + DateTime(dateTime.year, dateTime.month, dateTime.day, dateTime.hour, dateTime.minute); return dateTimeWithoutSeconds.millisecondsSinceEpoch ~/ 1000; } - Future toggleChange( - ToggleScheduleEvent event, Emitter emit) async { + Future toggleChange(ToggleScheduleEvent event, Emitter emit) async { try { emit(GarageDoorLoadingState()); final response = await DevicesAPI.changeSchedule( @@ -262,8 +255,7 @@ class GarageDoorBloc extends Bloc { } } - Future deleteSchedule( - DeleteScheduleEvent event, Emitter emit) async { + Future deleteSchedule(DeleteScheduleEvent event, Emitter emit) async { try { emit(GarageDoorLoadingState()); final response = await DevicesAPI.deleteSchedule( @@ -282,15 +274,13 @@ class GarageDoorBloc extends Bloc { } } - void toggleSelectedIndex( - ToggleSelectedEvent event, Emitter emit) { + void toggleSelectedIndex(ToggleSelectedEvent event, Emitter emit) { emit(GarageDoorLoadingState()); selectedTabIndex = event.index; emit(ChangeSlidingSegmentState(value: selectedTabIndex)); } - void toggleCreateSchedule( - ToggleCreateScheduleEvent event, Emitter emit) { + void toggleCreateSchedule(ToggleCreateScheduleEvent event, Emitter emit) { emit(GarageDoorLoadingState()); createSchedule = !createSchedule; selectedDays.clear(); @@ -307,16 +297,13 @@ class GarageDoorBloc extends Bloc { int secondSelected = 0; bool toggleDoor = false; - Future selectSeconds( - SelectSecondsEvent event, Emitter emit) async { + Future selectSeconds(SelectSecondsEvent event, Emitter emit) async { try { emit(GarageDoorLoadingState()); secondSelected = event.seconds; - final response = await DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: GDId, code: 'tr_timecon', value: secondSelected), - GDId); + await DevicesAPI.controlDevice( + DeviceControlModel(deviceId: GDId, code: 'tr_timecon', value: secondSelected), GDId); emit(UpdateState(garageSensor: deviceStatus)); } on DioException catch (e) { final errorData = e.response!.data; @@ -325,16 +312,13 @@ class GarageDoorBloc extends Bloc { } } - openCloseGarageDoor( - ToggleDoorEvent event, Emitter emit) async { + openCloseGarageDoor(ToggleDoorEvent event, Emitter emit) async { emit(GarageDoorLoadingState()); try { toggleDoor = !event.toggle; - final response = await DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: GDId, code: 'switch_1', value: toggleDoor), - GDId); - add(GarageDoorInitial()); + await DevicesAPI.controlDevice( + DeviceControlModel(deviceId: GDId, code: 'switch_1', value: toggleDoor), GDId); + add(const GarageDoorInitial()); emit(UpdateState(garageSensor: deviceStatus)); } on DioException catch (e) { final errorData = e.response!.data; @@ -343,21 +327,18 @@ class GarageDoorBloc extends Bloc { } } - void _setCounterValue( - SetCounterValue event, Emitter emit) async { + void _setCounterValue(SetCounterValue event, Emitter emit) async { emit(LoadingNewSate(doorSensor: deviceStatus)); int seconds = 0; try { seconds = event.duration.inSeconds; final response = await DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: GDId, code: 'countdown_1', value: seconds), - GDId); + DeviceControlModel(deviceId: GDId, code: 'countdown_1', value: seconds), GDId); if (response['success'] ?? false) { deviceStatus.countdown1 = seconds; } else { - emit(GarageDoorFailedState(errorMessage: 'Something went wrong')); + emit(const GarageDoorFailedState(errorMessage: 'Something went wrong')); return; } } catch (e) { @@ -372,8 +353,7 @@ class GarageDoorBloc extends Bloc { } } - void _getCounterValue( - GetCounterEvent event, Emitter emit) async { + void _getCounterValue(GetCounterEvent event, Emitter emit) async { emit(LoadingInitialState()); try { var response = await DevicesAPI.getDeviceStatus(GDId); diff --git a/lib/features/devices/bloc/one_touch_bloc/one_touch_bloc.dart b/lib/features/devices/bloc/one_touch_bloc/one_touch_bloc.dart index 3d6512f..4b64206 100644 --- a/lib/features/devices/bloc/one_touch_bloc/one_touch_bloc.dart +++ b/lib/features/devices/bloc/one_touch_bloc/one_touch_bloc.dart @@ -29,8 +29,7 @@ class OneTouchBloc extends Bloc { bool oneTouchGroup = false; List devicesList = []; - OneTouchBloc({required this.oneTouchId, required this.switchCode}) - : super(InitialState()) { + OneTouchBloc({required this.oneTouchId, required this.switchCode}) : super(InitialState()) { on(_fetchOneTouchStatus); on(_oneTouchUpdated); on(_changeFirstSwitch); @@ -53,8 +52,7 @@ class OneTouchBloc extends Bloc { on(_changeStatus); } - void _fetchOneTouchStatus( - InitialEvent event, Emitter emit) async { + void _fetchOneTouchStatus(InitialEvent event, Emitter emit) async { emit(LoadingInitialState()); try { var response = await DevicesAPI.getDeviceStatus(oneTouchId); @@ -73,21 +71,18 @@ class OneTouchBloc extends Bloc { _listenToChanges() { try { - DatabaseReference ref = - FirebaseDatabase.instance.ref('device-status/$oneTouchId'); + DatabaseReference ref = FirebaseDatabase.instance.ref('device-status/$oneTouchId'); Stream stream = ref.onValue; stream.listen((DatabaseEvent event) async { if (_timer != null) { await Future.delayed(const Duration(seconds: 2)); } - Map usersMap = - event.snapshot.value as Map; + Map usersMap = event.snapshot.value as Map; List statusList = []; usersMap['status'].forEach((element) { - statusList - .add(StatusModel(code: element['code'], value: element['value'])); + statusList.add(StatusModel(code: element['code'], value: element['value'])); }); deviceStatus = OneTouchModel.fromJson(statusList); @@ -102,8 +97,7 @@ class OneTouchBloc extends Bloc { emit(UpdateState(oneTouchModel: deviceStatus)); } - void _changeFirstSwitch( - ChangeFirstSwitchStatusEvent event, Emitter emit) async { + void _changeFirstSwitch(ChangeFirstSwitchStatusEvent event, Emitter emit) async { emit(LoadingNewSate(oneTouchModel: deviceStatus)); try { deviceStatus.firstSwitch = !event.value; @@ -128,20 +122,17 @@ class OneTouchBloc extends Bloc { } } - void _changeSliding( - ChangeSlidingSegment event, Emitter emit) async { + void _changeSliding(ChangeSlidingSegment event, Emitter emit) async { emit(ChangeSlidingSegmentState(value: event.value)); } - void _setCounterValue( - SetCounterValue event, Emitter emit) async { + void _setCounterValue(SetCounterValue event, Emitter emit) async { emit(LoadingNewSate(oneTouchModel: deviceStatus)); int seconds = 0; try { seconds = event.duration.inSeconds; final response = await DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: oneTouchId, code: event.deviceCode, value: seconds), + DeviceControlModel(deviceId: oneTouchId, code: event.deviceCode, value: seconds), oneTouchId); if (response['success'] ?? false) { @@ -164,8 +155,7 @@ class OneTouchBloc extends Bloc { } } - void _getCounterValue( - GetCounterEvent event, Emitter emit) async { + void _getCounterValue(GetCounterEvent event, Emitter emit) async { emit(LoadingInitialState()); try { var response = await DevicesAPI.getDeviceStatus(oneTouchId); @@ -254,8 +244,7 @@ class OneTouchBloc extends Bloc { deviceId: oneTouchId, ); List jsonData = response; - listSchedule = - jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); + listSchedule = jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); emit(InitialState()); } on DioException catch (e) { final errorData = e.response!.data; @@ -266,13 +255,12 @@ class OneTouchBloc extends Bloc { int? getTimeStampWithoutSeconds(DateTime? dateTime) { if (dateTime == null) return null; - DateTime dateTimeWithoutSeconds = DateTime(dateTime.year, dateTime.month, - dateTime.day, dateTime.hour, dateTime.minute); + DateTime dateTimeWithoutSeconds = + DateTime(dateTime.year, dateTime.month, dateTime.day, dateTime.hour, dateTime.minute); return dateTimeWithoutSeconds.millisecondsSinceEpoch ~/ 1000; } - Future toggleChange( - ToggleScheduleEvent event, Emitter emit) async { + Future toggleChange(ToggleScheduleEvent event, Emitter emit) async { try { emit(LoadingInitialState()); final response = await DevicesAPI.changeSchedule( @@ -291,8 +279,7 @@ class OneTouchBloc extends Bloc { } } - Future deleteSchedule( - DeleteScheduleEvent event, Emitter emit) async { + Future deleteSchedule(DeleteScheduleEvent event, Emitter emit) async { try { emit(LoadingInitialState()); final response = await DevicesAPI.deleteSchedule( @@ -312,8 +299,7 @@ class OneTouchBloc extends Bloc { } } - void toggleCreateSchedule( - ToggleCreateScheduleEvent event, Emitter emit) { + void toggleCreateSchedule(ToggleCreateScheduleEvent event, Emitter emit) { emit(LoadingInitialState()); createSchedule = !createSchedule; selectedDays.clear(); @@ -342,8 +328,7 @@ class OneTouchBloc extends Bloc { int selectedTabIndex = 0; - void toggleSelectedIndex( - ToggleSelectedEvent event, Emitter emit) { + void toggleSelectedIndex(ToggleSelectedEvent event, Emitter emit) { emit(LoadingInitialState()); selectedTabIndex = event.index; emit(ChangeSlidingSegmentState(value: selectedTabIndex)); @@ -352,8 +337,7 @@ class OneTouchBloc extends Bloc { List groupOneTouchList = []; bool allSwitchesOn = true; - void _fetchOneTouchWizardStatus( - InitialWizardEvent event, Emitter emit) async { + void _fetchOneTouchWizardStatus(InitialWizardEvent event, Emitter emit) async { emit(LoadingInitialState()); try { devicesList = []; @@ -363,8 +347,7 @@ class OneTouchBloc extends Bloc { HomeCubit.getInstance().selectedSpace?.id ?? '', '1GT'); for (int i = 0; i < devicesList.length; i++) { - var response = - await DevicesAPI.getDeviceStatus(devicesList[i].uuid ?? ''); + var response = await DevicesAPI.getDeviceStatus(devicesList[i].uuid ?? ''); List statusModelList = []; for (var status in response['status']) { statusModelList.add(StatusModel.fromJson(status)); @@ -385,16 +368,15 @@ class OneTouchBloc extends Bloc { return true; }); } - emit(UpdateGroupState( - oneTouchList: groupOneTouchList, allSwitches: allSwitchesOn)); + emit(UpdateGroupState(oneTouchList: groupOneTouchList, allSwitches: allSwitchesOn)); } catch (e) { emit(FailedState(error: e.toString())); return; } } - void _changeFirstWizardSwitch(ChangeFirstWizardSwitchStatusEvent event, - Emitter emit) async { + void _changeFirstWizardSwitch( + ChangeFirstWizardSwitchStatusEvent event, Emitter emit) async { emit(LoadingNewSate(oneTouchModel: deviceStatus)); try { bool allSwitchesValue = true; @@ -412,8 +394,7 @@ class OneTouchBloc extends Bloc { value: !event.value, ); - emit(UpdateGroupState( - oneTouchList: groupOneTouchList, allSwitches: allSwitchesValue)); + emit(UpdateGroupState(oneTouchList: groupOneTouchList, allSwitches: allSwitchesValue)); if (!response['success']) { add(InitialEvent(groupScreen: oneTouchGroup)); } @@ -431,12 +412,10 @@ class OneTouchBloc extends Bloc { } // Emit the state with updated values - emit( - UpdateGroupState(oneTouchList: groupOneTouchList, allSwitches: true)); + emit(UpdateGroupState(oneTouchList: groupOneTouchList, allSwitches: true)); // Get a list of all device IDs - List allDeviceIds = - groupOneTouchList.map((device) => device.deviceId).toList(); + List allDeviceIds = groupOneTouchList.map((device) => device.deviceId).toList(); // First call for switch_1 final response1 = await DevicesAPI.deviceBatchController( @@ -473,12 +452,10 @@ class OneTouchBloc extends Bloc { } // Emit the state with updated values - emit(UpdateGroupState( - oneTouchList: groupOneTouchList, allSwitches: false)); + emit(UpdateGroupState(oneTouchList: groupOneTouchList, allSwitches: false)); // Get a list of all device IDs - List allDeviceIds = - groupOneTouchList.map((device) => device.deviceId).toList(); + List allDeviceIds = groupOneTouchList.map((device) => device.deviceId).toList(); // First call for switch_1 final response1 = await DevicesAPI.deviceBatchController( @@ -508,40 +485,38 @@ class OneTouchBloc extends Bloc { String statusSelected = ''; String optionSelected = ''; - Future _changeStatus( - ChangeStatusEvent event, Emitter emit) async { - try { + Future _changeStatus(ChangeStatusEvent event, Emitter emit) async { + try { emit(LoadingInitialState()); - final Map> controlMap = { - "relay_status": { - 'Power On': 'power_on', - 'Power Off': 'power_off', - 'Restart Memory': 'last', - }, - "light_mode": { - 'Off': 'none', - 'On/Off Status': 'relay', - 'Switch Position': 'pos', - }, - "relay_status_1": { - 'Power On': 'power_on', - 'Power Off': 'power_off', - 'Restart Memory': 'last', - }, - }; + final Map> controlMap = { + "relay_status": { + 'Power On': 'power_on', + 'Power Off': 'power_off', + 'Restart Memory': 'last', + }, + "light_mode": { + 'Off': 'none', + 'On/Off Status': 'relay', + 'Switch Position': 'pos', + }, + "relay_status_1": { + 'Power On': 'power_on', + 'Power Off': 'power_off', + 'Restart Memory': 'last', + }, + }; - final selectedControl = controlMap[optionSelected]?[statusSelected]; - if (selectedControl != null) { - await DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: oneTouchId, code: optionSelected, value: selectedControl), - oneTouchId, - ); - } else { - print('Invalid statusSelected or optionSelected'); - } - } on DioException catch (e) { + final selectedControl = controlMap[optionSelected]?[statusSelected]; + if (selectedControl != null) { + await DevicesAPI.controlDevice( + DeviceControlModel(deviceId: oneTouchId, code: optionSelected, value: selectedControl), + oneTouchId, + ); + } else { + print('Invalid statusSelected or optionSelected'); + } + } on DioException catch (e) { final errorData = e.response!.data; String errorMessage = errorData['message']; emit(FailedState(error: errorMessage.toString())); diff --git a/lib/features/devices/bloc/three_touch_bloc/three_touch_bloc.dart b/lib/features/devices/bloc/three_touch_bloc/three_touch_bloc.dart index da8a97e..d4a59ea 100644 --- a/lib/features/devices/bloc/three_touch_bloc/three_touch_bloc.dart +++ b/lib/features/devices/bloc/three_touch_bloc/three_touch_bloc.dart @@ -1,7 +1,6 @@ import 'dart:async'; import 'package:dio/dio.dart'; import 'package:firebase_database/firebase_database.dart'; -import 'package:flutter/material.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; import 'package:syncrow_app/features/app_layout/bloc/home_cubit.dart'; import 'package:syncrow_app/features/devices/bloc/three_touch_bloc/three_touch_event.dart'; @@ -39,8 +38,7 @@ class ThreeTouchBloc extends Bloc { List groupThreeTouchList = []; bool allSwitchesOn = true; - ThreeTouchBloc({required this.threeTouchId, required this.switchCode}) - : super(InitialState()) { + ThreeTouchBloc({required this.threeTouchId, required this.switchCode}) : super(InitialState()) { on(_fetchThreeTouchStatus); on(_threeTouchUpdated); on(_changeFirstSwitch); @@ -67,8 +65,7 @@ class ThreeTouchBloc extends Bloc { on(_changeStatus); } - void _fetchThreeTouchStatus( - InitialEvent event, Emitter emit) async { + void _fetchThreeTouchStatus(InitialEvent event, Emitter emit) async { emit(LoadingInitialState()); try { threeTouchGroup = event.groupScreen; @@ -80,8 +77,7 @@ class ThreeTouchBloc extends Bloc { HomeCubit.getInstance().selectedSpace?.id ?? '', '3GT'); for (int i = 0; i < devicesList.length; i++) { - var response = - await DevicesAPI.getDeviceStatus(devicesList[i].uuid ?? ''); + var response = await DevicesAPI.getDeviceStatus(devicesList[i].uuid ?? ''); List statusModelList = []; for (var status in response['status']) { statusModelList.add(StatusModel.fromJson(status)); @@ -98,16 +94,13 @@ class ThreeTouchBloc extends Bloc { if (groupThreeTouchList.isNotEmpty) { groupThreeTouchList.firstWhere((element) { - if (!element.firstSwitch || - !element.secondSwitch || - !element.thirdSwitch) { + if (!element.firstSwitch || !element.secondSwitch || !element.thirdSwitch) { allSwitchesOn = false; } return true; }); } - emit(UpdateGroupState( - threeTouchList: groupThreeTouchList, allSwitches: allSwitchesOn)); + emit(UpdateGroupState(threeTouchList: groupThreeTouchList, allSwitches: allSwitchesOn)); } else { var response = await DevicesAPI.getDeviceStatus(threeTouchId); List statusModelList = []; @@ -126,21 +119,18 @@ class ThreeTouchBloc extends Bloc { _listenToChanges() { try { - DatabaseReference ref = - FirebaseDatabase.instance.ref('device-status/$threeTouchId'); + DatabaseReference ref = FirebaseDatabase.instance.ref('device-status/$threeTouchId'); Stream stream = ref.onValue; stream.listen((DatabaseEvent event) async { if (_timer != null) { await Future.delayed(const Duration(seconds: 2)); } - Map usersMap = - event.snapshot.value as Map; + Map usersMap = event.snapshot.value as Map; List statusList = []; usersMap['status'].forEach((element) { - statusList - .add(StatusModel(code: element['code'], value: element['value'])); + statusList.add(StatusModel(code: element['code'], value: element['value'])); }); deviceStatus = ThreeTouchModel.fromJson(statusList); @@ -155,8 +145,7 @@ class ThreeTouchBloc extends Bloc { emit(UpdateState(threeTouchModel: deviceStatus)); } - void _changeFirstSwitch( - ChangeFirstSwitchStatusEvent event, Emitter emit) async { + void _changeFirstSwitch(ChangeFirstSwitchStatusEvent event, Emitter emit) async { emit(LoadingNewSate(threeTouchModel: deviceStatus)); try { if (threeTouchGroup) { @@ -165,15 +154,11 @@ class ThreeTouchBloc extends Bloc { if (element.deviceId == event.deviceId) { element.firstSwitch = !event.value; } - if (!element.firstSwitch || - !element.secondSwitch || - !element.thirdSwitch) { + if (!element.firstSwitch || !element.secondSwitch || !element.thirdSwitch) { allSwitchesValue = false; } }); - emit(UpdateGroupState( - threeTouchList: groupThreeTouchList, - allSwitches: allSwitchesValue)); + emit(UpdateGroupState(threeTouchList: groupThreeTouchList, allSwitches: allSwitchesValue)); } else { deviceStatus.firstSwitch = !event.value; emit(UpdateState(threeTouchModel: deviceStatus)); @@ -200,8 +185,8 @@ class ThreeTouchBloc extends Bloc { } } - void _changeSecondSwitch(ChangeSecondSwitchStatusEvent event, - Emitter emit) async { + void _changeSecondSwitch( + ChangeSecondSwitchStatusEvent event, Emitter emit) async { emit(LoadingNewSate(threeTouchModel: deviceStatus)); try { if (threeTouchGroup) { @@ -210,15 +195,11 @@ class ThreeTouchBloc extends Bloc { if (element.deviceId == event.deviceId) { element.secondSwitch = !event.value; } - if (!element.firstSwitch || - !element.secondSwitch || - !element.thirdSwitch) { + if (!element.firstSwitch || !element.secondSwitch || !element.thirdSwitch) { allSwitchesValue = false; } }); - emit(UpdateGroupState( - threeTouchList: groupThreeTouchList, - allSwitches: allSwitchesValue)); + emit(UpdateGroupState(threeTouchList: groupThreeTouchList, allSwitches: allSwitchesValue)); } else { deviceStatus.secondSwitch = !event.value; emit(UpdateState(threeTouchModel: deviceStatus)); @@ -244,8 +225,7 @@ class ThreeTouchBloc extends Bloc { } } - void _changeThirdSwitch( - ChangeThirdSwitchStatusEvent event, Emitter emit) async { + void _changeThirdSwitch(ChangeThirdSwitchStatusEvent event, Emitter emit) async { emit(LoadingNewSate(threeTouchModel: deviceStatus)); try { if (threeTouchGroup) { @@ -254,15 +234,11 @@ class ThreeTouchBloc extends Bloc { if (element.deviceId == event.deviceId) { element.thirdSwitch = !event.value; } - if (!element.firstSwitch || - !element.secondSwitch || - !element.thirdSwitch) { + if (!element.firstSwitch || !element.secondSwitch || !element.thirdSwitch) { allSwitchesValue = false; } }); - emit(UpdateGroupState( - threeTouchList: groupThreeTouchList, - allSwitches: allSwitchesValue)); + emit(UpdateGroupState(threeTouchList: groupThreeTouchList, allSwitches: allSwitchesValue)); } else { deviceStatus.thirdSwitch = !event.value; emit(UpdateState(threeTouchModel: deviceStatus)); @@ -301,21 +277,15 @@ class ThreeTouchBloc extends Bloc { final response = await Future.wait([ DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeTouchId, - code: 'switch_1', - value: deviceStatus.firstSwitch), + deviceId: threeTouchId, code: 'switch_1', value: deviceStatus.firstSwitch), threeTouchId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeTouchId, - code: 'switch_2', - value: deviceStatus.secondSwitch), + deviceId: threeTouchId, code: 'switch_2', value: deviceStatus.secondSwitch), threeTouchId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeTouchId, - code: 'switch_3', - value: deviceStatus.thirdSwitch), + deviceId: threeTouchId, code: 'switch_3', value: deviceStatus.thirdSwitch), threeTouchId), ]); @@ -341,21 +311,15 @@ class ThreeTouchBloc extends Bloc { final response = await Future.wait([ DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeTouchId, - code: 'switch_1', - value: deviceStatus.firstSwitch), + deviceId: threeTouchId, code: 'switch_1', value: deviceStatus.firstSwitch), threeTouchId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeTouchId, - code: 'switch_2', - value: deviceStatus.secondSwitch), + deviceId: threeTouchId, code: 'switch_2', value: deviceStatus.secondSwitch), threeTouchId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeTouchId, - code: 'switch_3', - value: deviceStatus.thirdSwitch), + deviceId: threeTouchId, code: 'switch_3', value: deviceStatus.thirdSwitch), threeTouchId), ]); @@ -377,28 +341,21 @@ class ThreeTouchBloc extends Bloc { groupThreeTouchList[i].secondSwitch = true; groupThreeTouchList[i].thirdSwitch = true; } - emit(UpdateGroupState( - threeTouchList: groupThreeTouchList, allSwitches: true)); + emit(UpdateGroupState(threeTouchList: groupThreeTouchList, allSwitches: true)); for (int i = 0; i < groupThreeTouchList.length; i++) { final response = await Future.wait([ DevicesAPI.controlDevice( DeviceControlModel( - deviceId: groupThreeTouchList[i].deviceId, - code: 'switch_1', - value: true), + deviceId: groupThreeTouchList[i].deviceId, code: 'switch_1', value: true), groupThreeTouchList[i].deviceId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: groupThreeTouchList[i].deviceId, - code: 'switch_2', - value: true), + deviceId: groupThreeTouchList[i].deviceId, code: 'switch_2', value: true), groupThreeTouchList[i].deviceId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: groupThreeTouchList[i].deviceId, - code: 'switch_3', - value: true), + deviceId: groupThreeTouchList[i].deviceId, code: 'switch_3', value: true), groupThreeTouchList[i].deviceId), ]); @@ -414,8 +371,7 @@ class ThreeTouchBloc extends Bloc { } } - void _groupAllOff( - GroupAllOffEvent event, Emitter emit) async { + void _groupAllOff(GroupAllOffEvent event, Emitter emit) async { emit(LoadingNewSate(threeTouchModel: deviceStatus)); try { for (int i = 0; i < groupThreeTouchList.length; i++) { @@ -423,28 +379,21 @@ class ThreeTouchBloc extends Bloc { groupThreeTouchList[i].secondSwitch = false; groupThreeTouchList[i].thirdSwitch = false; } - emit(UpdateGroupState( - threeTouchList: groupThreeTouchList, allSwitches: false)); + emit(UpdateGroupState(threeTouchList: groupThreeTouchList, allSwitches: false)); for (int i = 0; i < groupThreeTouchList.length; i++) { final response = await Future.wait([ DevicesAPI.controlDevice( DeviceControlModel( - deviceId: groupThreeTouchList[i].deviceId, - code: 'switch_1', - value: false), + deviceId: groupThreeTouchList[i].deviceId, code: 'switch_1', value: false), groupThreeTouchList[i].deviceId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: groupThreeTouchList[i].deviceId, - code: 'switch_2', - value: false), + deviceId: groupThreeTouchList[i].deviceId, code: 'switch_2', value: false), groupThreeTouchList[i].deviceId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: groupThreeTouchList[i].deviceId, - code: 'switch_3', - value: false), + deviceId: groupThreeTouchList[i].deviceId, code: 'switch_3', value: false), groupThreeTouchList[i].deviceId), ]); @@ -460,20 +409,17 @@ class ThreeTouchBloc extends Bloc { } } - void _changeSliding( - ChangeSlidingSegment event, Emitter emit) async { + void _changeSliding(ChangeSlidingSegment event, Emitter emit) async { emit(ChangeSlidingSegmentState(value: event.value)); } - void _setCounterValue( - SetCounterValue event, Emitter emit) async { + void _setCounterValue(SetCounterValue event, Emitter emit) async { emit(LoadingNewSate(threeTouchModel: deviceStatus)); int seconds = 0; try { seconds = event.duration.inSeconds; final response = await DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: threeTouchId, code: event.deviceCode, value: seconds), + DeviceControlModel(deviceId: threeTouchId, code: event.deviceCode, value: seconds), threeTouchId); if (response['success'] ?? false) { @@ -500,8 +446,7 @@ class ThreeTouchBloc extends Bloc { } } - void _getCounterValue( - GetCounterEvent event, Emitter emit) async { + void _getCounterValue(GetCounterEvent event, Emitter emit) async { emit(LoadingInitialState()); try { var response = await DevicesAPI.getDeviceStatus(threeTouchId); @@ -611,8 +556,7 @@ class ThreeTouchBloc extends Bloc { deviceId: threeTouchId, ); List jsonData = response; - listSchedule = - jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); + listSchedule = jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); emit(InitialState()); } on DioException catch (e) { final errorData = e.response!.data; @@ -623,13 +567,12 @@ class ThreeTouchBloc extends Bloc { int? getTimeStampWithoutSeconds(DateTime? dateTime) { if (dateTime == null) return null; - DateTime dateTimeWithoutSeconds = DateTime(dateTime.year, dateTime.month, - dateTime.day, dateTime.hour, dateTime.minute); + DateTime dateTimeWithoutSeconds = + DateTime(dateTime.year, dateTime.month, dateTime.day, dateTime.hour, dateTime.minute); return dateTimeWithoutSeconds.millisecondsSinceEpoch ~/ 1000; } - Future toggleChange( - ToggleScheduleEvent event, Emitter emit) async { + Future toggleChange(ToggleScheduleEvent event, Emitter emit) async { try { emit(LoadingInitialState()); final response = await DevicesAPI.changeSchedule( @@ -648,8 +591,7 @@ class ThreeTouchBloc extends Bloc { } } - Future deleteSchedule( - DeleteScheduleEvent event, Emitter emit) async { + Future deleteSchedule(DeleteScheduleEvent event, Emitter emit) async { try { emit(LoadingInitialState()); final response = await DevicesAPI.deleteSchedule( @@ -669,15 +611,13 @@ class ThreeTouchBloc extends Bloc { } } - void toggleSelectedIndex( - ToggleSelectedEvent event, Emitter emit) { + void toggleSelectedIndex(ToggleSelectedEvent event, Emitter emit) { emit(LoadingInitialState()); selectedTabIndex = event.index; emit(ChangeSlidingSegmentState(value: selectedTabIndex)); } - void toggleCreateSchedule( - ToggleCreateScheduleEvent event, Emitter emit) { + void toggleCreateSchedule(ToggleCreateScheduleEvent event, Emitter emit) { emit(LoadingInitialState()); createSchedule = !createSchedule; selectedDays.clear(); @@ -695,8 +635,7 @@ class ThreeTouchBloc extends Bloc { String statusSelected = ''; String optionSelected = ''; - Future _changeStatus( - ChangeStatusEvent event, Emitter emit) async { + Future _changeStatus(ChangeStatusEvent event, Emitter emit) async { try { emit(LoadingInitialState()); final Map> controlMap = { @@ -730,10 +669,7 @@ class ThreeTouchBloc extends Bloc { final selectedControl = controlMap[optionSelected]?[statusSelected]; if (selectedControl != null) { await DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: threeTouchId, - code: optionSelected, - value: selectedControl), + DeviceControlModel(deviceId: threeTouchId, code: optionSelected, value: selectedControl), threeTouchId, ); } else { diff --git a/lib/features/devices/view/widgets/curtains/curtain_view.dart b/lib/features/devices/view/widgets/curtains/curtain_view.dart index 9f89aa2..acfb141 100644 --- a/lib/features/devices/view/widgets/curtains/curtain_view.dart +++ b/lib/features/devices/view/widgets/curtains/curtain_view.dart @@ -36,11 +36,11 @@ class CurtainView extends StatelessWidget { child: Column( children: [ Stack( - alignment: Alignment.centerLeft, + alignment: Alignment.center, children: [ Container( - height: 340, - width: 365, + height: MediaQuery.sizeOf(context).height * 0.5, + width: MediaQuery.sizeOf(context).width, decoration: const BoxDecoration( image: DecorationImage( image: AssetImage( @@ -49,42 +49,85 @@ class CurtainView extends StatelessWidget { ), ), ), - Padding( - padding: const EdgeInsets.all(40), - child: AnimatedContainer( - duration: const Duration(milliseconds: 200), - curve: Curves.linear, - height: 310, - width: curtainWidth, - child: Stack( - children: List.generate( - 10, - (index) { - double spacing = curtainWidth / 9; - double leftMostPosition = index * spacing; - return AnimatedPositioned( - duration: const Duration(milliseconds: 200), - curve: Curves.linear, - left: leftMostPosition, - child: SizedBox( - height: 320, - width: 32, - child: SvgPicture.asset( - Assets.assetsIconsCurtainsIconVerticalBlade, - fit: BoxFit.fill, + Container( + padding: const EdgeInsets.only(top: 40), + child: Column( + children: [ + SvgPicture.asset( + Assets.assetsIconsCurtainsIconCurtainHolder, + width: MediaQuery.sizeOf(context).width * 0.8, + ), + SizedBox( + width: MediaQuery.sizeOf(context).width * 0.8, + child: Row( + mainAxisAlignment: MainAxisAlignment.spaceBetween, + children: [ + Container( + padding: const EdgeInsets.only(bottom: 40, left: 8), + child: AnimatedContainer( + duration: const Duration(milliseconds: 200), + curve: Curves.linear, + height: MediaQuery.sizeOf(context).height * 0.4, + width: curtainWidth / 2, + child: Stack( + children: List.generate( + 4, + (index) { + double spacing = curtainWidth / 8; + double leftMostPosition = index * spacing; + return AnimatedPositioned( + duration: const Duration(milliseconds: 200), + curve: Curves.linear, + left: leftMostPosition, + child: SizedBox( + height: MediaQuery.sizeOf(context).height * 0.37, + width: 32, + child: SvgPicture.asset( + Assets.assetsIconsCurtainsIconVerticalBlade, + fit: BoxFit.fill, + ), + ), + ); + }, + ), + ), ), ), - ); - }, + Container( + padding: const EdgeInsets.only(bottom: 40, right: 8), + child: AnimatedContainer( + duration: const Duration(milliseconds: 200), + curve: Curves.linear, + height: MediaQuery.sizeOf(context).height * 0.4, + width: curtainWidth / 2, + child: Stack( + children: List.generate( + 4, + (index) { + double spacing = curtainWidth / 8; + double rightMostPosition = index * spacing; + return AnimatedPositioned( + duration: const Duration(milliseconds: 200), + curve: Curves.linear, + right: rightMostPosition, + child: SizedBox( + height: MediaQuery.sizeOf(context).height * 0.37, + width: 32, + child: SvgPicture.asset( + Assets.rightVerticalBlade, + fit: BoxFit.fill, + ), + ), + ); + }, + ), + ), + ), + ), + ], + ), ), - ), - ), - ), - Positioned( - top: 27, - left: 43, - child: SvgPicture.asset( - Assets.assetsIconsCurtainsIconCurtainHolder, + ], ), ), ], diff --git a/lib/features/devices/view/widgets/garage_door/garage_door_screen.dart b/lib/features/devices/view/widgets/garage_door/garage_door_screen.dart index 8fb6a9f..ae1fe0d 100644 --- a/lib/features/devices/view/widgets/garage_door/garage_door_screen.dart +++ b/lib/features/devices/view/widgets/garage_door/garage_door_screen.dart @@ -1,12 +1,10 @@ import 'package:flutter/material.dart'; -import 'package:flutter/widgets.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; import 'package:flutter_svg/flutter_svg.dart'; import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart'; import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_event.dart'; import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_state.dart'; import 'package:syncrow_app/features/devices/model/device_model.dart'; -import 'package:syncrow_app/features/devices/model/garage_door_model.dart'; import 'package:syncrow_app/features/devices/view/widgets/garage_door/garage_preferences_settings.dart'; import 'package:syncrow_app/features/devices/view/widgets/garage_door/garage_records_screen.dart'; import 'package:syncrow_app/features/devices/view/widgets/garage_door/schedule_garage_screen.dart'; @@ -26,34 +24,32 @@ class GarageDoorScreen extends StatelessWidget { return DefaultScaffold( title: 'Garage Door Opener', child: BlocProvider( - create: (context) => GarageDoorBloc(GDId: device?.uuid ?? '') - ..add(const GarageDoorInitial()), + create: (context) => + GarageDoorBloc(GDId: device?.uuid ?? '')..add(const GarageDoorInitial()), child: BlocBuilder( builder: (context, state) { final garageBloc = BlocProvider.of(context); - GarageDoorModel model = GarageDoorModel( - tr_timecon: 0, - countdown1: 0, - countdownAlarm: 0, - doorContactState: false, - doorControl1: '', - doorState1: '', - switch1: false, - voiceControl1: false, - batteryPercentage: 0, - ); + // GarageDoorModel model = GarageDoorModel( + // tr_timecon: 0, + // countdown1: 0, + // countdownAlarm: 0, + // doorContactState: false, + // doorControl1: '', + // doorState1: '', + // switch1: false, + // voiceControl1: false, + // batteryPercentage: 0, + // ); - if (state is LoadingNewSate) { - model = state.doorSensor; - } else if (state is UpdateState) { - model = state.garageSensor; - } + // if (state is LoadingNewSate) { + // model = state.doorSensor; + // } else if (state is UpdateState) { + // model = state.garageSensor; + // } return state is GarageDoorLoadingState ? const Center( - child: DefaultContainer( - width: 50, - height: 50, - child: CircularProgressIndicator()), + child: + DefaultContainer(width: 50, height: 50, child: CircularProgressIndicator()), ) : RefreshIndicator( onRefresh: () async { @@ -68,36 +64,30 @@ class GarageDoorScreen extends StatelessWidget { Expanded( flex: 4, child: InkWell( - overlayColor: WidgetStateProperty.all( - Colors.transparent), + overlayColor: WidgetStateProperty.all(Colors.transparent), onTap: () {}, child: Row( mainAxisAlignment: MainAxisAlignment.center, - crossAxisAlignment: - CrossAxisAlignment.center, + crossAxisAlignment: CrossAxisAlignment.center, children: [ Container( decoration: BoxDecoration( - borderRadius: - BorderRadius.circular(890), + borderRadius: BorderRadius.circular(890), boxShadow: [ BoxShadow( - color: Colors.white - .withOpacity(0.1), + color: Colors.white.withOpacity(0.1), blurRadius: 24, offset: const Offset(-5, -5), blurStyle: BlurStyle.outer, ), BoxShadow( - color: Colors.black - .withOpacity(0.11), + color: Colors.black.withOpacity(0.11), blurRadius: 25, offset: const Offset(5, 5), blurStyle: BlurStyle.outer, ), BoxShadow( - color: Colors.black - .withOpacity(0.13), + color: Colors.black.withOpacity(0.13), blurRadius: 30, offset: const Offset(5, 5), blurStyle: BlurStyle.inner, @@ -106,14 +96,12 @@ class GarageDoorScreen extends StatelessWidget { ), child: InkWell( onTap: () { - garageBloc.add(ToggleDoorEvent( - toggle: - garageBloc.toggleDoor)); + garageBloc.add( + ToggleDoorEvent(toggle: garageBloc.toggleDoor)); }, child: GradientWidget( doorStatus: garageBloc.toggleDoor, - seconds: - garageBloc.secondSelected, + seconds: garageBloc.secondSelected, ), )), ], @@ -128,8 +116,7 @@ class GarageDoorScreen extends StatelessWidget { onTap: () { Navigator.of(context).push( MaterialPageRoute( - builder: (context) => - TimerScheduleScreen( + builder: (context) => TimerScheduleScreen( device: device!, switchCode: 'switch_1', deviceCode: 'countdown_1', @@ -137,16 +124,13 @@ class GarageDoorScreen extends StatelessWidget { ); }, child: Column( - crossAxisAlignment: - CrossAxisAlignment.center, - mainAxisAlignment: - MainAxisAlignment.center, + crossAxisAlignment: CrossAxisAlignment.center, + mainAxisAlignment: MainAxisAlignment.center, children: [ ConstrainedBox( - constraints: const BoxConstraints( - maxHeight: 46, maxWidth: 50), - child: SvgPicture.asset( - Assets.garageSchedule), + constraints: + const BoxConstraints(maxHeight: 46, maxWidth: 50), + child: SvgPicture.asset(Assets.garageSchedule), ), const SizedBox( height: 15, @@ -179,16 +163,13 @@ class GarageDoorScreen extends StatelessWidget { ); }, child: Column( - crossAxisAlignment: - CrossAxisAlignment.center, - mainAxisAlignment: - MainAxisAlignment.center, + crossAxisAlignment: CrossAxisAlignment.center, + mainAxisAlignment: MainAxisAlignment.center, children: [ ConstrainedBox( - constraints: const BoxConstraints( - maxHeight: 46, maxWidth: 50), - child: SvgPicture.asset( - Assets.garageCountdown), + constraints: + const BoxConstraints(maxHeight: 46, maxWidth: 50), + child: SvgPicture.asset(Assets.garageCountdown), ), const SizedBox( height: 15, @@ -220,21 +201,17 @@ class GarageDoorScreen extends StatelessWidget { Navigator.of(context).push( MaterialPageRoute( builder: (context) => - GarageRecordsScreen( - GDId: device!.uuid!)), + GarageRecordsScreen(GDId: device!.uuid!)), ); }, child: Column( - crossAxisAlignment: - CrossAxisAlignment.center, - mainAxisAlignment: - MainAxisAlignment.center, + crossAxisAlignment: CrossAxisAlignment.center, + mainAxisAlignment: MainAxisAlignment.center, children: [ ConstrainedBox( - constraints: const BoxConstraints( - maxHeight: 46, maxWidth: 50), - child: SvgPicture.asset( - Assets.doorRecordsIcon), + constraints: + const BoxConstraints(maxHeight: 46, maxWidth: 50), + child: SvgPicture.asset(Assets.doorRecordsIcon), ), const SizedBox( height: 15, @@ -260,21 +237,17 @@ class GarageDoorScreen extends StatelessWidget { Navigator.of(context).push( MaterialPageRoute( builder: (context) => - PreferencesPage( - GDId: device!.uuid!)), + PreferencesPage(GDId: device!.uuid!)), ); }, child: Column( - crossAxisAlignment: - CrossAxisAlignment.center, - mainAxisAlignment: - MainAxisAlignment.center, + crossAxisAlignment: CrossAxisAlignment.center, + mainAxisAlignment: MainAxisAlignment.center, children: [ ConstrainedBox( - constraints: const BoxConstraints( - maxHeight: 46, maxWidth: 50), - child: SvgPicture.asset( - Assets.garagePreferencesIcon), + constraints: + const BoxConstraints(maxHeight: 46, maxWidth: 50), + child: SvgPicture.asset(Assets.garagePreferencesIcon), ), const SizedBox( height: 15, @@ -316,8 +289,7 @@ class GradientWidget extends StatefulWidget { State createState() => _GradientWidgetState(); } -class _GradientWidgetState extends State - with SingleTickerProviderStateMixin { +class _GradientWidgetState extends State with SingleTickerProviderStateMixin { late ScrollController _scrollController; late AnimationController _animationController; late Animation _itemExtentAnimation; @@ -330,16 +302,15 @@ class _GradientWidgetState extends State vsync: this, duration: Duration(seconds: widget.seconds), ); - _itemExtentAnimation = Tween( - begin: widget.doorStatus ? 0 : 15, end: widget.doorStatus ? 15 : 0) - .animate( + _itemExtentAnimation = + Tween(begin: widget.doorStatus ? 0 : 15, end: widget.doorStatus ? 15 : 0).animate( CurvedAnimation( parent: _animationController, curve: Curves.easeInOut, ), )..addListener(() { - setState(() {}); - }); + setState(() {}); + }); WidgetsBinding.instance.addPostFrameCallback((_) { if (widget.doorStatus) { diff --git a/lib/features/devices/view/widgets/garage_door/garage_preferences_settings.dart b/lib/features/devices/view/widgets/garage_door/garage_preferences_settings.dart index b0bb6db..72ea127 100644 --- a/lib/features/devices/view/widgets/garage_door/garage_preferences_settings.dart +++ b/lib/features/devices/view/widgets/garage_door/garage_preferences_settings.dart @@ -18,8 +18,7 @@ class PreferencesPage extends StatelessWidget { return DefaultScaffold( title: 'Preferences', child: BlocProvider( - create: (context) => - GarageDoorBloc(GDId: GDId)..add(const GarageDoorInitial()), + create: (context) => GarageDoorBloc(GDId: GDId)..add(const GarageDoorInitial()), child: BlocBuilder( builder: (context, state) { final garageDoorBloc = BlocProvider.of(context); @@ -27,9 +26,7 @@ class PreferencesPage extends StatelessWidget { return state is GarageDoorLoadingState ? const Center( child: DefaultContainer( - width: 50, - height: 50, - child: CircularProgressIndicator()), + width: 50, height: 50, child: CircularProgressIndicator()), ) : Column( children: [ @@ -59,8 +56,7 @@ class PreferencesPage extends StatelessWidget { trailing: Container( width: 100, child: Row( - mainAxisAlignment: - MainAxisAlignment.end, + mainAxisAlignment: MainAxisAlignment.end, children: [ Container( height: 30, @@ -70,8 +66,7 @@ class PreferencesPage extends StatelessWidget { Transform.scale( scale: .8, child: CupertinoSwitch( - value: - garageDoorBloc.lowBattery, + value: garageDoorBloc.lowBattery, onChanged: (value) { // context // .read() @@ -108,15 +103,12 @@ class PreferencesPage extends StatelessWidget { builder: (context) { return SecondDialog( label2: 'Close', - initialSelectedLabel: garageDoorBloc - .secondSelected - .toString(), + initialSelectedLabel: garageDoorBloc.secondSelected.toString(), cancelTab: () { Navigator.of(context).pop(); }, confirmTab: (v) { - garageDoorBloc - .add(SelectSecondsEvent(seconds: v)); + garageDoorBloc.add(SelectSecondsEvent(seconds: v)); Navigator.of(context).pop(); }, title: 'Control', @@ -137,10 +129,8 @@ class PreferencesPage extends StatelessWidget { height: 90, width: 120, child: Row( - crossAxisAlignment: - CrossAxisAlignment.center, - mainAxisAlignment: - MainAxisAlignment.spaceBetween, + crossAxisAlignment: CrossAxisAlignment.center, + mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ BodyMedium( fontColor: ColorsManager.textGray, @@ -193,7 +183,7 @@ class SecondDialog extends StatefulWidget { } class _SecondDialogState extends State { - late String _selectedOption; + // late String _selectedOption; late int selectedSecond; @override @@ -201,7 +191,7 @@ class _SecondDialogState extends State { super.initState(); // Parse the initialSelectedLabel as an integer. Default to 10 if invalid or not provided. selectedSecond = int.tryParse(widget.initialSelectedLabel ?? '10') ?? 10; - _selectedOption = widget.initialSelectedLabel ?? ''; + // _selectedOption = widget.initialSelectedLabel ?? ''; } @override @@ -252,9 +242,7 @@ class _SecondDialogState extends State { child: BodyLarge( text: (index + 10).toString().padLeft(2, '0'), style: const TextStyle( - fontWeight: FontWeight.w400, - fontSize: 30, - color: Colors.blue), + fontWeight: FontWeight.w400, fontSize: 30, color: Colors.blue), ), ); }), diff --git a/lib/features/devices/view/widgets/garage_door/schedule_garage_screen.dart b/lib/features/devices/view/widgets/garage_door/schedule_garage_screen.dart index 19ce643..1a20804 100644 --- a/lib/features/devices/view/widgets/garage_door/schedule_garage_screen.dart +++ b/lib/features/devices/view/widgets/garage_door/schedule_garage_screen.dart @@ -18,10 +18,7 @@ class TimerScheduleScreen extends StatelessWidget { final String deviceCode; final String switchCode; const TimerScheduleScreen( - {required this.device, - required this.deviceCode, - required this.switchCode, - super.key}); + {required this.device, required this.deviceCode, required this.switchCode, super.key}); @override Widget build(BuildContext context) { @@ -31,22 +28,21 @@ class TimerScheduleScreen extends StatelessWidget { statusBarIconBrightness: Brightness.light, ), child: BlocProvider( - create: (context) => - GarageDoorBloc(GDId: device.uuid ?? '')..add(GetScheduleEvent()), + create: (context) => GarageDoorBloc(GDId: device.uuid ?? '')..add(GetScheduleEvent()), child: BlocBuilder( builder: (context, state) { final garageBloc = BlocProvider.of(context); - Duration duration = Duration.zero; - int countNum = 0; - if (state is UpdateTimerState) { - countNum = state.seconds; - } else if (state is TimerRunInProgress) { - countNum = state.remainingTime; - } else if (state is TimerRunComplete) { - countNum = 0; - } else if (state is LoadingNewSate) { - countNum = 0; - } + // Duration duration = Duration.zero; + // int countNum = 0; + // if (state is UpdateTimerState) { + // countNum = state.seconds; + // } else if (state is TimerRunInProgress) { + // countNum = state.remainingTime; + // } else if (state is TimerRunComplete) { + // countNum = 0; + // } else if (state is LoadingNewSate) { + // countNum = 0; + // } return PopScope( canPop: false, onPopInvoked: (didPop) { @@ -75,9 +71,7 @@ class TimerScheduleScreen extends StatelessWidget { child: const Text('Save')) : IconButton( onPressed: () { - garageBloc.add( - const ToggleCreateScheduleEvent( - index: 1)); + garageBloc.add(const ToggleCreateScheduleEvent(index: 1)); }, icon: const Icon(Icons.add), ) @@ -92,8 +86,7 @@ class TimerScheduleScreen extends StatelessWidget { decoration: const ShapeDecoration( color: ColorsManager.onPrimaryColor, shape: RoundedRectangleBorder( - borderRadius: - BorderRadius.all(Radius.circular(30)), + borderRadius: BorderRadius.all(Radius.circular(30)), ), ), ), @@ -104,37 +97,25 @@ class TimerScheduleScreen extends StatelessWidget { onToggleChanged: (bool value) { garageBloc.toggleSchedule = value; }, - onDateTimeChanged: - (DateTime dateTime) { - garageBloc.selectedTime = - dateTime; + onDateTimeChanged: (DateTime dateTime) { + garageBloc.selectedTime = dateTime; }, days: garageBloc.days, - selectDays: - (List selectedDays) { - garageBloc.selectedDays = - selectedDays; + selectDays: (List selectedDays) { + garageBloc.selectedDays = selectedDays; }, ) : Padding( - padding: - const EdgeInsets.only(top: 10), + padding: const EdgeInsets.only(top: 10), child: ScheduleListView( - listSchedule: - garageBloc.listSchedule, + listSchedule: garageBloc.listSchedule, onDismissed: (scheduleId) { - garageBloc.listSchedule - .removeWhere((schedule) => - schedule.scheduleId == - scheduleId); - garageBloc.add( - DeleteScheduleEvent( - id: scheduleId)); + garageBloc.listSchedule.removeWhere((schedule) => + schedule.scheduleId == scheduleId); + garageBloc.add(DeleteScheduleEvent(id: scheduleId)); }, - onToggleSchedule: - (scheduleId, isEnabled) { - garageBloc - .add(ToggleScheduleEvent( + onToggleSchedule: (scheduleId, isEnabled) { + garageBloc.add(ToggleScheduleEvent( id: scheduleId, toggle: isEnabled, )); diff --git a/lib/features/devices/view/widgets/one_touch/one_touch_screen.dart b/lib/features/devices/view/widgets/one_touch/one_touch_screen.dart index 383e7d0..853469c 100644 --- a/lib/features/devices/view/widgets/one_touch/one_touch_screen.dart +++ b/lib/features/devices/view/widgets/one_touch/one_touch_screen.dart @@ -5,7 +5,6 @@ import 'package:syncrow_app/features/devices/bloc/one_touch_bloc/one_touch_bloc. import 'package:syncrow_app/features/devices/bloc/one_touch_bloc/one_touch_event.dart'; import 'package:syncrow_app/features/devices/bloc/one_touch_bloc/one_touch_state.dart'; import 'package:syncrow_app/features/devices/model/device_model.dart'; -import 'package:syncrow_app/features/devices/model/group_one_touch_model.dart'; import 'package:syncrow_app/features/devices/model/one_touch_model.dart'; import 'package:syncrow_app/features/devices/view/widgets/circular_button.dart'; import 'package:syncrow_app/features/devices/view/widgets/device_appbar.dart'; @@ -69,9 +68,9 @@ class OneTouchScreen extends StatelessWidget { bottom: Constants.bottomNavBarHeight, ), child: BlocProvider( - create: (context) => OneTouchBloc( - switchCode: 'switch_1', oneTouchId: device?.uuid ?? '') - ..add(const InitialEvent(groupScreen: false)), + create: (context) => + OneTouchBloc(switchCode: 'switch_1', oneTouchId: device?.uuid ?? '') + ..add(const InitialEvent(groupScreen: false)), child: BlocBuilder( builder: (context, state) { OneTouchModel oneTouchModel = OneTouchModel( @@ -81,30 +80,27 @@ class OneTouchScreen extends StatelessWidget { relay: status.off, relay_status_1: status.off); - List groupOneTouchModel = []; - bool allSwitchesOn = false; + // List groupOneTouchModel = []; + // bool allSwitchesOn = false; if (state is LoadingNewSate) { oneTouchModel = state.oneTouchModel; } else if (state is UpdateState) { oneTouchModel = state.oneTouchModel; - } else if (state is UpdateGroupState) { - groupOneTouchModel = state.oneTouchList; - allSwitchesOn = state.allSwitches; } + // else if (state is UpdateGroupState) { + // groupOneTouchModel = state.oneTouchList; + // allSwitchesOn = state.allSwitches; + // } return state is LoadingInitialState ? const Center( child: DefaultContainer( - width: 50, - height: 50, - child: CircularProgressIndicator()), + width: 50, height: 50, child: CircularProgressIndicator()), ) : RefreshIndicator( onRefresh: () async { - BlocProvider.of(context).add( - InitialEvent( - groupScreen: - device != null ? false : true)); + BlocProvider.of(context) + .add(InitialEvent(groupScreen: device != null ? false : true)); }, child: ListView( children: [ @@ -112,30 +108,23 @@ class OneTouchScreen extends StatelessWidget { height: MediaQuery.of(context).size.height, child: Column( mainAxisAlignment: MainAxisAlignment.center, - crossAxisAlignment: - CrossAxisAlignment.stretch, + crossAxisAlignment: CrossAxisAlignment.stretch, children: [ const Expanded(child: SizedBox.shrink()), Expanded( child: Row( - mainAxisAlignment: - MainAxisAlignment.spaceAround, - crossAxisAlignment: - CrossAxisAlignment.center, + mainAxisAlignment: MainAxisAlignment.spaceAround, + crossAxisAlignment: CrossAxisAlignment.center, children: [ Column( children: [ GangSwitch( threeGangSwitch: device!, - value: - oneTouchModel.firstSwitch, + value: oneTouchModel.firstSwitch, action: () { - BlocProvider.of< - OneTouchBloc>( - context) - .add(ChangeFirstSwitchStatusEvent( - value: oneTouchModel - .firstSwitch)); + BlocProvider.of(context).add( + ChangeFirstSwitchStatusEvent( + value: oneTouchModel.firstSwitch)); }, ), const SizedBox(height: 20), @@ -143,8 +132,7 @@ class OneTouchScreen extends StatelessWidget { width: 70, child: BodySmall( text: " Entrance Light", - fontColor: ColorsManager - .textPrimaryColor, + fontColor: ColorsManager.textPrimaryColor, textAlign: TextAlign.center, ), ), @@ -155,10 +143,8 @@ class OneTouchScreen extends StatelessWidget { ), Center( child: Row( - mainAxisAlignment: - MainAxisAlignment.center, - crossAxisAlignment: - CrossAxisAlignment.center, + mainAxisAlignment: MainAxisAlignment.center, + crossAxisAlignment: CrossAxisAlignment.center, children: [ CircularButton( device: device, @@ -168,16 +154,13 @@ class OneTouchScreen extends StatelessWidget { Navigator.push( context, PageRouteBuilder( - pageBuilder: (context, - animation1, - animation2) => - TimerScheduleScreen( - switchCode: - 'switch_1', - device: device!, - deviceCode: - 'countdown_1', - ))); + pageBuilder: + (context, animation1, animation2) => + TimerScheduleScreen( + switchCode: 'switch_1', + device: device!, + deviceCode: 'countdown_1', + ))); }, ), const SizedBox( @@ -191,12 +174,11 @@ class OneTouchScreen extends StatelessWidget { Navigator.push( context, PageRouteBuilder( - pageBuilder: (context, - animation1, - animation2) => - OneTouchSetting( - device: device, - ))); + pageBuilder: + (context, animation1, animation2) => + OneTouchSetting( + device: device, + ))); }, ), ], diff --git a/lib/features/devices/view/widgets/three_touch/three_touch_setting.dart b/lib/features/devices/view/widgets/three_touch/three_touch_setting.dart index 21ef6b3..f61d0d9 100644 --- a/lib/features/devices/view/widgets/three_touch/three_touch_setting.dart +++ b/lib/features/devices/view/widgets/three_touch/three_touch_setting.dart @@ -4,7 +4,6 @@ import 'package:syncrow_app/features/devices/bloc/three_touch_bloc/three_touch_b import 'package:syncrow_app/features/devices/bloc/three_touch_bloc/three_touch_event.dart'; import 'package:syncrow_app/features/devices/bloc/three_touch_bloc/three_touch_state.dart'; import 'package:syncrow_app/features/devices/model/device_model.dart'; -import 'package:syncrow_app/features/devices/model/three_touch_model.dart'; import 'package:syncrow_app/features/devices/view/widgets/restart_status_dialog.dart'; import 'package:syncrow_app/features/shared_widgets/default_container.dart'; import 'package:syncrow_app/features/shared_widgets/default_scaffold.dart'; @@ -23,41 +22,15 @@ class ThreeTouchSetting extends StatelessWidget { return DefaultScaffold( title: 'Setting', child: BlocProvider( - create: (context) => - ThreeTouchBloc(switchCode: '', threeTouchId: device?.uuid ?? '') - ..add(InitialEvent(groupScreen: false)), + create: (context) => ThreeTouchBloc(switchCode: '', threeTouchId: device?.uuid ?? '') + ..add(InitialEvent(groupScreen: false)), child: BlocBuilder( builder: (context, state) { final threeTouchBloc = BlocProvider.of(context); - ThreeTouchModel deviceStatus = ThreeTouchModel( - firstSwitch: false, - secondSwitch: false, - thirdSwitch: false, - firstCountDown: 0, - secondCountDown: 0, - thirdCountDown: 0, - light_mode: lightStatus.off, - relay: status.off, - relay_status_1: status.off, - relay_status_2: status.off, - relay_status_3: status.off, - ); - if (state is LoadingNewSate) { - deviceStatus = state.threeTouchModel; - } else if (state is UpdateState) { - deviceStatus = state.threeTouchModel; - } - // if (state is ChangeStateSetting) { - // // Navigator.of(context).pop(true); - // threeTouchBloc - // .add(InitialSettingDevises(id: device?.uuid ?? '')); - // } return state is LoadingInitialState ? const Center( child: DefaultContainer( - width: 50, - height: 50, - child: CircularProgressIndicator()), + width: 50, height: 50, child: CircularProgressIndicator()), ) : Column( children: [ @@ -70,22 +43,19 @@ class ThreeTouchSetting extends StatelessWidget { children: [ InkWell( onTap: () async { - threeTouchBloc.optionSelected = - 'relay_status'; + threeTouchBloc.optionSelected = 'relay_status'; final result = await showDialog( context: context, builder: (context) { return RestartStatusDialog( - initialSelectedLabel: threeTouchBloc - .deviceStatus.relay.value, + initialSelectedLabel: + threeTouchBloc.deviceStatus.relay.value, cancelTab: () { Navigator.of(context).pop(); }, confirmTab: () { - threeTouchBloc.add( - ChangeStatusEvent( - deviceId: device!.uuid!, - context: context)); + threeTouchBloc.add(ChangeStatusEvent( + deviceId: device!.uuid!, context: context)); Navigator.of(context).pop(true); }, title: 'Restart Status', @@ -93,34 +63,27 @@ class ThreeTouchSetting extends StatelessWidget { label2: 'Power On', label3: 'Restart Memory', onTapLabel1: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, onTapLabel2: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, onTapLabel3: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, ); }, ); if (result == true) { - Future.delayed(const Duration(seconds: 2), - () async { - threeTouchBloc.add( - InitialEvent(groupScreen: false)); + Future.delayed(const Duration(seconds: 2), () async { + threeTouchBloc.add(InitialEvent(groupScreen: false)); }); } }, child: Container( - padding: const EdgeInsets.only( - bottom: 10, top: 10), + padding: const EdgeInsets.only(bottom: 10, top: 10), child: Row( - mainAxisAlignment: - MainAxisAlignment.spaceBetween, + mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ const BodyLarge( fontSize: 15, @@ -131,10 +94,8 @@ class ThreeTouchSetting extends StatelessWidget { children: [ BodyMedium( fontSize: 13, - text: threeTouchBloc - .deviceStatus.relay.value, - fontColor: - ColorsManager.textGray, + text: threeTouchBloc.deviceStatus.relay.value, + fontColor: ColorsManager.textGray, ), const Icon( Icons.keyboard_arrow_right, @@ -149,26 +110,22 @@ class ThreeTouchSetting extends StatelessWidget { color: ColorsManager.graysColor, ), Padding( - padding: const EdgeInsets.only( - bottom: 10, top: 10), + padding: const EdgeInsets.only(bottom: 10, top: 10), child: InkWell( onTap: () async { - threeTouchBloc.optionSelected = - 'light_mode'; + threeTouchBloc.optionSelected = 'light_mode'; final result = await showDialog( context: context, builder: (context) { return RestartStatusDialog( - initialSelectedLabel: threeTouchBloc - .deviceStatus.light_mode.value, + initialSelectedLabel: + threeTouchBloc.deviceStatus.light_mode.value, cancelTab: () { Navigator.of(context).pop(); }, confirmTab: () { - threeTouchBloc.add( - ChangeStatusEvent( - deviceId: device!.uuid!, - context: context)); + threeTouchBloc.add(ChangeStatusEvent( + deviceId: device!.uuid!, context: context)); Navigator.of(context).pop(true); }, title: 'Indicator Status', @@ -176,33 +133,26 @@ class ThreeTouchSetting extends StatelessWidget { label2: 'On/Off Status', label3: 'Switch Position', onTapLabel1: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, onTapLabel2: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, onTapLabel3: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, ); }, ); if (result == true) { - Future.delayed( - const Duration(seconds: 2), - () async { - threeTouchBloc.add( - InitialEvent(groupScreen: false)); + Future.delayed(const Duration(seconds: 2), () async { + threeTouchBloc.add(InitialEvent(groupScreen: false)); }); } }, child: SizedBox( child: Row( - mainAxisAlignment: - MainAxisAlignment.spaceBetween, + mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ const BodyLarge( fontSize: 15, @@ -213,8 +163,7 @@ class ThreeTouchSetting extends StatelessWidget { children: [ BodyMedium( fontSize: 13, - text: threeTouchBloc.deviceStatus - .light_mode.value, + text: threeTouchBloc.deviceStatus.light_mode.value, fontColor: ColorsManager.textGray, ), const Icon( @@ -231,27 +180,22 @@ class ThreeTouchSetting extends StatelessWidget { color: ColorsManager.graysColor, ), Container( - padding: const EdgeInsets.only( - bottom: 10, top: 10), + padding: const EdgeInsets.only(bottom: 10, top: 10), child: InkWell( onTap: () async { - threeTouchBloc.optionSelected = - 'relay_status_1'; + threeTouchBloc.optionSelected = 'relay_status_1'; final result = await showDialog( context: context, builder: (context) { return RestartStatusDialog( initialSelectedLabel: - threeTouchBloc.deviceStatus - .relay_status_1.value, + threeTouchBloc.deviceStatus.relay_status_1.value, cancelTab: () { Navigator.of(context).pop(); }, confirmTab: () { - threeTouchBloc.add( - ChangeStatusEvent( - deviceId: device!.uuid!, - context: context)); + threeTouchBloc.add(ChangeStatusEvent( + deviceId: device!.uuid!, context: context)); Navigator.of(context).pop(true); }, title: 'Restart Status 1', @@ -259,33 +203,26 @@ class ThreeTouchSetting extends StatelessWidget { label2: 'Power On', label3: 'Restart Memory', onTapLabel1: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, onTapLabel2: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, onTapLabel3: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, ); }, ); if (result == true) { - Future.delayed( - const Duration(seconds: 2), - () async { - threeTouchBloc.add( - const InitialEvent( - groupScreen: false)); + Future.delayed(const Duration(seconds: 2), () async { + threeTouchBloc + .add(const InitialEvent(groupScreen: false)); }); } }, child: Row( - mainAxisAlignment: - MainAxisAlignment.spaceBetween, + mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ const BodyLarge( fontSize: 15, @@ -297,11 +234,8 @@ class ThreeTouchSetting extends StatelessWidget { BodyMedium( fontSize: 13, text: threeTouchBloc - .deviceStatus - .relay_status_1 - .value, - fontColor: - ColorsManager.textGray, + .deviceStatus.relay_status_1.value, + fontColor: ColorsManager.textGray, ), const Icon( Icons.keyboard_arrow_right, @@ -316,27 +250,22 @@ class ThreeTouchSetting extends StatelessWidget { color: ColorsManager.graysColor, ), Container( - padding: const EdgeInsets.only( - bottom: 10, top: 10), + padding: const EdgeInsets.only(bottom: 10, top: 10), child: InkWell( onTap: () async { - threeTouchBloc.optionSelected = - 'relay_status_2'; + threeTouchBloc.optionSelected = 'relay_status_2'; final result = await showDialog( context: context, builder: (context) { return RestartStatusDialog( initialSelectedLabel: - threeTouchBloc.deviceStatus - .relay_status_2.value, + threeTouchBloc.deviceStatus.relay_status_2.value, cancelTab: () { Navigator.of(context).pop(); }, confirmTab: () { - threeTouchBloc.add( - ChangeStatusEvent( - deviceId: device!.uuid!, - context: context)); + threeTouchBloc.add(ChangeStatusEvent( + deviceId: device!.uuid!, context: context)); Navigator.of(context).pop(true); }, title: 'Restart Status 2', @@ -344,36 +273,28 @@ class ThreeTouchSetting extends StatelessWidget { label2: 'Power On', label3: 'Restart Memory', onTapLabel1: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, onTapLabel2: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, onTapLabel3: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, ); }, ); if (result == true) { - Future.delayed( - const Duration(seconds: 2), - () async { - threeTouchBloc.add( - const InitialEvent( - groupScreen: false)); - threeTouchBloc.add( - const InitialEvent( - groupScreen: false)); + Future.delayed(const Duration(seconds: 2), () async { + threeTouchBloc + .add(const InitialEvent(groupScreen: false)); + threeTouchBloc + .add(const InitialEvent(groupScreen: false)); }); } }, child: Row( - mainAxisAlignment: - MainAxisAlignment.spaceBetween, + mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ const BodyLarge( fontSize: 15, @@ -385,11 +306,8 @@ class ThreeTouchSetting extends StatelessWidget { BodyMedium( fontSize: 13, text: threeTouchBloc - .deviceStatus - .relay_status_2 - .value, - fontColor: - ColorsManager.textGray, + .deviceStatus.relay_status_2.value, + fontColor: ColorsManager.textGray, ), const Icon( Icons.keyboard_arrow_right, @@ -404,27 +322,22 @@ class ThreeTouchSetting extends StatelessWidget { color: ColorsManager.graysColor, ), Container( - padding: const EdgeInsets.only( - bottom: 10, top: 10), + padding: const EdgeInsets.only(bottom: 10, top: 10), child: InkWell( onTap: () async { - threeTouchBloc.optionSelected = - 'relay_status_3'; + threeTouchBloc.optionSelected = 'relay_status_3'; final result = await showDialog( context: context, builder: (context) { return RestartStatusDialog( initialSelectedLabel: - threeTouchBloc.deviceStatus - .relay_status_3.value, + threeTouchBloc.deviceStatus.relay_status_3.value, cancelTab: () { Navigator.of(context).pop(); }, confirmTab: () { - threeTouchBloc.add( - ChangeStatusEvent( - deviceId: device!.uuid!, - context: context)); + threeTouchBloc.add(ChangeStatusEvent( + deviceId: device!.uuid!, context: context)); Navigator.of(context).pop(true); }, title: 'Restart Status 3', @@ -432,36 +345,28 @@ class ThreeTouchSetting extends StatelessWidget { label2: 'Power On', label3: 'Restart Memory', onTapLabel1: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, onTapLabel2: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, onTapLabel3: (selected) { - threeTouchBloc.statusSelected = - selected; + threeTouchBloc.statusSelected = selected; }, ); }, ); if (result == true) { - Future.delayed( - const Duration(seconds: 2), - () async { - threeTouchBloc.add( - const InitialEvent( - groupScreen: false)); - threeTouchBloc.add( - const InitialEvent( - groupScreen: false)); + Future.delayed(const Duration(seconds: 2), () async { + threeTouchBloc + .add(const InitialEvent(groupScreen: false)); + threeTouchBloc + .add(const InitialEvent(groupScreen: false)); }); } }, child: Row( - mainAxisAlignment: - MainAxisAlignment.spaceBetween, + mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ const BodyLarge( fontSize: 15, @@ -473,11 +378,8 @@ class ThreeTouchSetting extends StatelessWidget { BodyMedium( fontSize: 13, text: threeTouchBloc - .deviceStatus - .relay_status_3 - .value, - fontColor: - ColorsManager.textGray, + .deviceStatus.relay_status_3.value, + fontColor: ColorsManager.textGray, ), const Icon( Icons.keyboard_arrow_right, diff --git a/lib/features/devices/view/widgets/water_heater/wh_wizard.dart b/lib/features/devices/view/widgets/water_heater/wh_wizard.dart index c27fd55..c8ce572 100644 --- a/lib/features/devices/view/widgets/water_heater/wh_wizard.dart +++ b/lib/features/devices/view/widgets/water_heater/wh_wizard.dart @@ -19,28 +19,29 @@ class WHWizard extends StatelessWidget { List groupModel = []; return DefaultScaffold( + title: 'Water Heater', child: BlocProvider( - create: (context) => - WaterHeaterBloc(switchCode: '', whId: device?.uuid ?? '')..add(InitialWizardEvent()), - child: BlocBuilder( - builder: (context, state) { - bool allSwitchesOn = false; + create: (context) => + WaterHeaterBloc(switchCode: '', whId: device?.uuid ?? '')..add(InitialWizardEvent()), + child: BlocBuilder( + builder: (context, state) { + bool allSwitchesOn = false; - if (state is UpdateGroupState) { - groupModel = state.twoGangList; - allSwitchesOn = state.allSwitches; - } - return state is WHLoadingState - ? const Center( - child: - DefaultContainer(width: 50, height: 50, child: CircularProgressIndicator()), - ) - : WHList( - whList: groupModel, - allSwitches: allSwitchesOn, - ); - }, - ), - )); + if (state is UpdateGroupState) { + groupModel = state.twoGangList; + allSwitchesOn = state.allSwitches; + } + return state is WHLoadingState + ? const Center( + child: DefaultContainer( + width: 50, height: 50, child: CircularProgressIndicator()), + ) + : WHList( + whList: groupModel, + allSwitches: allSwitchesOn, + ); + }, + ), + )); } } diff --git a/lib/features/menu/view/menu_view.dart b/lib/features/menu/view/menu_view.dart index bba2896..aa1ae86 100644 --- a/lib/features/menu/view/menu_view.dart +++ b/lib/features/menu/view/menu_view.dart @@ -1,5 +1,6 @@ import 'package:flutter/material.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:flutter_dotenv/flutter_dotenv.dart'; import 'package:syncrow_app/features/auth/bloc/auth_cubit.dart'; import 'package:syncrow_app/features/menu/bloc/menu_cubit.dart'; import 'package:syncrow_app/features/menu/view/widgets/menu_list.dart'; @@ -7,7 +8,6 @@ import 'package:syncrow_app/features/menu/view/widgets/profile/profile_tab.dart' import 'package:syncrow_app/features/shared_widgets/default_container.dart'; import 'package:syncrow_app/features/shared_widgets/text_widgets/body_large.dart'; import 'package:syncrow_app/features/shared_widgets/text_widgets/body_medium.dart'; -import 'package:syncrow_app/services/locator.dart'; import 'package:syncrow_app/utils/context_extension.dart'; import 'package:syncrow_app/utils/resource_manager/constants.dart'; @@ -34,7 +34,7 @@ class MenuView extends StatelessWidget { const SizedBox( height: 15, ), - BodyMedium(text: serviceLocator.get()), + BodyMedium(text: dotenv.env['ENV_NAME'] ?? ''), const SizedBox( height: 15, ), diff --git a/lib/generated/assets.dart b/lib/generated/assets.dart index c94ff82..cb89189 100644 --- a/lib/generated/assets.dart +++ b/lib/generated/assets.dart @@ -3,8 +3,7 @@ class Assets { /// Assets for assetsFontsAftikaRegular /// assets/fonts/AftikaRegular.ttf - static const String assetsFontsAftikaRegular = - "assets/fonts/AftikaRegular.ttf"; + static const String assetsFontsAftikaRegular = "assets/fonts/AftikaRegular.ttf"; /// Assets for assetsIcons3GangSwitch /// assets/icons/3GangSwitch.svg @@ -20,98 +19,82 @@ class Assets { /// Assets for assetsIconsAutomatedClock /// assets/icons/automated_clock.svg - static const String assetsIconsAutomatedClock = - "assets/icons/automated_clock.svg"; + static const String assetsIconsAutomatedClock = "assets/icons/automated_clock.svg"; static const String acSwitchIcon = "assets/icons/ac_switch_ic.svg"; /// Assets for assetsIconsBatteryDmOffPerOffchargOfflowOffpmOffstChargeddmOff /// assets/icons/battery/dmOff/perOffchargOfflowOffpmOffstChargeddmOff.svg - static const String - assetsIconsBatteryDmOffPerOffchargOfflowOffpmOffstChargeddmOff = + static const String assetsIconsBatteryDmOffPerOffchargOfflowOffpmOffstChargeddmOff = "assets/icons/battery/dmOff/perOffchargOfflowOffpmOffstChargeddmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOffchargOfflowOffpmOffstDefaultdmOff /// assets/icons/battery/dmOff/perOffchargOfflowOffpmOffstDefaultdmOff.svg - static const String - assetsIconsBatteryDmOffPerOffchargOfflowOffpmOffstDefaultdmOff = + static const String assetsIconsBatteryDmOffPerOffchargOfflowOffpmOffstDefaultdmOff = "assets/icons/battery/dmOff/perOffchargOfflowOffpmOffstDefaultdmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOffchargOfflowOffpmOnstChargeddmOff /// assets/icons/battery/dmOff/perOffchargOfflowOffpmOnstChargeddmOff.svg - static const String - assetsIconsBatteryDmOffPerOffchargOfflowOffpmOnstChargeddmOff = + static const String assetsIconsBatteryDmOffPerOffchargOfflowOffpmOnstChargeddmOff = "assets/icons/battery/dmOff/perOffchargOfflowOffpmOnstChargeddmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOffchargOfflowOnpmOffstDefaultdmOff /// assets/icons/battery/dmOff/perOffchargOfflowOnpmOffstDefaultdmOff.svg - static const String - assetsIconsBatteryDmOffPerOffchargOfflowOnpmOffstDefaultdmOff = + static const String assetsIconsBatteryDmOffPerOffchargOfflowOnpmOffstDefaultdmOff = "assets/icons/battery/dmOff/perOffchargOfflowOnpmOffstDefaultdmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOffchargOfflowOnpmOnstDefaultdmOff /// assets/icons/battery/dmOff/perOffchargOfflowOnpmOnstDefaultdmOff.svg - static const String - assetsIconsBatteryDmOffPerOffchargOfflowOnpmOnstDefaultdmOff = + static const String assetsIconsBatteryDmOffPerOffchargOfflowOnpmOnstDefaultdmOff = "assets/icons/battery/dmOff/perOffchargOfflowOnpmOnstDefaultdmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOffchargOnlowOffpmOffstChargeddmOff /// assets/icons/battery/dmOff/perOffchargOnlowOffpmOffstChargeddmOff.svg - static const String - assetsIconsBatteryDmOffPerOffchargOnlowOffpmOffstChargeddmOff = + static const String assetsIconsBatteryDmOffPerOffchargOnlowOffpmOffstChargeddmOff = "assets/icons/battery/dmOff/perOffchargOnlowOffpmOffstChargeddmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOffchargOnlowOnpmOffstlowBatterydmOff /// assets/icons/battery/dmOff/perOffchargOnlowOnpmOffstlowBatterydmOff.svg - static const String - assetsIconsBatteryDmOffPerOffchargOnlowOnpmOffstlowBatterydmOff = + static const String assetsIconsBatteryDmOffPerOffchargOnlowOnpmOffstlowBatterydmOff = "assets/icons/battery/dmOff/perOffchargOnlowOnpmOffstlowBatterydmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOffchargOnlowOnpmOnstlowpmdmOff /// assets/icons/battery/dmOff/perOffchargOnlowOnpmOnstlowpmdmOff.svg - static const String - assetsIconsBatteryDmOffPerOffchargOnlowOnpmOnstlowpmdmOff = + static const String assetsIconsBatteryDmOffPerOffchargOnlowOnpmOnstlowpmdmOff = "assets/icons/battery/dmOff/perOffchargOnlowOnpmOnstlowpmdmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOnchargOfflowOffpmOffstChargeddmOff /// assets/icons/battery/dmOff/perOnchargOfflowOffpmOffstChargeddmOff.svg - static const String - assetsIconsBatteryDmOffPerOnchargOfflowOffpmOffstChargeddmOff = + static const String assetsIconsBatteryDmOffPerOnchargOfflowOffpmOffstChargeddmOff = "assets/icons/battery/dmOff/perOnchargOfflowOffpmOffstChargeddmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOnchargOfflowOffpmOffstDefaultdmOff /// assets/icons/battery/dmOff/perOnchargOfflowOffpmOffstDefaultdmOff.svg - static const String - assetsIconsBatteryDmOffPerOnchargOfflowOffpmOffstDefaultdmOff = + static const String assetsIconsBatteryDmOffPerOnchargOfflowOffpmOffstDefaultdmOff = "assets/icons/battery/dmOff/perOnchargOfflowOffpmOffstDefaultdmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOnchargOfflowOffpmOnstChargeddmOff /// assets/icons/battery/dmOff/perOnchargOfflowOffpmOnstChargeddmOff.svg - static const String - assetsIconsBatteryDmOffPerOnchargOfflowOffpmOnstChargeddmOff = + static const String assetsIconsBatteryDmOffPerOnchargOfflowOffpmOnstChargeddmOff = "assets/icons/battery/dmOff/perOnchargOfflowOffpmOnstChargeddmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOnchargOfflowOnpmOffstDefaultdmOff /// assets/icons/battery/dmOff/perOnchargOfflowOnpmOffstDefaultdmOff.svg - static const String - assetsIconsBatteryDmOffPerOnchargOfflowOnpmOffstDefaultdmOff = + static const String assetsIconsBatteryDmOffPerOnchargOfflowOnpmOffstDefaultdmOff = "assets/icons/battery/dmOff/perOnchargOfflowOnpmOffstDefaultdmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOnchargOfflowOnpmOnstDefaultdmOff /// assets/icons/battery/dmOff/perOnchargOfflowOnpmOnstDefaultdmOff.svg - static const String - assetsIconsBatteryDmOffPerOnchargOfflowOnpmOnstDefaultdmOff = + static const String assetsIconsBatteryDmOffPerOnchargOfflowOnpmOnstDefaultdmOff = "assets/icons/battery/dmOff/perOnchargOfflowOnpmOnstDefaultdmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOnchargOnlowOffpmOffstChargeddmOff /// assets/icons/battery/dmOff/perOnchargOnlowOffpmOffstChargeddmOff.svg - static const String - assetsIconsBatteryDmOffPerOnchargOnlowOffpmOffstChargeddmOff = + static const String assetsIconsBatteryDmOffPerOnchargOnlowOffpmOffstChargeddmOff = "assets/icons/battery/dmOff/perOnchargOnlowOffpmOffstChargeddmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOnchargOnlowOnpmOffstlowBatterydmOff /// assets/icons/battery/dmOff/perOnchargOnlowOnpmOffstlowBatterydmOff.svg - static const String - assetsIconsBatteryDmOffPerOnchargOnlowOnpmOffstlowBatterydmOff = + static const String assetsIconsBatteryDmOffPerOnchargOnlowOnpmOffstlowBatterydmOff = "assets/icons/battery/dmOff/perOnchargOnlowOnpmOffstlowBatterydmOff.svg"; /// Assets for assetsIconsBatteryDmOffPerOnchargOnlowOnpmOnstlowpmdmOff @@ -121,44 +104,37 @@ class Assets { /// Assets for assetsIconsBatteryDmOnPerOffchargOfflowOffpmOffstChargeddmOn /// assets/icons/battery/dmOn/perOffchargOfflowOffpmOffstChargeddmOn.svg - static const String - assetsIconsBatteryDmOnPerOffchargOfflowOffpmOffstChargeddmOn = + static const String assetsIconsBatteryDmOnPerOffchargOfflowOffpmOffstChargeddmOn = "assets/icons/battery/dmOn/perOffchargOfflowOffpmOffstChargeddmOn.svg"; /// Assets for assetsIconsBatteryDmOnPerOffchargOfflowOffpmOffstDefaultdmOn /// assets/icons/battery/dmOn/perOffchargOfflowOffpmOffstDefaultdmOn.svg - static const String - assetsIconsBatteryDmOnPerOffchargOfflowOffpmOffstDefaultdmOn = + static const String assetsIconsBatteryDmOnPerOffchargOfflowOffpmOffstDefaultdmOn = "assets/icons/battery/dmOn/perOffchargOfflowOffpmOffstDefaultdmOn.svg"; /// Assets for assetsIconsBatteryDmOnPerOffchargOfflowOffpmOnstChargeddmOn /// assets/icons/battery/dmOn/perOffchargOfflowOffpmOnstChargeddmOn.svg - static const String - assetsIconsBatteryDmOnPerOffchargOfflowOffpmOnstChargeddmOn = + static const String assetsIconsBatteryDmOnPerOffchargOfflowOffpmOnstChargeddmOn = "assets/icons/battery/dmOn/perOffchargOfflowOffpmOnstChargeddmOn.svg"; /// Assets for assetsIconsBatteryDmOnPerOffchargOfflowOnpmOffstDefaultdmOn /// assets/icons/battery/dmOn/perOffchargOfflowOnpmOffstDefaultdmOn.svg - static const String - assetsIconsBatteryDmOnPerOffchargOfflowOnpmOffstDefaultdmOn = + static const String assetsIconsBatteryDmOnPerOffchargOfflowOnpmOffstDefaultdmOn = "assets/icons/battery/dmOn/perOffchargOfflowOnpmOffstDefaultdmOn.svg"; /// Assets for assetsIconsBatteryDmOnPerOffchargOfflowOnpmOnstDefaultdmOn /// assets/icons/battery/dmOn/perOffchargOfflowOnpmOnstDefaultdmOn.svg - static const String - assetsIconsBatteryDmOnPerOffchargOfflowOnpmOnstDefaultdmOn = + static const String assetsIconsBatteryDmOnPerOffchargOfflowOnpmOnstDefaultdmOn = "assets/icons/battery/dmOn/perOffchargOfflowOnpmOnstDefaultdmOn.svg"; /// Assets for assetsIconsBatteryDmOnPerOffchargOnlowOffpmOffstChargeddmOn /// assets/icons/battery/dmOn/perOffchargOnlowOffpmOffstChargeddmOn.svg - static const String - assetsIconsBatteryDmOnPerOffchargOnlowOffpmOffstChargeddmOn = + static const String assetsIconsBatteryDmOnPerOffchargOnlowOffpmOffstChargeddmOn = "assets/icons/battery/dmOn/perOffchargOnlowOffpmOffstChargeddmOn.svg"; /// Assets for assetsIconsBatteryDmOnPerOffchargOnlowOnpmOffstlowBatterydmOn /// assets/icons/battery/dmOn/perOffchargOnlowOnpmOffstlowBatterydmOn.svg - static const String - assetsIconsBatteryDmOnPerOffchargOnlowOnpmOffstlowBatterydmOn = + static const String assetsIconsBatteryDmOnPerOffchargOnlowOnpmOffstlowBatterydmOn = "assets/icons/battery/dmOn/perOffchargOnlowOnpmOffstlowBatterydmOn.svg"; /// Assets for assetsIconsBatteryDmOnPerOffchargOnlowOnpmOnstlowpmdmOn @@ -168,44 +144,37 @@ class Assets { /// Assets for assetsIconsBatteryDmOnPerOnchargOfflowOffpmOffstChargeddmOn /// assets/icons/battery/dmOn/perOnchargOfflowOffpmOffstChargeddmOn.svg - static const String - assetsIconsBatteryDmOnPerOnchargOfflowOffpmOffstChargeddmOn = + static const String assetsIconsBatteryDmOnPerOnchargOfflowOffpmOffstChargeddmOn = "assets/icons/battery/dmOn/perOnchargOfflowOffpmOffstChargeddmOn.svg"; /// Assets for assetsIconsBatteryDmOnPerOnchargOfflowOffpmOffstDefaultdmOn /// assets/icons/battery/dmOn/perOnchargOfflowOffpmOffstDefaultdmOn.svg - static const String - assetsIconsBatteryDmOnPerOnchargOfflowOffpmOffstDefaultdmOn = + static const String assetsIconsBatteryDmOnPerOnchargOfflowOffpmOffstDefaultdmOn = "assets/icons/battery/dmOn/perOnchargOfflowOffpmOffstDefaultdmOn.svg"; /// Assets for assetsIconsBatteryDmOnPerOnchargOfflowOffpmOnstChargeddmOn /// assets/icons/battery/dmOn/perOnchargOfflowOffpmOnstChargeddmOn.svg - static const String - assetsIconsBatteryDmOnPerOnchargOfflowOffpmOnstChargeddmOn = + static const String assetsIconsBatteryDmOnPerOnchargOfflowOffpmOnstChargeddmOn = "assets/icons/battery/dmOn/perOnchargOfflowOffpmOnstChargeddmOn.svg"; /// Assets for assetsIconsBatteryDmOnPerOnchargOfflowOnpmOffstDefaultdmOn /// assets/icons/battery/dmOn/perOnchargOfflowOnpmOffstDefaultdmOn.svg - static const String - assetsIconsBatteryDmOnPerOnchargOfflowOnpmOffstDefaultdmOn = + static const String assetsIconsBatteryDmOnPerOnchargOfflowOnpmOffstDefaultdmOn = "assets/icons/battery/dmOn/perOnchargOfflowOnpmOffstDefaultdmOn.svg"; /// Assets for assetsIconsBatteryDmOnPerOnchargOfflowOnpmOnstDefaultdmOn /// assets/icons/battery/dmOn/perOnchargOfflowOnpmOnstDefaultdmOn.svg - static const String - assetsIconsBatteryDmOnPerOnchargOfflowOnpmOnstDefaultdmOn = + static const String assetsIconsBatteryDmOnPerOnchargOfflowOnpmOnstDefaultdmOn = "assets/icons/battery/dmOn/perOnchargOfflowOnpmOnstDefaultdmOn.svg"; /// Assets for assetsIconsBatteryDmOnPerOnchargOnlowOffpmOffstChargeddmOn /// assets/icons/battery/dmOn/perOnchargOnlowOffpmOffstChargeddmOn.svg - static const String - assetsIconsBatteryDmOnPerOnchargOnlowOffpmOffstChargeddmOn = + static const String assetsIconsBatteryDmOnPerOnchargOnlowOffpmOffstChargeddmOn = "assets/icons/battery/dmOn/perOnchargOnlowOffpmOffstChargeddmOn.svg"; /// Assets for assetsIconsBatteryDmOnPerOnchargOnlowOnpmOffstlowBatterydmOn /// assets/icons/battery/dmOn/perOnchargOnlowOnpmOffstlowBatterydmOn.svg - static const String - assetsIconsBatteryDmOnPerOnchargOnlowOnpmOffstlowBatterydmOn = + static const String assetsIconsBatteryDmOnPerOnchargOnlowOnpmOffstlowBatterydmOn = "assets/icons/battery/dmOn/perOnchargOnlowOnpmOffstlowBatterydmOn.svg"; /// Assets for assetsIconsBatteryDmOnPerOnchargOnlowOnpmOnstlowpmdmOn @@ -247,7 +216,9 @@ class Assets { /// Assets for assetsIconsCurtainsIconVerticalBlade /// assets/icons/curtainsIcon/verticalBlade.svg static const String assetsIconsCurtainsIconVerticalBlade = - "assets/icons/curtainsIcon/verticalBlade.svg"; + "assets/icons/curtainsIcon/left_vertical_blade.svg"; + + static const String rightVerticalBlade = "assets/icons/curtainsIcon/right_vertical_blade.svg"; /// Assets for assetsIconsDashboard /// assets/icons/dashboard.svg @@ -257,8 +228,7 @@ class Assets { /// Assets for assetsIconsDashboardFill /// assets/icons/dashboard-fill.svg - static const String assetsIconsDashboardFill = - "assets/icons/dashboard-fill.svg"; + static const String assetsIconsDashboardFill = "assets/icons/dashboard-fill.svg"; /// Assets for assetsIconsDevices /// assets/icons/Devices.svg @@ -274,8 +244,7 @@ class Assets { /// Assets for assetsIconsDoorLockLinkage /// assets/icons/DoorLockLinkage.svg - static const String assetsIconsDoorLockLinkage = - "assets/icons/DoorLockLinkage.svg"; + static const String assetsIconsDoorLockLinkage = "assets/icons/DoorLockLinkage.svg"; /// Assets for assetsIconsDoorLockLock /// assets/icons/DoorLockLock.svg @@ -283,18 +252,15 @@ class Assets { /// Assets for assetsIconsDoorLockMembers /// assets/icons/DoorLockMembers.svg - static const String assetsIconsDoorLockMembers = - "assets/icons/DoorLockMembers.svg"; + static const String assetsIconsDoorLockMembers = "assets/icons/DoorLockMembers.svg"; /// Assets for assetsIconsDoorLockPassword /// assets/icons/DoorLockPassword.svg - static const String assetsIconsDoorLockPassword = - "assets/icons/DoorLockPassword.svg"; + static const String assetsIconsDoorLockPassword = "assets/icons/DoorLockPassword.svg"; /// Assets for assetsIconsDoorLockRecords /// assets/icons/DoorLockRecords.svg - static const String assetsIconsDoorLockRecords = - "assets/icons/DoorLockRecords.svg"; + static const String assetsIconsDoorLockRecords = "assets/icons/DoorLockRecords.svg"; /// Assets for assetsIconsDoorlockAssetsBatteryIndicator /// assets/icons/doorlock-assets/BatteryIndicator.svg @@ -315,8 +281,7 @@ class Assets { /// assets/icons/doorlock-assets/lockIcon.svg static const String assetsIconsDoorlockAssetsLockIcon = "assets/icons/doorlock-assets/lockIcon.svg"; - static const String doorUnlockIcon = - "assets/icons/doorlock-assets/door_un_look_ic.svg"; + static const String doorUnlockIcon = "assets/icons/doorlock-assets/door_un_look_ic.svg"; /// Assets for assetsIconsDoorlockAssetsMembersManagement /// assets/icons/doorlock-assets/members-management.svg @@ -404,13 +369,11 @@ class Assets { /// Assets for assetsIconsLightSwitchOff /// assets/icons/lightSwitchOff.svg - static const String assetsIconsLightSwitchOff = - "assets/icons/lightSwitchOff.svg"; + static const String assetsIconsLightSwitchOff = "assets/icons/lightSwitchOff.svg"; /// Assets for assetsIconsLightSwitchOn /// assets/icons/lightSwitchOn.svg - static const String assetsIconsLightSwitchOn = - "assets/icons/lightSwitchOn.svg"; + static const String assetsIconsLightSwitchOn = "assets/icons/lightSwitchOn.svg"; /// Assets for assetsIconsLinkageIconsDoorLockAlarm /// assets/icons/linkageIcons/doorLockAlarm.svg @@ -419,8 +382,7 @@ class Assets { /// Assets for assetsIconsLinkTimeLimitedPasswordIcon /// assets/icons/timeLimitedPasswordIcon.svg - static const String timeLimitedPasswordIcon = - "assets/icons/timeLimitedPasswordIcon.svg"; + static const String timeLimitedPasswordIcon = "assets/icons/timeLimitedPasswordIcon.svg"; /// Assets for assetsIconsoneTimePassword /// assets/icons/oneTimePassword.svg @@ -428,8 +390,7 @@ class Assets { /// Assets for assetsIconsTimeLimitedPassword /// assets/icons/timeLimitedPassword.svg - static const String timeLimitedPassword = - "assets/icons/timeLimitedPassword.svg"; + static const String timeLimitedPassword = "assets/icons/timeLimitedPassword.svg"; /// Assets for assetsIconsNoValidPasswords /// assets/icons/noValidPasswords.svg @@ -598,13 +559,11 @@ class Assets { /// Assets for assetsIconsPresenceSensorAssetsParameterSettings /// assets/icons/presence-sensor-assets/space_type_icon.svg - static const String spaceTypeIcon = - "assets/icons/presence-sensor-assets/space_type_icon.svg"; + static const String spaceTypeIcon = "assets/icons/presence-sensor-assets/space_type_icon.svg"; /// Assets for assetsIconsPresenceSensorAssetsParameterSettings /// assets/icons/presence-sensor-assets/space_type_icon.svg - static const String sensitivityIcon = - "assets/icons/presence-sensor-assets/Sensitivity.svg"; + static const String sensitivityIcon = "assets/icons/presence-sensor-assets/Sensitivity.svg"; /// Assets for assetsIconsPresenceSensorAssetsParameterSettings /// assets/icons/presence-sensor-assets/maximum_distance.svg @@ -637,8 +596,7 @@ class Assets { /// Assets for assetsIconsRoutinesFill /// assets/icons/Routines-fill.svg - static const String assetsIconsRoutinesFill = - "assets/icons/Routines-fill.svg"; + static const String assetsIconsRoutinesFill = "assets/icons/Routines-fill.svg"; /// Assets for assetsIconsScan /// assets/icons/Scan.svg @@ -670,8 +628,7 @@ class Assets { /// Assets for assetsIconsSustainability /// assets/icons/sustainability.svg - static const String assetsIconsSustainability = - "assets/icons/sustainability.svg"; + static const String assetsIconsSustainability = "assets/icons/sustainability.svg"; /// Assets for assetsIconsUnlockingMethodsIconsFace /// assets/icons/unlockingMethodsIcons/face.svg @@ -767,8 +724,7 @@ class Assets { /// Assets for assetsImagesHorizintalBlade /// assets/images/HorizintalBlade.png - static const String assetsImagesHorizintalBlade = - "assets/images/HorizintalBlade.png"; + static const String assetsImagesHorizintalBlade = "assets/images/HorizintalBlade.png"; /// Assets for assetsImagesLogo /// assets/images/Logo.svg @@ -776,8 +732,7 @@ class Assets { /// Assets for assetsImagesLogoHorizontal /// assets/images/logo_horizontal.png - static const String assetsImagesLogoHorizontal = - "assets/images/logo_horizontal.png"; + static const String assetsImagesLogoHorizontal = "assets/images/logo_horizontal.png"; /// Assets for assetsImagesPause /// assets/images/Pause.png @@ -807,8 +762,7 @@ class Assets { /// assets/images/Window.png static const String assetsImagesWindow = "assets/images/Window.png"; - static const String assetsSensitivityFunction = - "assets/icons/functions_icons/sensitivity.svg"; + static const String assetsSensitivityFunction = "assets/icons/functions_icons/sensitivity.svg"; //assets/icons/functions_icons/sesitivity_operation_icon.svg static const String assetsSensitivityOperationIcon = @@ -816,73 +770,59 @@ class Assets { //assets/icons/functions_icons/ac_power.svg - static const String assetsAcPower = - "assets/icons/functions_icons/ac_power.svg"; + static const String assetsAcPower = "assets/icons/functions_icons/ac_power.svg"; //assets/icons/functions_icons/ac_power_off.svg - static const String assetsAcPowerOFF = - "assets/icons/functions_icons/ac_power_off.svg"; + static const String assetsAcPowerOFF = "assets/icons/functions_icons/ac_power_off.svg"; //assets/icons/functions_icons/child_lock.svg - static const String assetsChildLock = - "assets/icons/functions_icons/child_lock.svg"; + static const String assetsChildLock = "assets/icons/functions_icons/child_lock.svg"; //assets/icons/functions_icons/cooling.svg - static const String assetsFreezing = - "assets/icons/functions_icons/freezing.svg"; + static const String assetsFreezing = "assets/icons/functions_icons/freezing.svg"; //assets/icons/functions_icons/fan_speed.svg - static const String assetsFanSpeed = - "assets/icons/functions_icons/fan_speed.svg"; + static const String assetsFanSpeed = "assets/icons/functions_icons/fan_speed.svg"; //assets/icons/functions_icons/ac_cooling.svg - static const String assetsAcCooling = - "assets/icons/functions_icons/ac_cooling.svg"; + static const String assetsAcCooling = "assets/icons/functions_icons/ac_cooling.svg"; //assets/icons/functions_icons/ac_heating.svg - static const String assetsAcHeating = - "assets/icons/functions_icons/ac_heating.svg"; + static const String assetsAcHeating = "assets/icons/functions_icons/ac_heating.svg"; //assets/icons/functions_icons/celsius_degrees.svg - static const String assetsCelsiusDegrees = - "assets/icons/functions_icons/celsius_degrees.svg"; + static const String assetsCelsiusDegrees = "assets/icons/functions_icons/celsius_degrees.svg"; //assets/icons/functions_icons/tempreture.svg - static const String assetsTempreture = - "assets/icons/functions_icons/tempreture.svg"; + static const String assetsTempreture = "assets/icons/functions_icons/tempreture.svg"; //assets/icons/functions_icons/ac_fan_low.svg - static const String assetsAcFanLow = - "assets/icons/functions_icons/ac_fan_low.svg"; + static const String assetsAcFanLow = "assets/icons/functions_icons/ac_fan_low.svg"; //assets/icons/functions_icons/ac_fan_middle.svg - static const String assetsAcFanMiddle = - "assets/icons/functions_icons/ac_fan_middle.svg"; + static const String assetsAcFanMiddle = "assets/icons/functions_icons/ac_fan_middle.svg"; //assets/icons/functions_icons/ac_fan_high.svg - static const String assetsAcFanHigh = - "assets/icons/functions_icons/ac_fan_high.svg"; + static const String assetsAcFanHigh = "assets/icons/functions_icons/ac_fan_high.svg"; //assets/icons/functions_icons/ac_fan_auto.svg - static const String assetsAcFanAuto = - "assets/icons/functions_icons/ac_fan_auto.svg"; + static const String assetsAcFanAuto = "assets/icons/functions_icons/ac_fan_auto.svg"; //assets/icons/functions_icons/scene_child_lock.svg - static const String assetsSceneChildLock = - "assets/icons/functions_icons/scene_child_lock.svg"; + static const String assetsSceneChildLock = "assets/icons/functions_icons/scene_child_lock.svg"; //assets/icons/functions_icons/scene_child_unlock.svg @@ -891,18 +831,15 @@ class Assets { //assets/icons/functions_icons/scene_refresh.svg - static const String assetsSceneRefresh = - "assets/icons/functions_icons/scene_refresh.svg"; + static const String assetsSceneRefresh = "assets/icons/functions_icons/scene_refresh.svg"; //assets/icons/functions_icons/light_countdown.svg - static const String assetsLightCountdown = - "assets/icons/functions_icons/light_countdown.svg"; + static const String assetsLightCountdown = "assets/icons/functions_icons/light_countdown.svg"; //assets/icons/functions_icons/far_detection.svg - static const String assetsFarDetection = - "assets/icons/functions_icons/far_detection.svg"; + static const String assetsFarDetection = "assets/icons/functions_icons/far_detection.svg"; //assets/icons/functions_icons/far_detection_function.svg @@ -911,13 +848,11 @@ class Assets { //assets/icons/functions_icons/indicator.svg - static const String assetsIndicator = - "assets/icons/functions_icons/indicator.svg"; + static const String assetsIndicator = "assets/icons/functions_icons/indicator.svg"; //assets/icons/functions_icons/motion_detection.svg - static const String assetsMotionDetection = - "assets/icons/functions_icons/motion_detection.svg"; + static const String assetsMotionDetection = "assets/icons/functions_icons/motion_detection.svg"; //assets/icons/functions_icons/motionless_detection.svg @@ -926,18 +861,15 @@ class Assets { //assets/icons/functions_icons/nobody_time.svg - static const String assetsNobodyTime = - "assets/icons/functions_icons/nobody_time.svg"; + static const String assetsNobodyTime = "assets/icons/functions_icons/nobody_time.svg"; //assets/icons/functions_icons/factory_reset.svg - static const String assetsFactoryReset = - "assets/icons/functions_icons/factory_reset.svg"; + static const String assetsFactoryReset = "assets/icons/functions_icons/factory_reset.svg"; //assets/icons/functions_icons/master_state.svg - static const String assetsMasterState = - "assets/icons/functions_icons/master_state.svg"; + static const String assetsMasterState = "assets/icons/functions_icons/master_state.svg"; //assets/icons/functions_icons/switch_alarm_sound.svg @@ -946,8 +878,7 @@ class Assets { //assets/icons/functions_icons/reset_off.svg - static const String assetsResetOff = - "assets/icons/functions_icons/reset_off.svg"; + static const String assetsResetOff = "assets/icons/functions_icons/reset_off.svg"; //assets/icons/functions_icons/automation_functions/card_unlock.svg @@ -1021,8 +952,7 @@ class Assets { //assets/icons/functions_icons/automation_functions/motion.svg - static const String assetsMotion = - "assets/icons/functions_icons/automation_functions/motion.svg"; + static const String assetsMotion = "assets/icons/functions_icons/automation_functions/motion.svg"; //assets/icons/functions_icons/automation_functions/current_temp.svg @@ -1044,19 +974,15 @@ class Assets { static const String waterHeaterOn = "assets/icons/water_heater_on.svg"; static const String waterHeaterOff = "assets/icons/water_heater_off.svg"; - static const String scheduleCelenderIcon = - "assets/icons/schedule_celender_icon.svg"; - static const String scheduleCirculateIcon = - "assets/icons/schedule_circulate_icon.svg"; - static const String scheduleInchingIcon = - "assets/icons/schedule_Inching_icon.svg"; + static const String scheduleCelenderIcon = "assets/icons/schedule_celender_icon.svg"; + static const String scheduleCirculateIcon = "assets/icons/schedule_circulate_icon.svg"; + static const String scheduleInchingIcon = "assets/icons/schedule_Inching_icon.svg"; static const String scheduleTimeIcon = "assets/icons/schedule_time_icon.svg"; static const String waterHeaterIcon = "assets/icons/water_heater_icon.svg"; static const String doorOpen = "assets/icons/opened_door.svg"; static const String doorClose = "assets/icons/closed_door.svg"; - static const String doorNotificationSetting = - "assets/icons/door_notification_setting_icon.svg"; + static const String doorNotificationSetting = "assets/icons/door_notification_setting_icon.svg"; static const String doorRecordsIcon = "assets/icons/door_records_icon.svg"; static const String doorSensorIcon = "assets/icons/door_sensor_icon.svg"; static const String closedGarageIcon = "assets/icons/closed_garage_door.svg"; diff --git a/lib/main.dart b/lib/main.dart index 1a6c5a6..4f1f904 100644 --- a/lib/main.dart +++ b/lib/main.dart @@ -30,7 +30,7 @@ void main() { // }); //to initialize the locator - initialSetup(envName: 'prod'); + initialSetup(); await Firebase.initializeApp( options: DefaultFirebaseOptionsStaging.currentPlatform, diff --git a/lib/main_dev.dart b/lib/main_dev.dart index 9e53a7e..5f13c0a 100644 --- a/lib/main_dev.dart +++ b/lib/main_dev.dart @@ -30,7 +30,7 @@ void main() { // }); //to initialize the locator - initialSetup(envName: 'dev'); + initialSetup(); await Firebase.initializeApp( options: DefaultFirebaseOptionsDev.currentPlatform, diff --git a/lib/services/locator.dart b/lib/services/locator.dart index 97a9ae8..0fef6d7 100644 --- a/lib/services/locator.dart +++ b/lib/services/locator.dart @@ -5,9 +5,8 @@ import 'package:syncrow_app/services/api/http_service.dart'; final GetIt serviceLocator = GetIt.instance; // setupLocator() // to search for dependency injection in flutter -initialSetup({required String envName}) { +initialSetup() { serviceLocator.registerSingleton(HTTPInterceptor()); //Base classes serviceLocator.registerSingleton(HTTPService.setupDioClient()); - serviceLocator.registerSingleton(envName); } From 3454f0e28d3150878df2ea4063d23f6fe2cad442 Mon Sep 17 00:00:00 2001 From: Abdullah Alassaf Date: Mon, 7 Oct 2024 01:40:16 +0300 Subject: [PATCH 5/8] Updated the curtain design --- assets/images/Window.png | Bin 3246 -> 0 bytes assets/images/window_img.svg | 25 +++ .../devices/model/device_category_model.dart | 5 +- .../widgets/curtains/curtain_buttons.dart | 9 +- .../view/widgets/curtains/curtain_view.dart | 212 +++++++++--------- lib/generated/assets.dart | 5 +- 6 files changed, 144 insertions(+), 112 deletions(-) delete mode 100644 assets/images/Window.png create mode 100644 assets/images/window_img.svg diff --git a/assets/images/Window.png b/assets/images/Window.png deleted file mode 100644 index be38a0b74fff0b30c38ee915845d3ca7c130a088..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 3246 zcma)92~d;Q7EZ(L|GICWKj{qzCBqCA&X%v5D=vgts6xUM2Mh( zP(s)wgb>179|8?a0z?Q&qyl04K>>+Kz!$2mMQz{vXYQQ2XU^Pv&+>ie{6C(tHCL2Z zkq3c5ik22;b|4TKE?v%YvQo`L--WGGu^MmT90UTb*|@a8p!?}dN^p>!`7uyo>$VZ; zW~INWjVTCJ62C^`4FQ1^j$4|U+J6rQ_+z0Qq>AhdAU#uGaYy>xp`g{wB>F24nQ8L2 zH9LGS%I#1tM?Cy#Pr0vUvSjKA+Bac)xK%R16?S)fPw{XyM~x7Oc}MUwdpiLvFTP|>bk^YLQA*7OH-qwy*V<}pU|{g=q=30!JZZeo)zuZ^rPgT@`TDoH z8Q~bWC`C!b$ol;ym&Xe;oLi_ohqebtNwR9S&$|jDrUt|WBGC;itUiYo^u0F(&>Ce( zoCxgbU+A!{)~U;c{M5eiicR<;H_yioG^MzAoVa~ zSOdX@!C=j?tCX6_jz!J={hs}^n4ec^XWzG?zN!obBIse00{tgiL4(igq~DAw_2Km5 zxWg?_LA~^m%^e*bGtX|j($@O5BJ?P;VsY+6q`Agu^kEsr+I6EA7l62KFEU*p`aGYW z)#xiZH(7QDGZ5rXpT72M@4hxYcxucxozKnVs1W`xdmIoe47AfHm3GFZ)SIYHxD)Zp2DzTbti)YtK9`ntV766XY#^ep&Hth|&Gx;2Q6N5OJ z{&4#X#piL%L;J94}T+?l;usJaf?Lq$8boZtlFAi zy&2ou?R_9R8&i@m>K!Efr??e8rLJ5}P;EH5A@I_CLiyAD2V?mY;GUci26tfh@{le) zqV)_&^XGqf+FxxNJp7120GzwCO{Wvx<3ktVFnN6{uTQr8xt04YNEY6benf-tqWbXd zwoXUsT@gAnB3Ig`Ka#pU3?Fv`3Xtu0n*U7v|6w!SSUXSZOH#g;P53-f2FJl)(SAxM zyI1{}NaVJa3T_z8et4biua8{iKUK%?wc-+s*VB^MhqLkM4HptObM~%jrCFr8ms5u& ziOL+U`N)pYtL!1Fn_o3~2veF48|xf6%IQM)bcuY|H&o}wF>xsWx}7gJzh5#e#e%s$ z0u7xPaeDb_x?JP7Q;{~kBLS)8fG`i9&0`X7(E&$>0mS*|;edW>bWgdnp8aLpZ zrX~3mEohDrOZd*fP1dk&&FE;Px5ArK8N!Q+YjYJ#D7|GIM;l|5HpLS0WQdeIVt6PV zU_?YmRk!i9T|W2f6A-eg%&YbBzbt4vnIEt5cfg`eicNz)0q@KBe_1p7QeR|(PYiwl zRwLc?CzvA!JM}!I!mzAa@k-h1^gZ#UVExk>UsQL~!|f*7-luCe;H(Hr5%Vudr3vVlEe_Qkm0`)db2~6xN}b zUZQCBO%$JNNTrvvo`$C|k!@9T^OdvhK250UArkf1a1PIncEO>@H&J@IL5hurpq3lN z2-tZ*6>lQ~rb?oyjO$8IpUydM!uuz#Nrd#}ES8XloCyf`zMjKjqL)=7y})N9$-3zm ziFNV9{PJ^Y_y6^SG`LIQ{0mDg&)vY8b$fTd5W^b=hQA&LC%HhViHDd`>B(aOH5>7qyOU@kGW#oAL!LOeH7Owc|l3O-;H)gFa~dM=)gvCc3eC6NG< zZjxy|=6ukTKpZY5D=TZoK(9c(Fj~c@N!qMA8Zp(+MSp3#CfR~jn{ErX-4#y?w#1Bb znsQ6!nOAuXvF8UIPu~;KYwe1S~KnX66SZaD-Z&HE@90sc#d8DO=y>#n(^gR#u zfPjyHWbSWlY~2;}IbQw(use^hP$ykgQPcWgDWP(iPbfX5eC2?;}3Xe9KqzcC- z`RcEwNoT-hZjqR@u$z@AnR$9x5K6m`Ik+ zc=mxN(14DaSN&O2qg`awguRUnwjWRKa$z2LTl%ehduLsp=Lvhoib_O5=(#Ni^M~SG zkM5%-$7vW5?;+8Vk&zHDhX7Lt8Omm-#>Se{jDj2EYtxi3hm<{<=p_H>thy<%c3r@1 zCpO^Ccn=2!V+HwENN3qw_S6pPsJSKP;rRHt^^Jo3&F)mVK}$|Q(%cMP++~OF*sv}W zcj!i|-p_uW1-#hBoz$DxR-6x2$A@UREf^pW%;2A<8F)QS`GQ!N;I0G?i$y`1B3Buq zb!I8jL2rP(`@#CNUZl=r1^Gp@My%YP~147_1Y$@P_+-QR$mVtvfqevFD_}7a+?Mwq}LLysrEg1@agF diff --git a/assets/images/window_img.svg b/assets/images/window_img.svg new file mode 100644 index 0000000..d908db4 --- /dev/null +++ b/assets/images/window_img.svg @@ -0,0 +1,25 @@ + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/lib/features/devices/model/device_category_model.dart b/lib/features/devices/model/device_category_model.dart index 8ef4334..ccd2e0f 100644 --- a/lib/features/devices/model/device_category_model.dart +++ b/lib/features/devices/model/device_category_model.dart @@ -42,9 +42,7 @@ class DevicesCategoryModel { : name = json['groupName'], // id = json['groupId'], type = devicesTypesMap[json['groupName']] ?? DeviceType.Other, - icon = deviceTypeIconMap[ - devicesTypesMap[json['groupName']] ?? DeviceType.Other] ?? - '', + icon = deviceTypeIconMap[devicesTypesMap[json['groupName']] ?? DeviceType.Other] ?? '', devices = [], isSelected = false; @@ -70,4 +68,5 @@ Map deviceTypeIconMap = { DeviceType.OneTouch: Assets.oneGang, DeviceType.TowTouch: Assets.twoGang, DeviceType.ThreeTouch: Assets.assetsIconsGang, + DeviceType.GarageDoor: Assets.garageIcon }; diff --git a/lib/features/devices/view/widgets/curtains/curtain_buttons.dart b/lib/features/devices/view/widgets/curtains/curtain_buttons.dart index d1e0a06..91b919b 100644 --- a/lib/features/devices/view/widgets/curtains/curtain_buttons.dart +++ b/lib/features/devices/view/widgets/curtains/curtain_buttons.dart @@ -1,4 +1,3 @@ - import 'package:flutter/material.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; import 'package:flutter_svg/flutter_svg.dart'; @@ -17,8 +16,8 @@ class CurtainButtons extends StatelessWidget { mainAxisAlignment: MainAxisAlignment.spaceEvenly, children: [ _buildButton( - onTap: () => context.read().add(OpenCurtain(curtain.productType!)), - iconPath: Assets.assetsIconsCurtainsIconOpenCurtain, + onTap: () => context.read().add(CloseCurtain(curtain.productType!)), + iconPath: Assets.assetsIconsCurtainsIconCloseCurtain, ), _buildButton( onTap: () => context.read().add(PauseCurtain()), @@ -26,8 +25,8 @@ class CurtainButtons extends StatelessWidget { isSvg: false, ), _buildButton( - onTap: () => context.read().add(CloseCurtain(curtain.productType!)), - iconPath: Assets.assetsIconsCurtainsIconCloseCurtain, + onTap: () => context.read().add(OpenCurtain(curtain.productType!)), + iconPath: Assets.assetsIconsCurtainsIconOpenCurtain, ), ], ); diff --git a/lib/features/devices/view/widgets/curtains/curtain_view.dart b/lib/features/devices/view/widgets/curtains/curtain_view.dart index acfb141..7c0e4d0 100644 --- a/lib/features/devices/view/widgets/curtains/curtain_view.dart +++ b/lib/features/devices/view/widgets/curtains/curtain_view.dart @@ -6,6 +6,7 @@ import 'package:syncrow_app/features/devices/bloc/curtain_bloc/curtain_event.dar import 'package:syncrow_app/features/devices/bloc/curtain_bloc/curtain_state.dart'; import 'package:syncrow_app/features/devices/model/device_model.dart'; import 'package:syncrow_app/features/devices/view/widgets/curtains/curtain_buttons.dart'; +import 'package:syncrow_app/features/shared_widgets/default_container.dart'; import 'package:syncrow_app/features/shared_widgets/default_scaffold.dart'; import 'package:syncrow_app/generated/assets.dart'; @@ -19,7 +20,7 @@ class CurtainView extends StatelessWidget { create: (context) => CurtainBloc(curtain.uuid!)..add(InitCurtain()), child: BlocBuilder( builder: (context, state) { - double curtainWidth = 270; + double curtainWidth = MediaQuery.sizeOf(context).width * 0.6; // double blindHeight = 310; if (state is CurtainsOpening) { curtainWidth = state.curtainWidth; @@ -33,109 +34,118 @@ class CurtainView extends StatelessWidget { } return DefaultScaffold( title: curtain.name, - child: Column( - children: [ - Stack( - alignment: Alignment.center, - children: [ - Container( - height: MediaQuery.sizeOf(context).height * 0.5, - width: MediaQuery.sizeOf(context).width, - decoration: const BoxDecoration( - image: DecorationImage( - image: AssetImage( - Assets.assetsImagesWindow, - ), + child: state is CurtainLoadingState + ? const Center( + child: + DefaultContainer(width: 50, height: 50, child: CircularProgressIndicator()), + ) + : RefreshIndicator( + onRefresh: () async { + BlocProvider.of(context).add(InitCurtain()); + }, + child: ListView( + children: [ + const SizedBox( + height: 40, ), - ), - ), - Container( - padding: const EdgeInsets.only(top: 40), - child: Column( - children: [ - SvgPicture.asset( - Assets.assetsIconsCurtainsIconCurtainHolder, - width: MediaQuery.sizeOf(context).width * 0.8, - ), - SizedBox( - width: MediaQuery.sizeOf(context).width * 0.8, - child: Row( - mainAxisAlignment: MainAxisAlignment.spaceBetween, - children: [ - Container( - padding: const EdgeInsets.only(bottom: 40, left: 8), - child: AnimatedContainer( - duration: const Duration(milliseconds: 200), - curve: Curves.linear, - height: MediaQuery.sizeOf(context).height * 0.4, - width: curtainWidth / 2, - child: Stack( - children: List.generate( - 4, - (index) { - double spacing = curtainWidth / 8; - double leftMostPosition = index * spacing; - return AnimatedPositioned( - duration: const Duration(milliseconds: 200), - curve: Curves.linear, - left: leftMostPosition, - child: SizedBox( - height: MediaQuery.sizeOf(context).height * 0.37, - width: 32, - child: SvgPicture.asset( - Assets.assetsIconsCurtainsIconVerticalBlade, - fit: BoxFit.fill, - ), - ), - ); - }, - ), - ), - ), - ), - Container( - padding: const EdgeInsets.only(bottom: 40, right: 8), - child: AnimatedContainer( - duration: const Duration(milliseconds: 200), - curve: Curves.linear, - height: MediaQuery.sizeOf(context).height * 0.4, - width: curtainWidth / 2, - child: Stack( - children: List.generate( - 4, - (index) { - double spacing = curtainWidth / 8; - double rightMostPosition = index * spacing; - return AnimatedPositioned( - duration: const Duration(milliseconds: 200), - curve: Curves.linear, - right: rightMostPosition, - child: SizedBox( - height: MediaQuery.sizeOf(context).height * 0.37, - width: 32, - child: SvgPicture.asset( - Assets.rightVerticalBlade, - fit: BoxFit.fill, - ), - ), - ); - }, - ), - ), - ), - ), - ], + Stack( + alignment: Alignment.center, + children: [ + SvgPicture.asset( + Assets.assetsImagesWindow, + width: MediaQuery.sizeOf(context).width * 0.85, + height: MediaQuery.sizeOf(context).height * 0.4, ), - ), - ], - ), + SizedBox( + height: MediaQuery.sizeOf(context).height * 0.4, + child: Column( + children: [ + SvgPicture.asset( + Assets.assetsIconsCurtainsIconCurtainHolder, + width: MediaQuery.sizeOf(context).width * 0.75, + ), + SizedBox( + width: MediaQuery.sizeOf(context).width * 0.75, + child: Row( + mainAxisAlignment: MainAxisAlignment.spaceBetween, + children: [ + SizedBox( + width: MediaQuery.sizeOf(context).width * 0.025, + ), + AnimatedContainer( + duration: const Duration(milliseconds: 200), + curve: Curves.linear, + height: MediaQuery.sizeOf(context).height * 0.35, + width: MediaQuery.sizeOf(context).width * 0.35, + child: Stack( + children: List.generate( + 4, + (index) { + double spacing = curtainWidth / 7.5; + double leftMostPosition = index * spacing; + return AnimatedPositioned( + duration: const Duration(milliseconds: 200), + curve: Curves.linear, + left: leftMostPosition, + child: SizedBox( + height: + MediaQuery.sizeOf(context).height * 0.35, + width: MediaQuery.sizeOf(context).width * 0.08, + child: SvgPicture.asset( + Assets.assetsIconsCurtainsIconVerticalBlade, + fit: BoxFit.fill, + ), + ), + ); + }, + ), + ), + ), + AnimatedContainer( + duration: const Duration(milliseconds: 200), + curve: Curves.linear, + height: MediaQuery.sizeOf(context).height * 0.35, + width: MediaQuery.sizeOf(context).width * 0.35, + child: Stack( + children: List.generate( + 4, + (index) { + double spacing = curtainWidth / 7.5; + double rightMostPosition = index * spacing; + return AnimatedPositioned( + duration: const Duration(milliseconds: 200), + curve: Curves.linear, + right: rightMostPosition, + child: SizedBox( + height: + MediaQuery.sizeOf(context).height * 0.35, + width: MediaQuery.sizeOf(context).width * 0.08, + child: SvgPicture.asset( + Assets.rightVerticalBlade, + fit: BoxFit.fill, + ), + ), + ); + }, + ), + ), + ), + SizedBox( + width: MediaQuery.sizeOf(context).width * 0.025, + ), + ], + ), + ), + ], + ), + ), + ], + ), + const SizedBox(height: 80), + CurtainButtons(curtain: curtain), + ], ), - ], - ), - const SizedBox(height: 80), - CurtainButtons(curtain: curtain), - ], - ), + ), ); }, ), diff --git a/lib/generated/assets.dart b/lib/generated/assets.dart index cb89189..68575b6 100644 --- a/lib/generated/assets.dart +++ b/lib/generated/assets.dart @@ -760,7 +760,7 @@ class Assets { /// Assets for assetsImagesWindow /// assets/images/Window.png - static const String assetsImagesWindow = "assets/images/Window.png"; + static const String assetsImagesWindow = "assets/images/window_img.svg"; static const String assetsSensitivityFunction = "assets/icons/functions_icons/sensitivity.svg"; @@ -991,6 +991,5 @@ class Assets { static const String garagePreferencesIcon = "assets/icons/garage_preferences_icon.svg"; static const String garageSchedule = "assets/icons/garage_schedule.svg"; - static const String garageIcon = "assets/icons/garageIcon.svg"; - + static const String garageIcon = "assets/icons/garageIcon.svg"; } From 208fbd63f34789d6abc2170d4649076ba35e8d15 Mon Sep 17 00:00:00 2001 From: mohammad Date: Mon, 7 Oct 2024 10:26:08 +0300 Subject: [PATCH 6/8] garage door wizard --- .../garage_door_bloc/garage_door_bloc.dart | 216 ++++++++++++++++-- .../garage_door_bloc/garage_door_event.dart | 13 ++ .../garage_door_bloc/garage_door_state.dart | 12 + .../devices/model/group_garage_model.dart | 11 + .../view/widgets/curtains/curtain_view.dart | 3 +- .../view/widgets/garage_door/garage_list.dart | 70 ++++++ .../widgets/garage_door/garage_wizard.dart | 50 ++++ .../devices/view/widgets/wizard_page.dart | 9 + 8 files changed, 361 insertions(+), 23 deletions(-) create mode 100644 lib/features/devices/model/group_garage_model.dart create mode 100644 lib/features/devices/view/widgets/garage_door/garage_list.dart create mode 100644 lib/features/devices/view/widgets/garage_door/garage_wizard.dart diff --git a/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart b/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart index a8cb8a4..ae11720 100644 --- a/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart +++ b/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart @@ -2,11 +2,14 @@ import 'dart:async'; import 'package:dio/dio.dart'; import 'package:firebase_database/firebase_database.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:syncrow_app/features/app_layout/bloc/home_cubit.dart'; import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_event.dart'; import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_state.dart'; import 'package:syncrow_app/features/devices/model/device_control_model.dart'; +import 'package:syncrow_app/features/devices/model/device_model.dart'; import 'package:syncrow_app/features/devices/model/device_report_model.dart'; import 'package:syncrow_app/features/devices/model/garage_door_model.dart'; +import 'package:syncrow_app/features/devices/model/group_garage_model.dart'; import 'package:syncrow_app/features/devices/model/schedule_model.dart'; import 'package:syncrow_app/features/devices/model/status_model.dart'; import 'package:syncrow_app/services/api/devices_api.dart'; @@ -32,6 +35,10 @@ class GarageDoorBloc extends Bloc { on(_getCounterValue); on(_setCounterValue); on(_onTickTimer); + on(_fetchWizardStatus); + on(_groupAllOn); + on(_groupAllOff); + on(_changeFirstWizardSwitch); } void _onClose(OnClose event, Emitter emit) { _timer?.cancel(); @@ -54,7 +61,8 @@ class GarageDoorBloc extends Bloc { batteryPercentage: 0, ); - void _fetchStatus(GarageDoorInitial event, Emitter emit) async { + void _fetchStatus( + GarageDoorInitial event, Emitter emit) async { emit(GarageDoorLoadingState()); try { var response = await DevicesAPI.getDeviceStatus(GDId); @@ -76,8 +84,8 @@ class GarageDoorBloc extends Bloc { } } - void _toggleClosingReminder( - ToggleClosingReminderEvent event, Emitter emit) async { + void _toggleClosingReminder(ToggleClosingReminderEvent event, + Emitter emit) async { emit(LoadingNewSate(doorSensor: deviceStatus)); try { closingReminder = event.isClosingReminderEnabled; @@ -95,7 +103,8 @@ class GarageDoorBloc extends Bloc { } } - void _toggleDoorAlarm(ToggleDoorAlarmEvent event, Emitter emit) async { + void _toggleDoorAlarm( + ToggleDoorAlarmEvent event, Emitter emit) async { emit(LoadingNewSate(doorSensor: deviceStatus)); try { doorAlarm = event.isDoorAlarmEnabled; @@ -113,7 +122,8 @@ class GarageDoorBloc extends Bloc { } } - DeviceReport recordGroups = DeviceReport(startTime: '0', endTime: '0', data: []); + DeviceReport recordGroups = + DeviceReport(startTime: '0', endTime: '0', data: []); Future fetchLogsForLastMonth( ReportLogsInitial event, Emitter emit) async { @@ -141,14 +151,16 @@ class GarageDoorBloc extends Bloc { _listenToChanges() { try { - DatabaseReference ref = FirebaseDatabase.instance.ref('device-status/$GDId'); + DatabaseReference ref = + FirebaseDatabase.instance.ref('device-status/$GDId'); Stream stream = ref.onValue; stream.listen((DatabaseEvent event) async { if (_timer != null) { await Future.delayed(const Duration(seconds: 2)); } - Map usersMap = event.snapshot.value as Map; + Map usersMap = + event.snapshot.value as Map; List statusList = []; usersMap['status'].forEach((element) { statusList.add(StatusModel(code: element['code'], value: true)); @@ -222,7 +234,8 @@ class GarageDoorBloc extends Bloc { deviceId: GDId, ); List jsonData = response; - listSchedule = jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); + listSchedule = + jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); } on DioException catch (e) { final errorData = e.response!.data; String errorMessage = errorData['message']; @@ -232,12 +245,13 @@ class GarageDoorBloc extends Bloc { int? getTimeStampWithoutSeconds(DateTime? dateTime) { if (dateTime == null) return null; - DateTime dateTimeWithoutSeconds = - DateTime(dateTime.year, dateTime.month, dateTime.day, dateTime.hour, dateTime.minute); + DateTime dateTimeWithoutSeconds = DateTime(dateTime.year, dateTime.month, + dateTime.day, dateTime.hour, dateTime.minute); return dateTimeWithoutSeconds.millisecondsSinceEpoch ~/ 1000; } - Future toggleChange(ToggleScheduleEvent event, Emitter emit) async { + Future toggleChange( + ToggleScheduleEvent event, Emitter emit) async { try { emit(GarageDoorLoadingState()); final response = await DevicesAPI.changeSchedule( @@ -255,7 +269,8 @@ class GarageDoorBloc extends Bloc { } } - Future deleteSchedule(DeleteScheduleEvent event, Emitter emit) async { + Future deleteSchedule( + DeleteScheduleEvent event, Emitter emit) async { try { emit(GarageDoorLoadingState()); final response = await DevicesAPI.deleteSchedule( @@ -274,13 +289,15 @@ class GarageDoorBloc extends Bloc { } } - void toggleSelectedIndex(ToggleSelectedEvent event, Emitter emit) { + void toggleSelectedIndex( + ToggleSelectedEvent event, Emitter emit) { emit(GarageDoorLoadingState()); selectedTabIndex = event.index; emit(ChangeSlidingSegmentState(value: selectedTabIndex)); } - void toggleCreateSchedule(ToggleCreateScheduleEvent event, Emitter emit) { + void toggleCreateSchedule( + ToggleCreateScheduleEvent event, Emitter emit) { emit(GarageDoorLoadingState()); createSchedule = !createSchedule; selectedDays.clear(); @@ -297,13 +314,16 @@ class GarageDoorBloc extends Bloc { int secondSelected = 0; bool toggleDoor = false; - Future selectSeconds(SelectSecondsEvent event, Emitter emit) async { + Future selectSeconds( + SelectSecondsEvent event, Emitter emit) async { try { emit(GarageDoorLoadingState()); secondSelected = event.seconds; await DevicesAPI.controlDevice( - DeviceControlModel(deviceId: GDId, code: 'tr_timecon', value: secondSelected), GDId); + DeviceControlModel( + deviceId: GDId, code: 'tr_timecon', value: secondSelected), + GDId); emit(UpdateState(garageSensor: deviceStatus)); } on DioException catch (e) { final errorData = e.response!.data; @@ -312,12 +332,15 @@ class GarageDoorBloc extends Bloc { } } - openCloseGarageDoor(ToggleDoorEvent event, Emitter emit) async { + openCloseGarageDoor( + ToggleDoorEvent event, Emitter emit) async { emit(GarageDoorLoadingState()); try { toggleDoor = !event.toggle; await DevicesAPI.controlDevice( - DeviceControlModel(deviceId: GDId, code: 'switch_1', value: toggleDoor), GDId); + DeviceControlModel( + deviceId: GDId, code: 'switch_1', value: toggleDoor), + GDId); add(const GarageDoorInitial()); emit(UpdateState(garageSensor: deviceStatus)); } on DioException catch (e) { @@ -327,13 +350,16 @@ class GarageDoorBloc extends Bloc { } } - void _setCounterValue(SetCounterValue event, Emitter emit) async { + void _setCounterValue( + SetCounterValue event, Emitter emit) async { emit(LoadingNewSate(doorSensor: deviceStatus)); int seconds = 0; try { seconds = event.duration.inSeconds; final response = await DevicesAPI.controlDevice( - DeviceControlModel(deviceId: GDId, code: 'countdown_1', value: seconds), GDId); + DeviceControlModel( + deviceId: GDId, code: 'countdown_1', value: seconds), + GDId); if (response['success'] ?? false) { deviceStatus.countdown1 = seconds; @@ -353,7 +379,8 @@ class GarageDoorBloc extends Bloc { } } - void _getCounterValue(GetCounterEvent event, Emitter emit) async { + void _getCounterValue( + GetCounterEvent event, Emitter emit) async { emit(LoadingInitialState()); try { var response = await DevicesAPI.getDeviceStatus(GDId); @@ -388,4 +415,151 @@ class GarageDoorBloc extends Bloc { emit(TimerRunComplete()); } } + + bool oneGangGroup = false; + List devicesList = []; + List groupOneGangList = []; + bool allSwitchesOn = true; + + void _fetchWizardStatus( + InitialWizardEvent event, Emitter emit) async { + emit(LoadingInitialState()); + try { + devicesList = []; + groupOneGangList = []; + allSwitchesOn = true; + devicesList = await DevicesAPI.getDeviceByGroupName( + HomeCubit.getInstance().selectedSpace?.id ?? '', 'GD'); + + for (int i = 0; i < devicesList.length; i++) { + var response = + await DevicesAPI.getDeviceStatus(devicesList[i].uuid ?? ''); + List statusModelList = []; + for (var status in response['status']) { + statusModelList.add(StatusModel.fromJson(status)); + } + deviceStatus = GarageDoorModel.fromJson(statusModelList); + groupOneGangList.add(GroupGarageModel( + deviceId: devicesList[i].uuid ?? '', + deviceName: devicesList[i].name ?? '', + firstSwitch: deviceStatus.switch1, + )); + } + + if (groupOneGangList.isNotEmpty) { + groupOneGangList.firstWhere((element) { + if (!element.firstSwitch) { + allSwitchesOn = false; + } + return true; + }); + } + emit(UpdateGroupState( + oneGangList: groupOneGangList, allSwitches: allSwitchesOn)); + } catch (e) { + emit(GarageDoorFailedState(errorMessage: e.toString())); + + return; + } + } + + void _groupAllOn( + GroupAllOnEvent event, Emitter emit) async { + emit(LoadingNewSate(doorSensor: deviceStatus)); + try { + // Set all switches (firstSwitch and secondSwitch) based on the event value (on/off) + for (int i = 0; i < groupOneGangList.length; i++) { + groupOneGangList[i].firstSwitch = true; + } + + // Emit the state with updated values + emit(UpdateGroupState(oneGangList: groupOneGangList, allSwitches: true)); + + // Get a list of all device IDs + List allDeviceIds = + groupOneGangList.map((device) => device.deviceId).toList(); + + // First call for switch_1 + final response = await DevicesAPI.deviceBatchController( + code: 'switch_1', // Controls first switch for all devices + devicesUuid: allDeviceIds, + value: true, // true (on) or false (off) depending on the event value + ); + // Check if either response is unsuccessful, then reset to initial state + if (response['failedResults'].toString() != '[]') { + await Future.delayed(const Duration(milliseconds: 500)); + add(const InitialEvent(groupScreen: true)); + } + } catch (_) { + // In case of an error, delay and reset the screen to initial state + await Future.delayed(const Duration(milliseconds: 500)); + add(const InitialEvent(groupScreen: true)); + } + } + + void _groupAllOff( + GroupAllOffEvent event, Emitter emit) async { + emit(LoadingNewSate(doorSensor: deviceStatus)); + try { + // Set all switches (firstSwitch and secondSwitch) based on the event value (on/off) + for (int i = 0; i < groupOneGangList.length; i++) { + groupOneGangList[i].firstSwitch = false; + } + + // Emit the state with updated values + emit(UpdateGroupState(oneGangList: groupOneGangList, allSwitches: false)); + + // Get a list of all device IDs + List allDeviceIds = + groupOneGangList.map((device) => device.deviceId).toList(); + + // First call for switch_1 + final response = await DevicesAPI.deviceBatchController( + code: 'switch_1', // Controls first switch for all devices + devicesUuid: allDeviceIds, + value: false, // true (on) or false (off) depending on the event value + ); + + // Check if either response is unsuccessful, then reset to initial state + if (response['failedResults'].toString() != '[]') { + await Future.delayed(const Duration(milliseconds: 500)); + add(const InitialEvent(groupScreen: true)); + } + } catch (_) { + // In case of an error, delay and reset the screen to initial state + await Future.delayed(const Duration(milliseconds: 500)); + add(const InitialEvent(groupScreen: true)); + } + } + + void _changeFirstWizardSwitch(ChangeFirstWizardSwitchStatusEvent event, + Emitter emit) async { + emit(LoadingNewSate(doorSensor: deviceStatus)); + try { + bool allSwitchesValue = true; + groupOneGangList.forEach((element) { + if (element.deviceId == event.deviceId) { + element.firstSwitch = !event.value; + } + if (!element.firstSwitch) { + allSwitchesValue = false; + } + }); + + emit(UpdateGroupState( + oneGangList: groupOneGangList, allSwitches: allSwitchesValue)); + + final response = await DevicesAPI.deviceBatchController( + code: 'switch_1', + devicesUuid: [event.deviceId], + value: !event.value, + ); + + if (response['failedResults'].toString() != '[]') { + add(InitialEvent(groupScreen: oneGangGroup)); + } + } catch (_) { + add(InitialEvent(groupScreen: oneGangGroup)); + } + } } diff --git a/lib/features/devices/bloc/garage_door_bloc/garage_door_event.dart b/lib/features/devices/bloc/garage_door_bloc/garage_door_event.dart index 17ee34a..7114ce3 100644 --- a/lib/features/devices/bloc/garage_door_bloc/garage_door_event.dart +++ b/lib/features/devices/bloc/garage_door_bloc/garage_door_event.dart @@ -160,3 +160,16 @@ class ToggleDoorEvent extends GarageDoorEvent { @override List get props => [toggle]; } + +class InitialWizardEvent extends GarageDoorEvent {} + +class GroupAllOnEvent extends GarageDoorEvent {} + +class GroupAllOffEvent extends GarageDoorEvent {} + +class InitialEvent extends GarageDoorEvent { + final bool groupScreen; + const InitialEvent({required this.groupScreen}); + @override + List get props => [groupScreen]; +} diff --git a/lib/features/devices/bloc/garage_door_bloc/garage_door_state.dart b/lib/features/devices/bloc/garage_door_bloc/garage_door_state.dart index 4cb4e6a..86f3f5e 100644 --- a/lib/features/devices/bloc/garage_door_bloc/garage_door_state.dart +++ b/lib/features/devices/bloc/garage_door_bloc/garage_door_state.dart @@ -1,5 +1,6 @@ import 'package:equatable/equatable.dart'; import 'package:syncrow_app/features/devices/model/garage_door_model.dart'; +import 'package:syncrow_app/features/devices/model/group_garage_model.dart'; class GarageDoorSensorState extends Equatable { const GarageDoorSensorState(); @@ -80,3 +81,14 @@ class UpdateCreateScheduleState extends GarageDoorSensorState { final bool createSchedule; UpdateCreateScheduleState(this.createSchedule); } + +class UpdateGroupState extends GarageDoorSensorState { + final List oneGangList; + final bool allSwitches; + + const UpdateGroupState( + {required this.oneGangList, required this.allSwitches}); + + @override + List get props => [oneGangList, allSwitches]; +} diff --git a/lib/features/devices/model/group_garage_model.dart b/lib/features/devices/model/group_garage_model.dart new file mode 100644 index 0000000..e4012ec --- /dev/null +++ b/lib/features/devices/model/group_garage_model.dart @@ -0,0 +1,11 @@ +class GroupGarageModel { + final String deviceId; + final String deviceName; + bool firstSwitch; + + GroupGarageModel({ + required this.deviceId, + required this.deviceName, + required this.firstSwitch, + }); +} diff --git a/lib/features/devices/view/widgets/curtains/curtain_view.dart b/lib/features/devices/view/widgets/curtains/curtain_view.dart index 7c0e4d0..6965008 100644 --- a/lib/features/devices/view/widgets/curtains/curtain_view.dart +++ b/lib/features/devices/view/widgets/curtains/curtain_view.dart @@ -117,8 +117,7 @@ class CurtainView extends StatelessWidget { curve: Curves.linear, right: rightMostPosition, child: SizedBox( - height: - MediaQuery.sizeOf(context).height * 0.35, + height: MediaQuery.sizeOf(context).height * 0.35, width: MediaQuery.sizeOf(context).width * 0.08, child: SvgPicture.asset( Assets.rightVerticalBlade, diff --git a/lib/features/devices/view/widgets/garage_door/garage_list.dart b/lib/features/devices/view/widgets/garage_door/garage_list.dart new file mode 100644 index 0000000..b3d3f81 --- /dev/null +++ b/lib/features/devices/view/widgets/garage_door/garage_list.dart @@ -0,0 +1,70 @@ +import 'package:flutter/material.dart'; +import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_event.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_state.dart'; +import 'package:syncrow_app/features/devices/model/group_garage_model.dart'; +import 'package:syncrow_app/features/shared_widgets/devices_default_switch.dart'; +import 'package:syncrow_app/features/shared_widgets/text_widgets/body_small.dart'; + +class GarageList extends StatelessWidget { + const GarageList( + {super.key, required this.garageList, required this.allSwitches}); + + final List garageList; + final bool allSwitches; + + @override + Widget build(BuildContext context) { + return BlocBuilder( + builder: (context, state) { + return SingleChildScrollView( + child: Column( + crossAxisAlignment: CrossAxisAlignment.stretch, + children: [ + const SizedBox(height: 10), + const BodySmall(text: 'All Lights'), + const SizedBox(height: 5), + DevicesDefaultSwitch( + switchValue: allSwitches, + action: () { + BlocProvider.of(context) + .add(GroupAllOnEvent()); + }, + secondAction: () { + BlocProvider.of(context) + .add(GroupAllOffEvent()); + }, + ), + ListView.builder( + shrinkWrap: true, + physics: const NeverScrollableScrollPhysics(), + padding: const EdgeInsets.all(0), + itemCount: garageList.length, + itemBuilder: (context, index) { + return Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + const SizedBox(height: 10), + BodySmall(text: garageList[index].deviceName), + const SizedBox(height: 5), + DevicesDefaultSwitch( + switchValue: garageList[index].firstSwitch, + action: () { + BlocProvider.of(context).add( + ChangeFirstWizardSwitchStatusEvent( + value: garageList[index].firstSwitch, + deviceId: garageList[index].deviceId)); + }, + ), + ], + ); + }, + ), + ], + ), + ); + }, + ); + } +} diff --git a/lib/features/devices/view/widgets/garage_door/garage_wizard.dart b/lib/features/devices/view/widgets/garage_door/garage_wizard.dart new file mode 100644 index 0000000..e143dab --- /dev/null +++ b/lib/features/devices/view/widgets/garage_door/garage_wizard.dart @@ -0,0 +1,50 @@ +import 'package:flutter/material.dart'; +import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_event.dart'; +import 'package:syncrow_app/features/devices/bloc/garage_door_bloc/garage_door_state.dart'; +import 'package:syncrow_app/features/devices/model/device_model.dart'; +import 'package:syncrow_app/features/devices/model/group_garage_model.dart'; +import 'package:syncrow_app/features/devices/view/widgets/garage_door/garage_list.dart'; +import 'package:syncrow_app/features/shared_widgets/default_container.dart'; +import 'package:syncrow_app/features/shared_widgets/default_scaffold.dart'; + +class GarageWizard extends StatelessWidget { + const GarageWizard({super.key, this.device}); + + final DeviceModel? device; + + @override + Widget build(BuildContext context) { + List groupGarageModel = []; + + return DefaultScaffold( + title: 'Garage Door Opener', + child: BlocProvider( + create: (context) => + GarageDoorBloc( GDId: device?.uuid ?? '') + ..add(InitialWizardEvent()), + child: BlocBuilder( + builder: (context, state) { + bool allSwitchesOn = false; + + if (state is UpdateGroupState) { + groupGarageModel = state.oneGangList; + allSwitchesOn = state.allSwitches; + } + return state is LoadingInitialState + ? const Center( + child: DefaultContainer( + width: 50, + height: 50, + child: CircularProgressIndicator()), + ) + : GarageList( + garageList: groupGarageModel, + allSwitches: allSwitchesOn, + ); + }, + ), + )); + } +} diff --git a/lib/features/devices/view/widgets/wizard_page.dart b/lib/features/devices/view/widgets/wizard_page.dart index d617bad..3b62d1c 100644 --- a/lib/features/devices/view/widgets/wizard_page.dart +++ b/lib/features/devices/view/widgets/wizard_page.dart @@ -2,6 +2,7 @@ import 'package:flutter/material.dart'; import 'package:flutter_svg/svg.dart'; import 'package:syncrow_app/features/devices/model/device_category_model.dart'; import 'package:syncrow_app/features/devices/view/widgets/ACs/acs_view.dart'; +import 'package:syncrow_app/features/devices/view/widgets/garage_door/garage_wizard.dart'; import 'package:syncrow_app/features/devices/view/widgets/one_gang/one_gang_wizard.dart'; import 'package:syncrow_app/features/devices/view/widgets/one_touch/one_touch_wizard.dart'; import 'package:syncrow_app/features/devices/view/widgets/three_gang/three_gang_wizard.dart'; @@ -91,6 +92,14 @@ class WizardPage extends StatelessWidget { pageBuilder: (context, animation1, animation2) => const ThreeTouchWizard())); } + + if (groupsList[index].name == 'GD') { + Navigator.push( + context, + PageRouteBuilder( + pageBuilder: (context, animation1, animation2) => + const GarageWizard())); + } }, child: DefaultContainer( padding: const EdgeInsets.all(15), From 281414ac41a113e92fa09bfc372116cb377f7ad5 Mon Sep 17 00:00:00 2001 From: mohammad Date: Mon, 7 Oct 2024 10:29:42 +0300 Subject: [PATCH 7/8] garage wizard --- .../garage_door_bloc/garage_door_bloc.dart | 33 +++++++++---------- .../garage_door_bloc/garage_door_state.dart | 6 ++-- .../widgets/garage_door/garage_wizard.dart | 7 ++-- 3 files changed, 22 insertions(+), 24 deletions(-) diff --git a/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart b/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart index ae11720..995cd0c 100644 --- a/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart +++ b/lib/features/devices/bloc/garage_door_bloc/garage_door_bloc.dart @@ -418,7 +418,7 @@ class GarageDoorBloc extends Bloc { bool oneGangGroup = false; List devicesList = []; - List groupOneGangList = []; + List groupList = []; bool allSwitchesOn = true; void _fetchWizardStatus( @@ -426,7 +426,7 @@ class GarageDoorBloc extends Bloc { emit(LoadingInitialState()); try { devicesList = []; - groupOneGangList = []; + groupList = []; allSwitchesOn = true; devicesList = await DevicesAPI.getDeviceByGroupName( HomeCubit.getInstance().selectedSpace?.id ?? '', 'GD'); @@ -439,23 +439,22 @@ class GarageDoorBloc extends Bloc { statusModelList.add(StatusModel.fromJson(status)); } deviceStatus = GarageDoorModel.fromJson(statusModelList); - groupOneGangList.add(GroupGarageModel( + groupList.add(GroupGarageModel( deviceId: devicesList[i].uuid ?? '', deviceName: devicesList[i].name ?? '', firstSwitch: deviceStatus.switch1, )); } - if (groupOneGangList.isNotEmpty) { - groupOneGangList.firstWhere((element) { + if (groupList.isNotEmpty) { + groupList.firstWhere((element) { if (!element.firstSwitch) { allSwitchesOn = false; } return true; }); } - emit(UpdateGroupState( - oneGangList: groupOneGangList, allSwitches: allSwitchesOn)); + emit(UpdateGroupState(garageList: groupList, allSwitches: allSwitchesOn)); } catch (e) { emit(GarageDoorFailedState(errorMessage: e.toString())); @@ -468,16 +467,16 @@ class GarageDoorBloc extends Bloc { emit(LoadingNewSate(doorSensor: deviceStatus)); try { // Set all switches (firstSwitch and secondSwitch) based on the event value (on/off) - for (int i = 0; i < groupOneGangList.length; i++) { - groupOneGangList[i].firstSwitch = true; + for (int i = 0; i < groupList.length; i++) { + groupList[i].firstSwitch = true; } // Emit the state with updated values - emit(UpdateGroupState(oneGangList: groupOneGangList, allSwitches: true)); + emit(UpdateGroupState(garageList: groupList, allSwitches: true)); // Get a list of all device IDs List allDeviceIds = - groupOneGangList.map((device) => device.deviceId).toList(); + groupList.map((device) => device.deviceId).toList(); // First call for switch_1 final response = await DevicesAPI.deviceBatchController( @@ -502,16 +501,16 @@ class GarageDoorBloc extends Bloc { emit(LoadingNewSate(doorSensor: deviceStatus)); try { // Set all switches (firstSwitch and secondSwitch) based on the event value (on/off) - for (int i = 0; i < groupOneGangList.length; i++) { - groupOneGangList[i].firstSwitch = false; + for (int i = 0; i < groupList.length; i++) { + groupList[i].firstSwitch = false; } // Emit the state with updated values - emit(UpdateGroupState(oneGangList: groupOneGangList, allSwitches: false)); + emit(UpdateGroupState(garageList: groupList, allSwitches: false)); // Get a list of all device IDs List allDeviceIds = - groupOneGangList.map((device) => device.deviceId).toList(); + groupList.map((device) => device.deviceId).toList(); // First call for switch_1 final response = await DevicesAPI.deviceBatchController( @@ -537,7 +536,7 @@ class GarageDoorBloc extends Bloc { emit(LoadingNewSate(doorSensor: deviceStatus)); try { bool allSwitchesValue = true; - groupOneGangList.forEach((element) { + groupList.forEach((element) { if (element.deviceId == event.deviceId) { element.firstSwitch = !event.value; } @@ -547,7 +546,7 @@ class GarageDoorBloc extends Bloc { }); emit(UpdateGroupState( - oneGangList: groupOneGangList, allSwitches: allSwitchesValue)); + garageList: groupList, allSwitches: allSwitchesValue)); final response = await DevicesAPI.deviceBatchController( code: 'switch_1', diff --git a/lib/features/devices/bloc/garage_door_bloc/garage_door_state.dart b/lib/features/devices/bloc/garage_door_bloc/garage_door_state.dart index 86f3f5e..d16f326 100644 --- a/lib/features/devices/bloc/garage_door_bloc/garage_door_state.dart +++ b/lib/features/devices/bloc/garage_door_bloc/garage_door_state.dart @@ -83,12 +83,12 @@ class UpdateCreateScheduleState extends GarageDoorSensorState { } class UpdateGroupState extends GarageDoorSensorState { - final List oneGangList; + final List garageList; final bool allSwitches; const UpdateGroupState( - {required this.oneGangList, required this.allSwitches}); + {required this.garageList, required this.allSwitches}); @override - List get props => [oneGangList, allSwitches]; + List get props => [garageList, allSwitches]; } diff --git a/lib/features/devices/view/widgets/garage_door/garage_wizard.dart b/lib/features/devices/view/widgets/garage_door/garage_wizard.dart index e143dab..4419139 100644 --- a/lib/features/devices/view/widgets/garage_door/garage_wizard.dart +++ b/lib/features/devices/view/widgets/garage_door/garage_wizard.dart @@ -21,15 +21,14 @@ class GarageWizard extends StatelessWidget { return DefaultScaffold( title: 'Garage Door Opener', child: BlocProvider( - create: (context) => - GarageDoorBloc( GDId: device?.uuid ?? '') - ..add(InitialWizardEvent()), + create: (context) => GarageDoorBloc(GDId: device?.uuid ?? '') + ..add(InitialWizardEvent()), child: BlocBuilder( builder: (context, state) { bool allSwitchesOn = false; if (state is UpdateGroupState) { - groupGarageModel = state.oneGangList; + groupGarageModel = state.garageList; allSwitchesOn = state.allSwitches; } return state is LoadingInitialState From b89053c1fbcbbd7f542d1f005a09fb10fcaef500 Mon Sep 17 00:00:00 2001 From: mohammad Date: Mon, 7 Oct 2024 15:24:06 +0300 Subject: [PATCH 8/8] fiz wizard issue --- .../bloc/one_touch_bloc/one_touch_bloc.dart | 111 +++++---- .../bloc/three_gang_bloc/three_gang_bloc.dart | 101 ++++---- .../three_touch_bloc/three_touch_bloc.dart | 221 +++++++++++------- .../bloc/two_touch_bloc/two_touch_bloc.dart | 14 +- lib/services/api/devices_api.dart | 2 + 5 files changed, 250 insertions(+), 199 deletions(-) diff --git a/lib/features/devices/bloc/one_touch_bloc/one_touch_bloc.dart b/lib/features/devices/bloc/one_touch_bloc/one_touch_bloc.dart index 4b64206..1d431e9 100644 --- a/lib/features/devices/bloc/one_touch_bloc/one_touch_bloc.dart +++ b/lib/features/devices/bloc/one_touch_bloc/one_touch_bloc.dart @@ -29,7 +29,8 @@ class OneTouchBloc extends Bloc { bool oneTouchGroup = false; List devicesList = []; - OneTouchBloc({required this.oneTouchId, required this.switchCode}) : super(InitialState()) { + OneTouchBloc({required this.oneTouchId, required this.switchCode}) + : super(InitialState()) { on(_fetchOneTouchStatus); on(_oneTouchUpdated); on(_changeFirstSwitch); @@ -52,7 +53,8 @@ class OneTouchBloc extends Bloc { on(_changeStatus); } - void _fetchOneTouchStatus(InitialEvent event, Emitter emit) async { + void _fetchOneTouchStatus( + InitialEvent event, Emitter emit) async { emit(LoadingInitialState()); try { var response = await DevicesAPI.getDeviceStatus(oneTouchId); @@ -71,18 +73,21 @@ class OneTouchBloc extends Bloc { _listenToChanges() { try { - DatabaseReference ref = FirebaseDatabase.instance.ref('device-status/$oneTouchId'); + DatabaseReference ref = + FirebaseDatabase.instance.ref('device-status/$oneTouchId'); Stream stream = ref.onValue; stream.listen((DatabaseEvent event) async { if (_timer != null) { await Future.delayed(const Duration(seconds: 2)); } - Map usersMap = event.snapshot.value as Map; + Map usersMap = + event.snapshot.value as Map; List statusList = []; usersMap['status'].forEach((element) { - statusList.add(StatusModel(code: element['code'], value: element['value'])); + statusList + .add(StatusModel(code: element['code'], value: element['value'])); }); deviceStatus = OneTouchModel.fromJson(statusList); @@ -97,7 +102,8 @@ class OneTouchBloc extends Bloc { emit(UpdateState(oneTouchModel: deviceStatus)); } - void _changeFirstSwitch(ChangeFirstSwitchStatusEvent event, Emitter emit) async { + void _changeFirstSwitch( + ChangeFirstSwitchStatusEvent event, Emitter emit) async { emit(LoadingNewSate(oneTouchModel: deviceStatus)); try { deviceStatus.firstSwitch = !event.value; @@ -122,17 +128,20 @@ class OneTouchBloc extends Bloc { } } - void _changeSliding(ChangeSlidingSegment event, Emitter emit) async { + void _changeSliding( + ChangeSlidingSegment event, Emitter emit) async { emit(ChangeSlidingSegmentState(value: event.value)); } - void _setCounterValue(SetCounterValue event, Emitter emit) async { + void _setCounterValue( + SetCounterValue event, Emitter emit) async { emit(LoadingNewSate(oneTouchModel: deviceStatus)); int seconds = 0; try { seconds = event.duration.inSeconds; final response = await DevicesAPI.controlDevice( - DeviceControlModel(deviceId: oneTouchId, code: event.deviceCode, value: seconds), + DeviceControlModel( + deviceId: oneTouchId, code: event.deviceCode, value: seconds), oneTouchId); if (response['success'] ?? false) { @@ -155,7 +164,8 @@ class OneTouchBloc extends Bloc { } } - void _getCounterValue(GetCounterEvent event, Emitter emit) async { + void _getCounterValue( + GetCounterEvent event, Emitter emit) async { emit(LoadingInitialState()); try { var response = await DevicesAPI.getDeviceStatus(oneTouchId); @@ -244,7 +254,8 @@ class OneTouchBloc extends Bloc { deviceId: oneTouchId, ); List jsonData = response; - listSchedule = jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); + listSchedule = + jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); emit(InitialState()); } on DioException catch (e) { final errorData = e.response!.data; @@ -255,12 +266,13 @@ class OneTouchBloc extends Bloc { int? getTimeStampWithoutSeconds(DateTime? dateTime) { if (dateTime == null) return null; - DateTime dateTimeWithoutSeconds = - DateTime(dateTime.year, dateTime.month, dateTime.day, dateTime.hour, dateTime.minute); + DateTime dateTimeWithoutSeconds = DateTime(dateTime.year, dateTime.month, + dateTime.day, dateTime.hour, dateTime.minute); return dateTimeWithoutSeconds.millisecondsSinceEpoch ~/ 1000; } - Future toggleChange(ToggleScheduleEvent event, Emitter emit) async { + Future toggleChange( + ToggleScheduleEvent event, Emitter emit) async { try { emit(LoadingInitialState()); final response = await DevicesAPI.changeSchedule( @@ -279,7 +291,8 @@ class OneTouchBloc extends Bloc { } } - Future deleteSchedule(DeleteScheduleEvent event, Emitter emit) async { + Future deleteSchedule( + DeleteScheduleEvent event, Emitter emit) async { try { emit(LoadingInitialState()); final response = await DevicesAPI.deleteSchedule( @@ -299,7 +312,8 @@ class OneTouchBloc extends Bloc { } } - void toggleCreateSchedule(ToggleCreateScheduleEvent event, Emitter emit) { + void toggleCreateSchedule( + ToggleCreateScheduleEvent event, Emitter emit) { emit(LoadingInitialState()); createSchedule = !createSchedule; selectedDays.clear(); @@ -328,7 +342,8 @@ class OneTouchBloc extends Bloc { int selectedTabIndex = 0; - void toggleSelectedIndex(ToggleSelectedEvent event, Emitter emit) { + void toggleSelectedIndex( + ToggleSelectedEvent event, Emitter emit) { emit(LoadingInitialState()); selectedTabIndex = event.index; emit(ChangeSlidingSegmentState(value: selectedTabIndex)); @@ -337,7 +352,8 @@ class OneTouchBloc extends Bloc { List groupOneTouchList = []; bool allSwitchesOn = true; - void _fetchOneTouchWizardStatus(InitialWizardEvent event, Emitter emit) async { + void _fetchOneTouchWizardStatus( + InitialWizardEvent event, Emitter emit) async { emit(LoadingInitialState()); try { devicesList = []; @@ -347,7 +363,8 @@ class OneTouchBloc extends Bloc { HomeCubit.getInstance().selectedSpace?.id ?? '', '1GT'); for (int i = 0; i < devicesList.length; i++) { - var response = await DevicesAPI.getDeviceStatus(devicesList[i].uuid ?? ''); + var response = + await DevicesAPI.getDeviceStatus(devicesList[i].uuid ?? ''); List statusModelList = []; for (var status in response['status']) { statusModelList.add(StatusModel.fromJson(status)); @@ -368,15 +385,16 @@ class OneTouchBloc extends Bloc { return true; }); } - emit(UpdateGroupState(oneTouchList: groupOneTouchList, allSwitches: allSwitchesOn)); + emit(UpdateGroupState( + oneTouchList: groupOneTouchList, allSwitches: allSwitchesOn)); } catch (e) { emit(FailedState(error: e.toString())); return; } } - void _changeFirstWizardSwitch( - ChangeFirstWizardSwitchStatusEvent event, Emitter emit) async { + void _changeFirstWizardSwitch(ChangeFirstWizardSwitchStatusEvent event, + Emitter emit) async { emit(LoadingNewSate(oneTouchModel: deviceStatus)); try { bool allSwitchesValue = true; @@ -394,8 +412,9 @@ class OneTouchBloc extends Bloc { value: !event.value, ); - emit(UpdateGroupState(oneTouchList: groupOneTouchList, allSwitches: allSwitchesValue)); - if (!response['success']) { + emit(UpdateGroupState( + oneTouchList: groupOneTouchList, allSwitches: allSwitchesValue)); + if (response['success']) { add(InitialEvent(groupScreen: oneTouchGroup)); } } catch (_) { @@ -412,10 +431,12 @@ class OneTouchBloc extends Bloc { } // Emit the state with updated values - emit(UpdateGroupState(oneTouchList: groupOneTouchList, allSwitches: true)); + emit( + UpdateGroupState(oneTouchList: groupOneTouchList, allSwitches: true)); // Get a list of all device IDs - List allDeviceIds = groupOneTouchList.map((device) => device.deviceId).toList(); + List allDeviceIds = + groupOneTouchList.map((device) => device.deviceId).toList(); // First call for switch_1 final response1 = await DevicesAPI.deviceBatchController( @@ -423,20 +444,12 @@ class OneTouchBloc extends Bloc { devicesUuid: allDeviceIds, value: true, // true (on) or false (off) depending on the event value ); - - // Second call for switch_2 - final response2 = await DevicesAPI.deviceBatchController( - code: 'switch_2', // Controls second switch for all devices - devicesUuid: allDeviceIds, - value: true, // true (on) or false (off) depending on the event value - ); - - // Check if either response is unsuccessful, then reset to initial state - if (!response1['success'] || !response2['success']) { + if (response1['failedResults'].toString() != '[]') { await Future.delayed(const Duration(milliseconds: 500)); add(const InitialEvent(groupScreen: true)); } } catch (_) { + emit(FailedState(error: _.toString())); // In case of an error, delay and reset the screen to initial state await Future.delayed(const Duration(milliseconds: 500)); add(const InitialEvent(groupScreen: true)); @@ -452,31 +465,27 @@ class OneTouchBloc extends Bloc { } // Emit the state with updated values - emit(UpdateGroupState(oneTouchList: groupOneTouchList, allSwitches: false)); + emit(UpdateGroupState( + oneTouchList: groupOneTouchList, allSwitches: false)); // Get a list of all device IDs - List allDeviceIds = groupOneTouchList.map((device) => device.deviceId).toList(); + List allDeviceIds = + groupOneTouchList.map((device) => device.deviceId).toList(); // First call for switch_1 final response1 = await DevicesAPI.deviceBatchController( code: 'switch_1', // Controls first switch for all devices devicesUuid: allDeviceIds, - value: true, // true (on) or false (off) depending on the event value + value: false, // true (on) or false (off) depending on the event value ); - // Second call for switch_2 - final response2 = await DevicesAPI.deviceBatchController( - code: 'switch_2', // Controls second switch for all devices - devicesUuid: allDeviceIds, - value: true, // true (on) or false (off) depending on the event value - ); // Check if either response is unsuccessful, then reset to initial state - if (!response1['success'] || !response2['success']) { + if (response1['failedResults'].toString() != '[]') { await Future.delayed(const Duration(milliseconds: 500)); add(const InitialEvent(groupScreen: true)); } } catch (_) { - // In case of an error, delay and reset the screen to initial state + emit(FailedState(error: _.toString())); await Future.delayed(const Duration(milliseconds: 500)); add(const InitialEvent(groupScreen: true)); } @@ -485,7 +494,8 @@ class OneTouchBloc extends Bloc { String statusSelected = ''; String optionSelected = ''; - Future _changeStatus(ChangeStatusEvent event, Emitter emit) async { + Future _changeStatus( + ChangeStatusEvent event, Emitter emit) async { try { emit(LoadingInitialState()); @@ -510,7 +520,10 @@ class OneTouchBloc extends Bloc { final selectedControl = controlMap[optionSelected]?[statusSelected]; if (selectedControl != null) { await DevicesAPI.controlDevice( - DeviceControlModel(deviceId: oneTouchId, code: optionSelected, value: selectedControl), + DeviceControlModel( + deviceId: oneTouchId, + code: optionSelected, + value: selectedControl), oneTouchId, ); } else { diff --git a/lib/features/devices/bloc/three_gang_bloc/three_gang_bloc.dart b/lib/features/devices/bloc/three_gang_bloc/three_gang_bloc.dart index 242f2c5..af74e8d 100644 --- a/lib/features/devices/bloc/three_gang_bloc/three_gang_bloc.dart +++ b/lib/features/devices/bloc/three_gang_bloc/three_gang_bloc.dart @@ -107,7 +107,7 @@ class ThreeGangBloc extends Bloc { } deviceStatus = ThreeGangModel.fromJson(statusModelList); emit(UpdateState(threeGangModel: deviceStatus)); - _listenToChanges(); + // _listenToChanges(); } } catch (e) { emit(FailedState(error: e.toString())); @@ -368,33 +368,30 @@ class ThreeGangBloc extends Bloc { emit(UpdateGroupState( threeGangList: groupThreeGangList, allSwitches: true)); - for (int i = 0; i < groupThreeGangList.length; i++) { - final response = await Future.wait([ - DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: groupThreeGangList[i].deviceId, - code: 'switch_1', - value: true), - groupThreeGangList[i].deviceId), - DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: groupThreeGangList[i].deviceId, - code: 'switch_2', - value: true), - groupThreeGangList[i].deviceId), - DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: groupThreeGangList[i].deviceId, - code: 'switch_3', - value: true), - groupThreeGangList[i].deviceId), - ]); + List allDeviceIds = + groupThreeGangList.map((device) => device.deviceId).toList(); - if (response.every((element) => !element['success'])) { - await Future.delayed(const Duration(milliseconds: 500)); - add(const InitialEvent(groupScreen: true)); - break; - } + final response1 = await DevicesAPI.deviceBatchController( + code: 'switch_1', + devicesUuid: allDeviceIds, + value: true, + ); + final response2 = await DevicesAPI.deviceBatchController( + code: 'switch_2', + devicesUuid: allDeviceIds, + value: true, + ); + final response3 = await DevicesAPI.deviceBatchController( + code: 'switch_3', + devicesUuid: allDeviceIds, + value: true, + ); + + if (response1['failedResults'].toString() != '[]' || + response2['failedResults'].toString() != '[]' || + response3['failedResults'].toString() != '[]') { + await Future.delayed(const Duration(milliseconds: 500)); + add(const InitialEvent(groupScreen: true)); } } catch (_) { await Future.delayed(const Duration(milliseconds: 500)); @@ -413,34 +410,30 @@ class ThreeGangBloc extends Bloc { } emit(UpdateGroupState( threeGangList: groupThreeGangList, allSwitches: false)); + List allDeviceIds = + groupThreeGangList.map((device) => device.deviceId).toList(); - for (int i = 0; i < groupThreeGangList.length; i++) { - final response = await Future.wait([ - DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: groupThreeGangList[i].deviceId, - code: 'switch_1', - value: false), - groupThreeGangList[i].deviceId), - DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: groupThreeGangList[i].deviceId, - code: 'switch_2', - value: false), - groupThreeGangList[i].deviceId), - DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: groupThreeGangList[i].deviceId, - code: 'switch_3', - value: false), - groupThreeGangList[i].deviceId), - ]); + final response1 = await DevicesAPI.deviceBatchController( + code: 'switch_1', + devicesUuid: allDeviceIds, + value: false, + ); + final response2 = await DevicesAPI.deviceBatchController( + code: 'switch_2', + devicesUuid: allDeviceIds, + value: false, + ); + final response3 = await DevicesAPI.deviceBatchController( + code: 'switch_3', + devicesUuid: allDeviceIds, + value: false, + ); - if (response.every((element) => !element['success'])) { - await Future.delayed(const Duration(milliseconds: 500)); - add(const InitialEvent(groupScreen: true)); - break; - } + if (response1['failedResults'].toString() != '[]' || + response2['failedResults'].toString() != '[]' || + response3['failedResults'].toString() != '[]') { + await Future.delayed(const Duration(milliseconds: 500)); + add(const InitialEvent(groupScreen: true)); } } catch (_) { await Future.delayed(const Duration(milliseconds: 500)); @@ -592,8 +585,6 @@ class ThreeGangBloc extends Bloc { GetScheduleEvent event, Emitter emit, ) async { - print('getSchedule=${switchCode}'); - try { emit(LoadingInitialState()); final response = await DevicesAPI.getSchedule( diff --git a/lib/features/devices/bloc/three_touch_bloc/three_touch_bloc.dart b/lib/features/devices/bloc/three_touch_bloc/three_touch_bloc.dart index d4a59ea..8a4ac56 100644 --- a/lib/features/devices/bloc/three_touch_bloc/three_touch_bloc.dart +++ b/lib/features/devices/bloc/three_touch_bloc/three_touch_bloc.dart @@ -38,7 +38,8 @@ class ThreeTouchBloc extends Bloc { List groupThreeTouchList = []; bool allSwitchesOn = true; - ThreeTouchBloc({required this.threeTouchId, required this.switchCode}) : super(InitialState()) { + ThreeTouchBloc({required this.threeTouchId, required this.switchCode}) + : super(InitialState()) { on(_fetchThreeTouchStatus); on(_threeTouchUpdated); on(_changeFirstSwitch); @@ -53,19 +54,18 @@ class ThreeTouchBloc extends Bloc { on(_onClose); on(_groupAllOn); on(_groupAllOff); - on(toggleDaySelection); on(saveSchedule); on(getSchedule); on(toggleChange); on(deleteSchedule); - on(toggleSelectedIndex); on(toggleCreateSchedule); on(_changeStatus); } - void _fetchThreeTouchStatus(InitialEvent event, Emitter emit) async { + void _fetchThreeTouchStatus( + InitialEvent event, Emitter emit) async { emit(LoadingInitialState()); try { threeTouchGroup = event.groupScreen; @@ -77,7 +77,8 @@ class ThreeTouchBloc extends Bloc { HomeCubit.getInstance().selectedSpace?.id ?? '', '3GT'); for (int i = 0; i < devicesList.length; i++) { - var response = await DevicesAPI.getDeviceStatus(devicesList[i].uuid ?? ''); + var response = + await DevicesAPI.getDeviceStatus(devicesList[i].uuid ?? ''); List statusModelList = []; for (var status in response['status']) { statusModelList.add(StatusModel.fromJson(status)); @@ -94,13 +95,16 @@ class ThreeTouchBloc extends Bloc { if (groupThreeTouchList.isNotEmpty) { groupThreeTouchList.firstWhere((element) { - if (!element.firstSwitch || !element.secondSwitch || !element.thirdSwitch) { + if (!element.firstSwitch || + !element.secondSwitch || + !element.thirdSwitch) { allSwitchesOn = false; } return true; }); } - emit(UpdateGroupState(threeTouchList: groupThreeTouchList, allSwitches: allSwitchesOn)); + emit(UpdateGroupState( + threeTouchList: groupThreeTouchList, allSwitches: allSwitchesOn)); } else { var response = await DevicesAPI.getDeviceStatus(threeTouchId); List statusModelList = []; @@ -109,7 +113,7 @@ class ThreeTouchBloc extends Bloc { } deviceStatus = ThreeTouchModel.fromJson(statusModelList); emit(UpdateState(threeTouchModel: deviceStatus)); - _listenToChanges(); + // _listenToChanges(); } } catch (e) { emit(FailedState(error: e.toString())); @@ -119,18 +123,21 @@ class ThreeTouchBloc extends Bloc { _listenToChanges() { try { - DatabaseReference ref = FirebaseDatabase.instance.ref('device-status/$threeTouchId'); + DatabaseReference ref = + FirebaseDatabase.instance.ref('device-status/$threeTouchId'); Stream stream = ref.onValue; stream.listen((DatabaseEvent event) async { if (_timer != null) { await Future.delayed(const Duration(seconds: 2)); } - Map usersMap = event.snapshot.value as Map; + Map usersMap = + event.snapshot.value as Map; List statusList = []; usersMap['status'].forEach((element) { - statusList.add(StatusModel(code: element['code'], value: element['value'])); + statusList + .add(StatusModel(code: element['code'], value: element['value'])); }); deviceStatus = ThreeTouchModel.fromJson(statusList); @@ -145,7 +152,8 @@ class ThreeTouchBloc extends Bloc { emit(UpdateState(threeTouchModel: deviceStatus)); } - void _changeFirstSwitch(ChangeFirstSwitchStatusEvent event, Emitter emit) async { + void _changeFirstSwitch( + ChangeFirstSwitchStatusEvent event, Emitter emit) async { emit(LoadingNewSate(threeTouchModel: deviceStatus)); try { if (threeTouchGroup) { @@ -154,11 +162,15 @@ class ThreeTouchBloc extends Bloc { if (element.deviceId == event.deviceId) { element.firstSwitch = !event.value; } - if (!element.firstSwitch || !element.secondSwitch || !element.thirdSwitch) { + if (!element.firstSwitch || + !element.secondSwitch || + !element.thirdSwitch) { allSwitchesValue = false; } }); - emit(UpdateGroupState(threeTouchList: groupThreeTouchList, allSwitches: allSwitchesValue)); + emit(UpdateGroupState( + threeTouchList: groupThreeTouchList, + allSwitches: allSwitchesValue)); } else { deviceStatus.firstSwitch = !event.value; emit(UpdateState(threeTouchModel: deviceStatus)); @@ -185,8 +197,8 @@ class ThreeTouchBloc extends Bloc { } } - void _changeSecondSwitch( - ChangeSecondSwitchStatusEvent event, Emitter emit) async { + void _changeSecondSwitch(ChangeSecondSwitchStatusEvent event, + Emitter emit) async { emit(LoadingNewSate(threeTouchModel: deviceStatus)); try { if (threeTouchGroup) { @@ -195,11 +207,15 @@ class ThreeTouchBloc extends Bloc { if (element.deviceId == event.deviceId) { element.secondSwitch = !event.value; } - if (!element.firstSwitch || !element.secondSwitch || !element.thirdSwitch) { + if (!element.firstSwitch || + !element.secondSwitch || + !element.thirdSwitch) { allSwitchesValue = false; } }); - emit(UpdateGroupState(threeTouchList: groupThreeTouchList, allSwitches: allSwitchesValue)); + emit(UpdateGroupState( + threeTouchList: groupThreeTouchList, + allSwitches: allSwitchesValue)); } else { deviceStatus.secondSwitch = !event.value; emit(UpdateState(threeTouchModel: deviceStatus)); @@ -225,7 +241,8 @@ class ThreeTouchBloc extends Bloc { } } - void _changeThirdSwitch(ChangeThirdSwitchStatusEvent event, Emitter emit) async { + void _changeThirdSwitch( + ChangeThirdSwitchStatusEvent event, Emitter emit) async { emit(LoadingNewSate(threeTouchModel: deviceStatus)); try { if (threeTouchGroup) { @@ -234,11 +251,15 @@ class ThreeTouchBloc extends Bloc { if (element.deviceId == event.deviceId) { element.thirdSwitch = !event.value; } - if (!element.firstSwitch || !element.secondSwitch || !element.thirdSwitch) { + if (!element.firstSwitch || + !element.secondSwitch || + !element.thirdSwitch) { allSwitchesValue = false; } }); - emit(UpdateGroupState(threeTouchList: groupThreeTouchList, allSwitches: allSwitchesValue)); + emit(UpdateGroupState( + threeTouchList: groupThreeTouchList, + allSwitches: allSwitchesValue)); } else { deviceStatus.thirdSwitch = !event.value; emit(UpdateState(threeTouchModel: deviceStatus)); @@ -277,15 +298,21 @@ class ThreeTouchBloc extends Bloc { final response = await Future.wait([ DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeTouchId, code: 'switch_1', value: deviceStatus.firstSwitch), + deviceId: threeTouchId, + code: 'switch_1', + value: deviceStatus.firstSwitch), threeTouchId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeTouchId, code: 'switch_2', value: deviceStatus.secondSwitch), + deviceId: threeTouchId, + code: 'switch_2', + value: deviceStatus.secondSwitch), threeTouchId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeTouchId, code: 'switch_3', value: deviceStatus.thirdSwitch), + deviceId: threeTouchId, + code: 'switch_3', + value: deviceStatus.thirdSwitch), threeTouchId), ]); @@ -311,15 +338,21 @@ class ThreeTouchBloc extends Bloc { final response = await Future.wait([ DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeTouchId, code: 'switch_1', value: deviceStatus.firstSwitch), + deviceId: threeTouchId, + code: 'switch_1', + value: deviceStatus.firstSwitch), threeTouchId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeTouchId, code: 'switch_2', value: deviceStatus.secondSwitch), + deviceId: threeTouchId, + code: 'switch_2', + value: deviceStatus.secondSwitch), threeTouchId), DevicesAPI.controlDevice( DeviceControlModel( - deviceId: threeTouchId, code: 'switch_3', value: deviceStatus.thirdSwitch), + deviceId: threeTouchId, + code: 'switch_3', + value: deviceStatus.thirdSwitch), threeTouchId), ]); @@ -341,29 +374,31 @@ class ThreeTouchBloc extends Bloc { groupThreeTouchList[i].secondSwitch = true; groupThreeTouchList[i].thirdSwitch = true; } - emit(UpdateGroupState(threeTouchList: groupThreeTouchList, allSwitches: true)); + emit(UpdateGroupState( + threeTouchList: groupThreeTouchList, allSwitches: true)); + List allDeviceIds = + groupThreeTouchList.map((device) => device.deviceId).toList(); + final response1 = await DevicesAPI.deviceBatchController( + code: 'switch_1', + devicesUuid: allDeviceIds, + value: true, + ); + final response2 = await DevicesAPI.deviceBatchController( + code: 'switch_2', + devicesUuid: allDeviceIds, + value: true, + ); + final response3 = await DevicesAPI.deviceBatchController( + code: 'switch_3', + devicesUuid: allDeviceIds, + value: true, + ); - for (int i = 0; i < groupThreeTouchList.length; i++) { - final response = await Future.wait([ - DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: groupThreeTouchList[i].deviceId, code: 'switch_1', value: true), - groupThreeTouchList[i].deviceId), - DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: groupThreeTouchList[i].deviceId, code: 'switch_2', value: true), - groupThreeTouchList[i].deviceId), - DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: groupThreeTouchList[i].deviceId, code: 'switch_3', value: true), - groupThreeTouchList[i].deviceId), - ]); - - if (response.every((element) => !element['success'])) { - await Future.delayed(const Duration(milliseconds: 500)); - add(const InitialEvent(groupScreen: true)); - break; - } + if (response1['failedResults'].toString() != '[]' || + response2['failedResults'].toString() != '[]' || + response3['failedResults'].toString() != '[]') { + await Future.delayed(const Duration(milliseconds: 500)); + add(const InitialEvent(groupScreen: true)); } } catch (_) { await Future.delayed(const Duration(milliseconds: 500)); @@ -371,7 +406,8 @@ class ThreeTouchBloc extends Bloc { } } - void _groupAllOff(GroupAllOffEvent event, Emitter emit) async { + void _groupAllOff( + GroupAllOffEvent event, Emitter emit) async { emit(LoadingNewSate(threeTouchModel: deviceStatus)); try { for (int i = 0; i < groupThreeTouchList.length; i++) { @@ -379,29 +415,31 @@ class ThreeTouchBloc extends Bloc { groupThreeTouchList[i].secondSwitch = false; groupThreeTouchList[i].thirdSwitch = false; } - emit(UpdateGroupState(threeTouchList: groupThreeTouchList, allSwitches: false)); + List allDeviceIds = + groupThreeTouchList.map((device) => device.deviceId).toList(); + emit(UpdateGroupState( + threeTouchList: groupThreeTouchList, allSwitches: false)); + final response1 = await DevicesAPI.deviceBatchController( + code: 'switch_1', + devicesUuid: allDeviceIds, + value: false, + ); + final response2 = await DevicesAPI.deviceBatchController( + code: 'switch_2', + devicesUuid: allDeviceIds, + value: false, + ); + final response3 = await DevicesAPI.deviceBatchController( + code: 'switch_3', + devicesUuid: allDeviceIds, + value: false, + ); - for (int i = 0; i < groupThreeTouchList.length; i++) { - final response = await Future.wait([ - DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: groupThreeTouchList[i].deviceId, code: 'switch_1', value: false), - groupThreeTouchList[i].deviceId), - DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: groupThreeTouchList[i].deviceId, code: 'switch_2', value: false), - groupThreeTouchList[i].deviceId), - DevicesAPI.controlDevice( - DeviceControlModel( - deviceId: groupThreeTouchList[i].deviceId, code: 'switch_3', value: false), - groupThreeTouchList[i].deviceId), - ]); - - if (response.every((element) => !element['success'])) { - await Future.delayed(const Duration(milliseconds: 500)); - add(const InitialEvent(groupScreen: true)); - break; - } + if (response1['failedResults'].toString() != '[]' || + response2['failedResults'].toString() != '[]' || + response3['failedResults'].toString() != '[]') { + await Future.delayed(const Duration(milliseconds: 500)); + add(const InitialEvent(groupScreen: true)); } } catch (_) { await Future.delayed(const Duration(milliseconds: 500)); @@ -409,17 +447,20 @@ class ThreeTouchBloc extends Bloc { } } - void _changeSliding(ChangeSlidingSegment event, Emitter emit) async { + void _changeSliding( + ChangeSlidingSegment event, Emitter emit) async { emit(ChangeSlidingSegmentState(value: event.value)); } - void _setCounterValue(SetCounterValue event, Emitter emit) async { + void _setCounterValue( + SetCounterValue event, Emitter emit) async { emit(LoadingNewSate(threeTouchModel: deviceStatus)); int seconds = 0; try { seconds = event.duration.inSeconds; final response = await DevicesAPI.controlDevice( - DeviceControlModel(deviceId: threeTouchId, code: event.deviceCode, value: seconds), + DeviceControlModel( + deviceId: threeTouchId, code: event.deviceCode, value: seconds), threeTouchId); if (response['success'] ?? false) { @@ -446,7 +487,8 @@ class ThreeTouchBloc extends Bloc { } } - void _getCounterValue(GetCounterEvent event, Emitter emit) async { + void _getCounterValue( + GetCounterEvent event, Emitter emit) async { emit(LoadingInitialState()); try { var response = await DevicesAPI.getDeviceStatus(threeTouchId); @@ -556,7 +598,8 @@ class ThreeTouchBloc extends Bloc { deviceId: threeTouchId, ); List jsonData = response; - listSchedule = jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); + listSchedule = + jsonData.map((item) => ScheduleModel.fromJson(item)).toList(); emit(InitialState()); } on DioException catch (e) { final errorData = e.response!.data; @@ -567,12 +610,13 @@ class ThreeTouchBloc extends Bloc { int? getTimeStampWithoutSeconds(DateTime? dateTime) { if (dateTime == null) return null; - DateTime dateTimeWithoutSeconds = - DateTime(dateTime.year, dateTime.month, dateTime.day, dateTime.hour, dateTime.minute); + DateTime dateTimeWithoutSeconds = DateTime(dateTime.year, dateTime.month, + dateTime.day, dateTime.hour, dateTime.minute); return dateTimeWithoutSeconds.millisecondsSinceEpoch ~/ 1000; } - Future toggleChange(ToggleScheduleEvent event, Emitter emit) async { + Future toggleChange( + ToggleScheduleEvent event, Emitter emit) async { try { emit(LoadingInitialState()); final response = await DevicesAPI.changeSchedule( @@ -591,7 +635,8 @@ class ThreeTouchBloc extends Bloc { } } - Future deleteSchedule(DeleteScheduleEvent event, Emitter emit) async { + Future deleteSchedule( + DeleteScheduleEvent event, Emitter emit) async { try { emit(LoadingInitialState()); final response = await DevicesAPI.deleteSchedule( @@ -611,13 +656,15 @@ class ThreeTouchBloc extends Bloc { } } - void toggleSelectedIndex(ToggleSelectedEvent event, Emitter emit) { + void toggleSelectedIndex( + ToggleSelectedEvent event, Emitter emit) { emit(LoadingInitialState()); selectedTabIndex = event.index; emit(ChangeSlidingSegmentState(value: selectedTabIndex)); } - void toggleCreateSchedule(ToggleCreateScheduleEvent event, Emitter emit) { + void toggleCreateSchedule( + ToggleCreateScheduleEvent event, Emitter emit) { emit(LoadingInitialState()); createSchedule = !createSchedule; selectedDays.clear(); @@ -635,7 +682,8 @@ class ThreeTouchBloc extends Bloc { String statusSelected = ''; String optionSelected = ''; - Future _changeStatus(ChangeStatusEvent event, Emitter emit) async { + Future _changeStatus( + ChangeStatusEvent event, Emitter emit) async { try { emit(LoadingInitialState()); final Map> controlMap = { @@ -669,7 +717,10 @@ class ThreeTouchBloc extends Bloc { final selectedControl = controlMap[optionSelected]?[statusSelected]; if (selectedControl != null) { await DevicesAPI.controlDevice( - DeviceControlModel(deviceId: threeTouchId, code: optionSelected, value: selectedControl), + DeviceControlModel( + deviceId: threeTouchId, + code: optionSelected, + value: selectedControl), threeTouchId, ); } else { diff --git a/lib/features/devices/bloc/two_touch_bloc/two_touch_bloc.dart b/lib/features/devices/bloc/two_touch_bloc/two_touch_bloc.dart index 0f4c794..ff32edf 100644 --- a/lib/features/devices/bloc/two_touch_bloc/two_touch_bloc.dart +++ b/lib/features/devices/bloc/two_touch_bloc/two_touch_bloc.dart @@ -3,7 +3,6 @@ import 'package:dio/dio.dart'; import 'package:firebase_database/firebase_database.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; import 'package:syncrow_app/features/app_layout/bloc/home_cubit.dart'; - import 'package:syncrow_app/features/devices/bloc/two_touch_bloc/two_touch_event.dart'; import 'package:syncrow_app/features/devices/bloc/two_touch_bloc/two_touch_state.dart'; import 'package:syncrow_app/features/devices/model/device_control_model.dart'; @@ -30,14 +29,14 @@ class TwoTouchBloc extends Bloc { relay_status_2: status.off, ); Timer? _timer; - + bool twoTouchGroup = false; List devicesList = []; List groupTwoTouchList = []; bool allSwitchesOn = true; bool toggleSchedule = true; List selectedDays = []; - + bool createSchedule = false; List listSchedule = []; @@ -586,12 +585,9 @@ class TwoTouchBloc extends Bloc { emit(UpdateGroupState( twoTouchList: groupTwoTouchList, allSwitches: allSwitchesValue)); - - List allDeviceIds = - groupTwoTouchList.map((device) => device.deviceId).toList(); final response = await DevicesAPI.deviceBatchController( code: 'switch_1', - devicesUuid: allDeviceIds, + devicesUuid: [event.deviceId], value: !event.value, ); @@ -616,15 +612,13 @@ class TwoTouchBloc extends Bloc { allSwitchesValue = false; } }); - List allDeviceIds = - groupTwoTouchList.map((device) => device.deviceId).toList(); emit(UpdateGroupState( twoTouchList: groupTwoTouchList, allSwitches: allSwitchesValue)); final response = await DevicesAPI.deviceBatchController( code: 'switch_2', - devicesUuid: allDeviceIds, + devicesUuid: [event.deviceId], value: !event.value, ); diff --git a/lib/services/api/devices_api.dart b/lib/services/api/devices_api.dart index c7305db..e277df4 100644 --- a/lib/services/api/devices_api.dart +++ b/lib/services/api/devices_api.dart @@ -385,11 +385,13 @@ class DevicesAPI { String? code, bool? value, }) async { + print({"devicesUuid": devicesUuid, "code": code, "value": value}); final response = await _httpService.post( path: ApiEndpoints.controlBatch, body: {"devicesUuid": devicesUuid, "code": code, "value": value}, showServerMessage: true, expectedResponseModel: (json) { + print('json===$json'); return json; }, );