formatted all files.

This commit is contained in:
Faris Armoush
2025-06-12 15:33:32 +03:00
parent 29959f567e
commit 04250ebc98
474 changed files with 5425 additions and 4338 deletions

View File

@ -1,4 +1,3 @@
import 'dart:convert';
class AutomationStatusUpdate {
@ -17,23 +16,23 @@ class AutomationStatusUpdate {
factory AutomationStatusUpdate.fromJson(Map<String, dynamic> json) =>
AutomationStatusUpdate(
spaceUuid: json["spaceUuid"],
isEnable: json["isEnable"],
spaceUuid: json['spaceUuid'],
isEnable: json['isEnable'],
);
Map<String, dynamic> toJson() => {
"spaceUuid": spaceUuid,
"isEnable": isEnable,
'spaceUuid': spaceUuid,
'isEnable': isEnable,
};
factory AutomationStatusUpdate.fromMap(Map<String, dynamic> map) =>
AutomationStatusUpdate(
spaceUuid: map["spaceUuid"],
isEnable: map["isEnable"],
spaceUuid: map['spaceUuid'],
isEnable: map['isEnable'],
);
Map<String, dynamic> toMap() => {
"spaceUuid": spaceUuid,
"isEnable": isEnable,
'spaceUuid': spaceUuid,
'isEnable': isEnable,
};
}

View File

@ -36,7 +36,7 @@ class CreateRoutineBloc extends Bloc<CreateRoutineEvent, CreateRoutineState> {
}
}
saveSpaceIdCommunityId(
void saveSpaceIdCommunityId(
SaveCommunityIdAndSpaceIdEvent event, Emitter<CreateRoutineState> emit) {
emit(const SpaceWithDeviceLoadingState());
selectedSpaceId = event.spaceID!;
@ -44,7 +44,8 @@ class CreateRoutineBloc extends Bloc<CreateRoutineEvent, CreateRoutineState> {
emit(const SelectedState());
}
resetSelected(ResetSelectedEvent event, Emitter<CreateRoutineState> emit) {
void resetSelected(
ResetSelectedEvent event, Emitter<CreateRoutineState> emit) {
emit(const SpaceWithDeviceLoadingState());
selectedSpaceId = '';
selectedCommunityId = '';

View File

@ -42,10 +42,9 @@ class ResetSelectedEvent extends CreateRoutineEvent {
List<Object> get props => [];
}
class FetchCommunityEvent extends CreateRoutineEvent {
const FetchCommunityEvent();
@override
List<Object> get props => [];
}
}

View File

@ -1,4 +1,3 @@
import 'package:equatable/equatable.dart';
import 'package:syncrow_web/pages/spaces_management/all_spaces/model/space_model.dart';
@ -39,7 +38,6 @@ class SelectedState extends CreateRoutineState {
const SelectedState();
}
class ResetSelectedState extends CreateRoutineState {
const ResetSelectedState();
}
@ -50,4 +48,4 @@ class CommunityLoadedState extends CreateRoutineState {
class CommunitiesLoadingState extends CreateRoutineState {
const CommunitiesLoadingState();
}
}

View File

@ -25,7 +25,8 @@ class EffectPeriodBloc extends Bloc<EffectPeriodEvent, EffectPeriodState> {
on<SetDays>(_setAllDays);
}
void _initialEvent(InitialEffectPeriodEvent event, Emitter<EffectPeriodState> emit) {
void _initialEvent(
InitialEffectPeriodEvent event, Emitter<EffectPeriodState> emit) {
add(SetCustomTime(event.effectiveTime.start, event.effectiveTime.end));
emit(state.copyWith(
selectedDaysBinary: event.effectiveTime.loops,
@ -35,8 +36,8 @@ class EffectPeriodBloc extends Bloc<EffectPeriodEvent, EffectPeriodState> {
}
void _onSetPeriod(SetPeriod event, Emitter<EffectPeriodState> emit) {
String startTime = '';
String endTime = '';
var startTime = '';
var endTime = '';
switch (event.period) {
case EnumEffectivePeriodOptions.allDay:
@ -60,7 +61,9 @@ class EffectPeriodBloc extends Bloc<EffectPeriodEvent, EffectPeriodState> {
}
emit(state.copyWith(
selectedPeriod: event.period, customStartTime: startTime, customEndTime: endTime));
selectedPeriod: event.period,
customStartTime: startTime,
customEndTime: endTime));
}
void _onToggleDay(ToggleDay event, Emitter<EffectPeriodState> emit) {
@ -76,8 +79,8 @@ class EffectPeriodBloc extends Bloc<EffectPeriodEvent, EffectPeriodState> {
}
void _onSetCustomTime(SetCustomTime event, Emitter<EffectPeriodState> emit) {
String startTime = event.startTime;
String endTime = event.endTime;
final startTime = event.startTime;
final endTime = event.endTime;
EnumEffectivePeriodOptions period;
// Determine the period based on start and end times
@ -91,11 +94,14 @@ class EffectPeriodBloc extends Bloc<EffectPeriodEvent, EffectPeriodState> {
period = EnumEffectivePeriodOptions.custom;
}
emit(
state.copyWith(customStartTime: startTime, customEndTime: endTime, selectedPeriod: period));
emit(state.copyWith(
customStartTime: startTime,
customEndTime: endTime,
selectedPeriod: period));
}
void _onResetEffectivePeriod(ResetEffectivePeriod event, Emitter<EffectPeriodState> emit) {
void _onResetEffectivePeriod(
ResetEffectivePeriod event, Emitter<EffectPeriodState> emit) {
emit(state.copyWith(
selectedPeriod: EnumEffectivePeriodOptions.allDay,
customStartTime: '00:00',

View File

@ -17,9 +17,9 @@ class EffectPeriodState extends Equatable {
factory EffectPeriodState.initial() {
return const EffectPeriodState(
selectedPeriod: EnumEffectivePeriodOptions.allDay,
selectedDaysBinary: "1111111", // All days selected
customStartTime: "00:00",
customEndTime: "23:59",
selectedDaysBinary: '1111111', // All days selected
customStartTime: '00:00',
customEndTime: '23:59',
);
}
@ -50,5 +50,6 @@ class EffectPeriodState extends Equatable {
}
@override
List<Object?> get props => [selectedPeriod, selectedDaysBinary, customStartTime, customEndTime];
List<Object?> get props =>
[selectedPeriod, selectedDaysBinary, customStartTime, customEndTime];
}

View File

@ -1,11 +1,9 @@
import 'dart:async';
import 'package:bloc/bloc.dart';
import 'package:dio/dio.dart';
import 'package:equatable/equatable.dart';
import 'package:flutter/material.dart';
import 'package:syncrow_web/pages/common/bloc/project_manager.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:syncrow_web/pages/common/bloc/project_manager.dart';
import 'package:syncrow_web/pages/device_managment/all_devices/models/devices_model.dart';
import 'package:syncrow_web/pages/routines/bloc/automation_scene_trigger_bloc/automation_status_update.dart';
import 'package:syncrow_web/pages/routines/bloc/create_routine_bloc/create_routine_bloc.dart';
@ -75,7 +73,7 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
}
}
_resetErrorMessage(
void _resetErrorMessage(
ResetErrorMessage event,
Emitter<RoutineState> emit,
) {
@ -93,7 +91,7 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
final updatedIfItems = List<Map<String, dynamic>>.from(state.ifItems);
// Find the index of the item in teh current itemsList
int index = updatedIfItems.indexWhere(
final index = updatedIfItems.indexWhere(
(map) => map['uniqueCustomId'] == event.item['uniqueCustomId']);
// Replace the map if the index is valid
if (index != -1) {
@ -116,7 +114,7 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
final currentItems = List<Map<String, dynamic>>.from(state.thenItems);
// Find the index of the item in teh current itemsList
int index = currentItems.indexWhere(
final index = currentItems.indexWhere(
(map) => map['uniqueCustomId'] == event.item['uniqueCustomId']);
// Replace the map if the index is valid
if (index != -1) {
@ -135,7 +133,7 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
// List<DeviceFunctionData> selectedFunction = List<DeviceFunctionData>.from(event.functions);
Map<String, List<DeviceFunctionData>> currentSelectedFunctions =
final currentSelectedFunctions =
Map<String, List<DeviceFunctionData>>.from(state.selectedFunctions);
// if (currentSelectedFunctions.containsKey(event.uniqueCustomId)) {
@ -176,18 +174,18 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
Future<void> _onLoadScenes(
LoadScenes event, Emitter<RoutineState> emit) async {
emit(state.copyWith(isLoading: true, errorMessage: null));
List<ScenesModel> scenes = [];
final scenes = <ScenesModel>[];
try {
BuildContext context = NavigationService.navigatorKey.currentContext!;
var createRoutineBloc = context.read<CreateRoutineBloc>();
final context = NavigationService.navigatorKey.currentContext!;
final createRoutineBloc = context.read<CreateRoutineBloc>();
final projectUuid = await ProjectManager.getProjectUUID() ?? '';
if (createRoutineBloc.selectedSpaceId == '' &&
createRoutineBloc.selectedCommunityId == '') {
var spaceBloc = context.read<SpaceTreeBloc>();
for (var communityId in spaceBloc.state.selectedCommunities) {
List<String> spacesList =
final spaceBloc = context.read<SpaceTreeBloc>();
for (final communityId in spaceBloc.state.selectedCommunities) {
final spacesList =
spaceBloc.state.selectedCommunityAndSpaces[communityId] ?? [];
for (var spaceId in spacesList) {
for (final spaceId in spacesList) {
scenes.addAll(
await SceneApi.getScenes(spaceId, communityId, projectUuid));
}
@ -216,19 +214,19 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
Future<void> _onLoadAutomation(
LoadAutomation event, Emitter<RoutineState> emit) async {
emit(state.copyWith(isLoading: true, errorMessage: null));
List<ScenesModel> automations = [];
final automations = <ScenesModel>[];
final projectId = await ProjectManager.getProjectUUID() ?? '';
BuildContext context = NavigationService.navigatorKey.currentContext!;
var createRoutineBloc = context.read<CreateRoutineBloc>();
final context = NavigationService.navigatorKey.currentContext!;
final createRoutineBloc = context.read<CreateRoutineBloc>();
try {
if (createRoutineBloc.selectedSpaceId == '' &&
createRoutineBloc.selectedCommunityId == '') {
var spaceBloc = context.read<SpaceTreeBloc>();
for (var communityId in spaceBloc.state.selectedCommunities) {
List<String> spacesList =
final spaceBloc = context.read<SpaceTreeBloc>();
for (final communityId in spaceBloc.state.selectedCommunities) {
final spacesList =
spaceBloc.state.selectedCommunityAndSpaces[communityId] ?? [];
for (var spaceId in spacesList) {
for (final spaceId in spacesList) {
automations.addAll(
await SceneApi.getAutomation(spaceId, communityId, projectId));
}
@ -336,8 +334,8 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
});
}).toList();
BuildContext context = NavigationService.navigatorKey.currentContext!;
var createRoutineBloc = context.read<CreateRoutineBloc>();
final context = NavigationService.navigatorKey.currentContext!;
final createRoutineBloc = context.read<CreateRoutineBloc>();
final createSceneModel = CreateSceneModel(
spaceUuid: createRoutineBloc.selectedSpaceId,
@ -361,7 +359,7 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
}
} on APIException catch (e) {
final errorData = e.message;
String errorMessage = errorData;
final errorMessage = errorData;
emit(state.copyWith(
isLoading: false,
errorMessage: errorMessage,
@ -400,7 +398,7 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
return;
}
emit(state.copyWith(isLoading: true, errorMessage: null));
int i = 0;
var i = 0;
final conditions = state.ifItems.expand((item) {
final functions = state.selectedFunctions[item['uniqueCustomId']] ?? [];
return functions.map((function) {
@ -468,8 +466,8 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
);
});
}).toList();
BuildContext context = NavigationService.navigatorKey.currentContext!;
var createRoutineBloc = context.read<CreateRoutineBloc>();
final context = NavigationService.navigatorKey.currentContext!;
final createRoutineBloc = context.read<CreateRoutineBloc>();
final createAutomationModel = CreateAutomationModel(
spaceUuid: createRoutineBloc.selectedSpaceId,
@ -499,7 +497,7 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
}
} on APIException catch (e) {
final errorData = e.message;
String errorMessage = errorData;
final errorMessage = errorData;
emit(state.copyWith(
isLoading: false,
errorMessage: errorMessage,
@ -705,14 +703,14 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
final List<Map<String, dynamic>> thenItems;
final List<Map<String, dynamic>> ifItems;
final Map<String, List<DeviceFunctionData>> updatedFunctions =
final updatedFunctions =
Map<String, List<DeviceFunctionData>>.from(state.selectedFunctions);
final Map<String, Map<String, dynamic>> deviceCards = {};
final deviceCards = <String, Map<String, dynamic>>{};
for (var action in sceneDetails.actions) {
for (final action in sceneDetails.actions) {
AllDevicesModel? matchingDevice;
for (var device in state.devices) {
for (final device in state.devices) {
if (device.uuid == action.entityId) {
matchingDevice = device;
break;
@ -777,7 +775,7 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
action.actionExecutor != 'delay') {
final functions = matchingDevice?.functions ?? [];
final functionCode = action.executorProperty?.functionCode;
for (DeviceFunction function in functions) {
for (final function in functions) {
if (function.code == functionCode) {
updatedFunctions[uniqueCustomId]!.add(
DeviceFunctionData(
@ -871,8 +869,8 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
final projectId = await ProjectManager.getProjectUUID() ?? '';
emit(state.copyWith(isLoading: true));
BuildContext context = NavigationService.navigatorKey.currentContext!;
var spaceBloc = context.read<SpaceTreeBloc>();
final context = NavigationService.navigatorKey.currentContext!;
final spaceBloc = context.read<SpaceTreeBloc>();
if (state.isTabToRun) {
await SceneApi.deleteScene(
unitUuid: spaceBloc.state.selectedSpaces[0],
@ -901,7 +899,7 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
emit(state.copyWith(isLoading: false, createRoutineView: false));
} on APIException catch (e) {
final errorData = e.message;
String errorMessage = errorData;
final errorMessage = errorData;
emit(state.copyWith(
isLoading: false,
errorMessage: errorMessage,
@ -929,17 +927,17 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
emit(state.copyWith(isLoading: true));
try {
final projectUuid = await ProjectManager.getProjectUUID() ?? '';
List<AllDevicesModel> devices = [];
BuildContext context = NavigationService.navigatorKey.currentContext!;
var createRoutineBloc = context.read<CreateRoutineBloc>();
var spaceBloc = context.read<SpaceTreeBloc>();
final devices = <AllDevicesModel>[];
final context = NavigationService.navigatorKey.currentContext!;
final createRoutineBloc = context.read<CreateRoutineBloc>();
final spaceBloc = context.read<SpaceTreeBloc>();
if (createRoutineBloc.selectedSpaceId == '' &&
createRoutineBloc.selectedCommunityId == '') {
for (var communityId in spaceBloc.state.selectedCommunities) {
List<String> spacesList =
for (final communityId in spaceBloc.state.selectedCommunities) {
final spacesList =
spaceBloc.state.selectedCommunityAndSpaces[communityId] ?? [];
for (var spaceId in spacesList) {
for (final spaceId in spacesList) {
devices.addAll(await DevicesManagementApi()
.fetchDevices(communityId, spaceId, projectUuid));
}
@ -1071,7 +1069,7 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
return;
}
emit(state.copyWith(isLoading: true, errorMessage: null));
int i = 0;
var i = 0;
final conditions = state.ifItems.expand((item) {
final functions = state.selectedFunctions[item['uniqueCustomId']] ?? [];
return functions.map((function) {
@ -1142,8 +1140,8 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
});
}).toList();
BuildContext context = NavigationService.navigatorKey.currentContext!;
var spaceBloc = context.read<CreateRoutineBloc>();
final context = NavigationService.navigatorKey.currentContext!;
final spaceBloc = context.read<CreateRoutineBloc>();
final createAutomationModel = CreateAutomationModel(
spaceUuid: spaceBloc.selectedSpaceId,
@ -1163,8 +1161,8 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
if (result['success']) {
add(ResetRoutineState());
add(LoadAutomation());
add(LoadScenes());
add(const LoadAutomation());
add(const LoadScenes());
} else {
emit(state.copyWith(
isLoading: false,
@ -1197,14 +1195,14 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
final automationDetails =
await SceneApi.getAutomationDetails(event.automationId, projectUuid);
final Map<String, Map<String, dynamic>> deviceIfCards = {};
final Map<String, Map<String, dynamic>> deviceThenCards = {};
final deviceIfCards = <String, Map<String, dynamic>>{};
final deviceThenCards = <String, Map<String, dynamic>>{};
final Map<String, List<DeviceFunctionData>> updatedFunctions =
final updatedFunctions =
Map<String, List<DeviceFunctionData>>.from(state.selectedFunctions);
for (RoutineCondition condition in automationDetails.conditions ?? []) {
AllDevicesModel? matchingDevice = state.devices.firstWhere(
for (final condition in automationDetails.conditions ?? []) {
final matchingDevice = state.devices.firstWhere(
(device) => device.uuid == condition.entityId,
orElse: () => AllDevicesModel(
uuid: condition.entityId,
@ -1241,7 +1239,7 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
}
final functions = matchingDevice.functions;
for (var function in functions) {
for (final function in functions) {
if (function.code == condition.expr.statusCode) {
updatedFunctions[uniqueCustomId]!.add(
DeviceFunctionData(
@ -1257,8 +1255,8 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
}
// Process actions (thenItems)
for (var action in automationDetails.actions) {
AllDevicesModel? matchingDevice = state.devices.firstWhere(
for (final action in automationDetails.actions) {
final matchingDevice = state.devices.firstWhere(
(device) => device.uuid == action.entityId,
orElse: () => AllDevicesModel(
uuid: action.entityId,
@ -1312,7 +1310,7 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
action.actionExecutor != 'delay') {
final functions = matchingDevice.functions;
final functionCode = action.executorProperty!.functionCode;
for (var function in functions) {
for (final function in functions) {
if (function.code == functionCode) {
updatedFunctions[uniqueCustomId]!.add(
DeviceFunctionData(
@ -1403,7 +1401,7 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
} catch (e) {
emit(state.copyWith(
loadingSceneId: null,
errorMessage: 'Trigger error: ${e.toString()}',
errorMessage: 'Trigger error: $e',
));
}
}
@ -1448,7 +1446,7 @@ class RoutineBloc extends Bloc<RoutineEvent, RoutineState> {
..remove(event.automationId);
emit(state.copyWith(
loadingAutomationIds: updatedLoadingIds,
errorMessage: 'Update error: ${e.toString()}',
errorMessage: 'Update error: $e',
));
}
}

View File

@ -86,7 +86,8 @@ class RemoveDragCard extends RoutineEvent {
final int index;
final bool isFromThen;
final String key;
const RemoveDragCard({required this.index, required this.isFromThen, required this.key});
const RemoveDragCard(
{required this.index, required this.isFromThen, required this.key});
@override
List<Object> get props => [index, isFromThen, key];
}
@ -211,9 +212,6 @@ class ClearFunctions extends RoutineEvent {}
class ResetErrorMessage extends RoutineEvent {}
class SceneTrigger extends RoutineEvent {
final String? sceneId;
final String? name;
@ -221,7 +219,7 @@ class SceneTrigger extends RoutineEvent {
const SceneTrigger({this.sceneId, this.name});
@override
List<Object> get props => [sceneId!,name!];
List<Object> get props => [sceneId!, name!];
}
//updateAutomationStatus
@ -230,7 +228,10 @@ class UpdateAutomationStatus extends RoutineEvent {
final AutomationStatusUpdate automationStatusUpdate;
final String communityId;
const UpdateAutomationStatus({required this.automationStatusUpdate, required this.automationId, required this.communityId});
const UpdateAutomationStatus(
{required this.automationStatusUpdate,
required this.automationId,
required this.communityId});
@override
List<Object> get props => [automationStatusUpdate];

View File

@ -15,37 +15,44 @@ class SettingBloc extends Bloc<SettingEvent, SettingState> {
on<SelectIcon>(_selectIcon);
}
void _initialSetting(InitialEvent event, Emitter<SettingState> emit) async {
Future<void> _initialSetting(
InitialEvent event, Emitter<SettingState> emit) async {
try {
emit(const LoadingState());
selectedIcon = event.selectedIcon;
emit(TabToRunSettingLoaded(
showInDevice: true, selectedIcon: event.selectedIcon, iconList: iconModelList));
showInDevice: true,
selectedIcon: event.selectedIcon,
iconList: iconModelList));
} catch (e) {
emit(const FailedState(error: 'Something went wrong'));
}
}
void _fetchIcons(FetchIcons event, Emitter<SettingState> emit) async {
Future<void> _fetchIcons(FetchIcons event, Emitter<SettingState> emit) async {
try {
isExpanded = event.expanded;
emit(const LoadingState());
if (isExpanded) {
iconModelList = await SceneApi.getIcon();
emit(TabToRunSettingLoaded(
showInDevice: true, selectedIcon: selectedIcon, iconList: iconModelList));
showInDevice: true,
selectedIcon: selectedIcon,
iconList: iconModelList));
}
} catch (e) {
emit(const FailedState(error: 'Something went wrong'));
}
}
void _selectIcon(SelectIcon event, Emitter<SettingState> emit) async {
Future<void> _selectIcon(SelectIcon event, Emitter<SettingState> emit) async {
try {
emit(const LoadingState());
selectedIcon = event.iconId;
emit(TabToRunSettingLoaded(
showInDevice: true, selectedIcon: event.iconId, iconList: iconModelList));
showInDevice: true,
selectedIcon: event.iconId,
iconList: iconModelList));
} catch (e) {
emit(const FailedState(error: 'Something went wrong'));
}

View File

@ -1,11 +1,11 @@
import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:syncrow_web/pages/routines/create_new_routines/dropdown_menu_content.dart';
import 'package:syncrow_web/pages/routines/create_new_routines/space_tree_dropdown_bloc.dart';
import 'package:syncrow_web/pages/space_tree/bloc/space_tree_bloc.dart';
import 'package:syncrow_web/pages/space_tree/bloc/space_tree_state.dart';
import 'package:syncrow_web/pages/spaces_management/all_spaces/model/community_model.dart';
import 'package:syncrow_web/utils/color_manager.dart';
import 'space_tree_dropdown_bloc.dart';
class SpaceTreeDropdown extends StatefulWidget {
final String? selectedSpaceId;
@ -68,7 +68,7 @@ class _SpaceTreeDropdownState extends State<SpaceTreeDropdown> {
Padding(
padding: const EdgeInsets.symmetric(horizontal: 10),
child: Text(
"Community",
'Community',
style: Theme.of(context).textTheme.bodyMedium!.copyWith(
fontWeight: FontWeight.w400,
fontSize: 13,

View File

@ -1,8 +1,8 @@
import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:syncrow_web/pages/routines/bloc/create_routine_bloc/create_routine_bloc.dart';
import 'package:syncrow_web/pages/routines/bloc/create_routine_bloc/create_routine_event.dart';
import 'package:syncrow_web/pages/routines/bloc/create_routine_bloc/create_routine_state.dart';
import 'package:syncrow_web/pages/routines/bloc/create_routine_bloc/create_routine_bloc.dart';
import 'package:syncrow_web/pages/routines/create_new_routines/commu_dropdown.dart';
import 'package:syncrow_web/pages/routines/create_new_routines/space_dropdown.dart';
import 'package:syncrow_web/utils/color_manager.dart';
@ -27,11 +27,11 @@ class _CreateNewRoutinesDialogState extends State<CreateNewRoutinesDialog> {
CreateRoutineBloc()..add(const FetchCommunityEvent()),
child: BlocBuilder<CreateRoutineBloc, CreateRoutineState>(
builder: (context, state) {
final _bloc = BlocProvider.of<CreateRoutineBloc>(context);
final spaces = _bloc.spacesOnlyWithDevices;
final bloc = BlocProvider.of<CreateRoutineBloc>(context);
final spaces = bloc.spacesOnlyWithDevices;
final isLoadingCommunities = state is CommunitiesLoadingState;
final isLoadingSpaces = state is SpaceWithDeviceLoadingState;
String spaceHint = 'Please Select';
var spaceHint = 'Please Select';
if (_selectedCommunity != null) {
if (isLoadingSpaces) {
spaceHint = 'Loading spaces...';
@ -77,9 +77,9 @@ class _CreateNewRoutinesDialogState extends State<CreateNewRoutinesDialog> {
SpaceTreeDropdown(
selectedSpaceId: _selectedId,
onChanged: (String? newValue) {
setState(() => _selectedId = newValue!);
setState(() => _selectedId = newValue);
if (_selectedId != null) {
_bloc.add(SpaceOnlyWithDevicesEvent(
bloc.add(SpaceOnlyWithDevicesEvent(
_selectedId!));
}
},

View File

@ -1,7 +1,3 @@
import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:syncrow_web/pages/space_tree/bloc/space_tree_bloc.dart';
@ -14,6 +10,7 @@ class DropdownMenuContent extends StatefulWidget {
final VoidCallback onClose;
const DropdownMenuContent({
super.key,
required this.selectedSpaceId,
required this.onChanged,
required this.onClose,
@ -45,7 +42,7 @@ class _DropdownMenuContentState extends State<DropdownMenuContent> {
final state = bloc.state;
if (_scrollController.position.pixels >=
_scrollController.position.maxScrollExtent - 30) {
if (state is SpaceTreeState && !state.paginationIsLoading) {
if (!state.paginationIsLoading) {
bloc.add(PaginationEvent(state.paginationModel, state.communityList));
}
}
@ -126,7 +123,7 @@ class _DropdownMenuContentState extends State<DropdownMenuContent> {
_searchController.text.isEmpty
? context
.read<SpaceTreeBloc>()
.add(SearchQueryEvent(''))
.add(const SearchQueryEvent(''))
: context.read<SpaceTreeBloc>().add(
SearchQueryEvent(_searchController.text));
});

View File

@ -10,12 +10,12 @@ class SpaceDropdown extends StatelessWidget {
final String hintMessage;
const SpaceDropdown({
Key? key,
super.key,
required this.spaces,
required this.selectedValue,
required this.onChanged,
required this.hintMessage,
}) : super(key: key);
});
@override
Widget build(BuildContext context) {
@ -25,7 +25,7 @@ class SpaceDropdown extends StatelessWidget {
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Text(
"Space",
'Space',
style: Theme.of(context).textTheme.bodyMedium!.copyWith(
fontWeight: FontWeight.w400,
fontSize: 13,
@ -67,7 +67,7 @@ class SpaceDropdown extends StatelessWidget {
);
}).toList(),
onChanged: onChanged,
style: TextStyle(color: Colors.black),
style: const TextStyle(color: Colors.black),
hint: Padding(
padding: const EdgeInsets.only(left: 10),
child: Text(

View File

@ -24,4 +24,4 @@ class SpaceTreeDropdownBloc
) {
emit(SpaceTreeDropdownState(selectedSpaceId: event.initialId));
}
}
}

View File

@ -12,4 +12,4 @@ class SpaceTreeDropdownResetEvent extends SpaceTreeDropdownEvent {
final String? initialId;
SpaceTreeDropdownResetEvent(this.initialId);
}
}

View File

@ -4,4 +4,4 @@ class SpaceTreeDropdownState {
final String? selectedSpaceId;
SpaceTreeDropdownState({this.selectedSpaceId});
}
}

View File

@ -17,9 +17,10 @@ class SaveRoutineHelper {
builder: (context) {
return BlocBuilder<RoutineBloc, RoutineState>(
builder: (context, state) {
final selectedConditionLabel = state.selectedAutomationOperator == 'and'
? 'All Conditions are met'
: 'Any Condition is met';
final selectedConditionLabel =
state.selectedAutomationOperator == 'and'
? 'All Conditions are met'
: 'Any Condition is met';
return AlertDialog(
contentPadding: EdgeInsets.zero,
@ -37,10 +38,11 @@ class SaveRoutineHelper {
Text(
'Create a scene: ${state.routineName ?? ""}',
textAlign: TextAlign.center,
style: Theme.of(context).textTheme.headlineMedium!.copyWith(
color: ColorsManager.primaryColorWithOpacity,
fontWeight: FontWeight.bold,
),
style:
Theme.of(context).textTheme.headlineMedium!.copyWith(
color: ColorsManager.primaryColorWithOpacity,
fontWeight: FontWeight.bold,
),
),
const SizedBox(height: 18),
_buildDivider(),
@ -58,7 +60,8 @@ class SaveRoutineHelper {
_buildIfConditions(state, context),
Container(
width: 1,
color: ColorsManager.greyColor.withValues(alpha: 0.8),
color: ColorsManager.greyColor
.withValues(alpha: 0.8),
),
_buildThenActions(state, context),
],
@ -97,7 +100,8 @@ class SaveRoutineHelper {
child: Row(
spacing: 16,
children: [
Expanded(child: Text('IF: $selectedConditionLabel', style: textStyle)),
Expanded(
child: Text('IF: $selectedConditionLabel', style: textStyle)),
const Expanded(child: Text('THEN:', style: textStyle)),
],
),
@ -109,7 +113,7 @@ class SaveRoutineHelper {
spacing: 16,
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: [
DialogFooterButton(
DialogFooterButton(
text: 'Back',
onTap: () => Navigator.pop(context),
),
@ -143,7 +147,8 @@ class SaveRoutineHelper {
child: ListView(
// shrinkWrap: true,
children: state.thenItems.map((item) {
final functions = state.selectedFunctions[item['uniqueCustomId']] ?? [];
final functions =
state.selectedFunctions[item['uniqueCustomId']] ?? [];
return functionRow(item, context, functions);
}).toList(),
),
@ -203,19 +208,20 @@ class SaveRoutineHelper {
),
),
child: Center(
child: item['type'] == 'tap_to_run' || item['type'] == 'scene'
? Image.memory(
base64Decode(item['icon']),
width: 12,
height: 22,
fit: BoxFit.scaleDown,
)
: SvgPicture.asset(
item['imagePath'],
width: 12,
height: 12,
fit: BoxFit.scaleDown,
),
child:
item['type'] == 'tap_to_run' || item['type'] == 'scene'
? Image.memory(
base64Decode(item['icon']),
width: 12,
height: 22,
fit: BoxFit.scaleDown,
)
: SvgPicture.asset(
item['imagePath'],
width: 12,
height: 12,
fit: BoxFit.scaleDown,
),
),
),
Flexible(

View File

@ -37,12 +37,12 @@ class SwitchFunction extends ACFunction {
List<ACOperationalValue> getOperationalValues() => [
ACOperationalValue(
icon: Assets.assetsAcPower,
description: "ON",
description: 'ON',
value: true,
),
ACOperationalValue(
icon: Assets.assetsAcPowerOFF,
description: "OFF",
description: 'OFF',
value: false,
),
];
@ -62,17 +62,17 @@ class ModeFunction extends ACFunction {
List<ACOperationalValue> getOperationalValues() => [
ACOperationalValue(
icon: Assets.assetsAcCooling,
description: "Cooling",
description: 'Cooling',
value: TempModes.cold.name,
),
ACOperationalValue(
icon: Assets.assetsAcHeating,
description: "Heating",
description: 'Heating',
value: TempModes.hot.name,
),
ACOperationalValue(
icon: Assets.assetsFanSpeed,
description: "Ventilation",
description: 'Ventilation',
value: TempModes.wind.name,
),
];
@ -90,22 +90,23 @@ class TempSetFunction extends ACFunction {
min: 200,
max: 300,
step: 1,
unit: "°C",
unit: '°C',
);
@override
List<ACOperationalValue> getOperationalValues() {
List<ACOperationalValue> values = [];
for (int temp = min!.toInt(); temp <= max!; temp += step!.toInt()) {
final values = <ACOperationalValue>[];
for (var temp = min!.toInt(); temp <= max!; temp += step!.toInt()) {
values.add(ACOperationalValue(
icon: Assets.assetsTempreture,
description: "${temp / 10}°C",
description: '${temp / 10}°C',
value: temp,
));
}
return values;
}
}
class LevelFunction extends ACFunction {
LevelFunction(
{required super.deviceId, required super.deviceName, required type})
@ -120,22 +121,22 @@ class LevelFunction extends ACFunction {
List<ACOperationalValue> getOperationalValues() => [
ACOperationalValue(
icon: Assets.assetsAcFanLow,
description: "LOW",
description: 'LOW',
value: FanSpeeds.low.name,
),
ACOperationalValue(
icon: Assets.assetsAcFanMiddle,
description: "MIDDLE",
description: 'MIDDLE',
value: FanSpeeds.middle.name,
),
ACOperationalValue(
icon: Assets.assetsAcFanHigh,
description: "HIGH",
description: 'HIGH',
value: FanSpeeds.high.name,
),
ACOperationalValue(
icon: Assets.assetsAcFanAuto,
description: "AUTO",
description: 'AUTO',
value: FanSpeeds.auto.name,
),
];
@ -155,22 +156,26 @@ class ChildLockFunction extends ACFunction {
List<ACOperationalValue> getOperationalValues() => [
ACOperationalValue(
icon: Assets.assetsSceneChildLock,
description: "Lock",
description: 'Lock',
value: true,
),
ACOperationalValue(
icon: Assets.assetsSceneChildUnlock,
description: "Unlock",
description: 'Unlock',
value: false,
),
];
}
class CurrentTempFunction extends ACFunction {
@override
final double min;
@override
final double max;
@override
final double step;
final String unit = "°C";
@override
final String unit = '°C';
CurrentTempFunction(
{required super.deviceId, required super.deviceName, required type})
@ -186,11 +191,11 @@ class CurrentTempFunction extends ACFunction {
@override
List<ACOperationalValue> getOperationalValues() {
List<ACOperationalValue> values = [];
for (int temp = min.toInt(); temp <= max; temp += step.toInt()) {
final values = <ACOperationalValue>[];
for (var temp = min.toInt(); temp <= max; temp += step.toInt()) {
values.add(ACOperationalValue(
icon: Assets.currentTemp,
description: "${temp / 10}°C",
description: '${temp / 10}°C',
value: temp,
));
}

View File

@ -6,12 +6,10 @@ class CpsOperationalValue {
final String description;
final dynamic value;
CpsOperationalValue({
required this.icon,
required this.description,
required this.value,
});
}
@ -45,12 +43,12 @@ final class CpsRadarSwitchFunction extends CpsFunctions {
List<CpsOperationalValue> getOperationalValues() => [
CpsOperationalValue(
icon: Assets.assetsAcPower,
description: "ON",
description: 'ON',
value: true,
),
CpsOperationalValue(
icon: Assets.assetsAcPowerOFF,
description: "OFF",
description: 'OFF',
value: false,
),
];
@ -71,12 +69,12 @@ final class CpsSpatialParameterSwitchFunction extends CpsFunctions {
List<CpsOperationalValue> getOperationalValues() => [
CpsOperationalValue(
icon: Assets.assetsAcPower,
description: "ON",
description: 'ON',
value: true,
),
CpsOperationalValue(
icon: Assets.assetsAcPowerOFF,
description: "OFF",
description: 'OFF',
value: false,
),
];
@ -96,8 +94,11 @@ final class CpsSensitivityFunction extends CpsFunctions {
icon: Assets.sensitivity,
);
@override
final double min;
@override
final double max;
@override
final double step;
static const _images = <String>[
@ -144,8 +145,11 @@ final class CpsMovingSpeedFunction extends CpsFunctions {
icon: Assets.speedoMeter,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -175,8 +179,11 @@ final class CpsSpatialStaticValueFunction extends CpsFunctions {
icon: Assets.spatialStaticValue,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -206,8 +213,11 @@ final class CpsSpatialMotionValueFunction extends CpsFunctions {
icon: Assets.spatialMotionValue,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -237,8 +247,11 @@ final class CpsMaxDistanceOfDetectionFunction extends CpsFunctions {
icon: Assets.currentDistanceIcon,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -247,7 +260,7 @@ final class CpsMaxDistanceOfDetectionFunction extends CpsFunctions {
return List.generate(
count,
(index) {
final value = (min + (index * step));
final value = min + (index * step);
return CpsOperationalValue(
icon: Assets.currentDistanceIcon,
description: '${value.toStringAsFixed(1)} M',
@ -272,8 +285,11 @@ final class CpsMaxDistanceOfStaticDetectionFunction extends CpsFunctions {
icon: Assets.currentDistanceIcon,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -282,7 +298,7 @@ final class CpsMaxDistanceOfStaticDetectionFunction extends CpsFunctions {
return List.generate(
count,
(index) {
final value = (min + (index * step));
final value = min + (index * step);
return CpsOperationalValue(
icon: Assets.currentDistanceIcon,
description: '${value.toStringAsFixed(1)} M',
@ -307,8 +323,11 @@ final class CpsDetectionRangeFunction extends CpsFunctions {
icon: Assets.farDetection,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -317,7 +336,7 @@ final class CpsDetectionRangeFunction extends CpsFunctions {
return List.generate(
count,
(index) {
final value = (min + (index * step));
final value = min + (index * step);
return CpsOperationalValue(
icon: Assets.farDetection,
description: '${value.toStringAsFixed(1)} M',
@ -342,8 +361,11 @@ final class CpsDistanceOfMovingObjectsFunction extends CpsFunctions {
icon: Assets.currentDistanceIcon,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -352,7 +374,7 @@ final class CpsDistanceOfMovingObjectsFunction extends CpsFunctions {
return List.generate(
count,
(index) {
final value = (min + (index * step));
final value = min + (index * step);
return CpsOperationalValue(
icon: Assets.currentDistanceIcon,
description: '${value.toStringAsFixed(1)} M',
@ -377,8 +399,11 @@ final class CpsPresenceJudgementThrsholdFunction extends CpsFunctions {
icon: Assets.presenceJudgementThrshold,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -408,8 +433,11 @@ final class CpsMotionAmplitudeTriggerThresholdFunction extends CpsFunctions {
icon: Assets.presenceJudgementThrshold,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -439,8 +467,11 @@ final class CpsPerpetualBoundaryFunction extends CpsFunctions {
icon: Assets.boundary,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -449,7 +480,7 @@ final class CpsPerpetualBoundaryFunction extends CpsFunctions {
return List.generate(
count,
(index) {
final value = (min + (index * step));
final value = min + (index * step);
return CpsOperationalValue(
icon: Assets.boundary,
description: '${value.toStringAsFixed(1)}M',
@ -474,8 +505,11 @@ final class CpsMotionTriggerBoundaryFunction extends CpsFunctions {
icon: Assets.motionMeter,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -484,7 +518,7 @@ final class CpsMotionTriggerBoundaryFunction extends CpsFunctions {
return List.generate(
count,
(index) {
final value = (min + (index * step));
final value = min + (index * step);
return CpsOperationalValue(
icon: Assets.motionMeter,
description: '${value.toStringAsFixed(1)} M',
@ -509,8 +543,11 @@ final class CpsMotionTriggerTimeFunction extends CpsFunctions {
icon: Assets.motionMeter,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -519,7 +556,7 @@ final class CpsMotionTriggerTimeFunction extends CpsFunctions {
return List.generate(
count,
(index) {
final value = (min + (index * step));
final value = min + (index * step);
return CpsOperationalValue(
icon: Assets.motionMeter,
description: '${value.toStringAsFixed(3)} sec',
@ -544,8 +581,11 @@ final class CpsMotionToStaticTimeFunction extends CpsFunctions {
icon: Assets.motionMeter,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -554,7 +594,7 @@ final class CpsMotionToStaticTimeFunction extends CpsFunctions {
return List.generate(
count,
(index) {
final value = (min + (index * step));
final value = min + (index * step);
return CpsOperationalValue(
icon: Assets.motionMeter,
description: '${value.toStringAsFixed(0)} sec',
@ -579,8 +619,11 @@ final class CpsEnteringNoBodyStateTimeFunction extends CpsFunctions {
icon: Assets.motionMeter,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -589,7 +632,7 @@ final class CpsEnteringNoBodyStateTimeFunction extends CpsFunctions {
return List.generate(
count,
(index) {
final value = (min + (index * step));
final value = min + (index * step);
return CpsOperationalValue(
icon: Assets.motionMeter,
description: '${value.toStringAsFixed(0)} sec',
@ -869,8 +912,11 @@ final class CpsSportsParaFunction extends CpsFunctions {
icon: Assets.sportsPara,
);
@override
final double min;
@override
final double max;
@override
final double step;
@override
@ -879,7 +925,7 @@ final class CpsSportsParaFunction extends CpsFunctions {
return List.generate(
count,
(index) {
final value = (min + (index * step));
final value = min + (index * step);
return CpsOperationalValue(
icon: Assets.motionMeter,
description: value.toStringAsFixed(0),

View File

@ -112,7 +112,7 @@ class CreateSceneAction {
CreateSceneExecutorProperty? executorProperty,
}) {
return CreateSceneAction(
actionType: actionType ?? this.actionType,
actionType: actionType ?? actionType,
entityId: entityId ?? this.entityId,
actionExecutor: actionExecutor ?? this.actionExecutor,
executorProperty: executorProperty ?? this.executorProperty,
@ -128,7 +128,7 @@ class CreateSceneAction {
};
} else {
return {
"actionType": actionType,
'actionType': actionType,
'entityId': entityId,
'actionExecutor': actionExecutor,
};

View File

@ -14,7 +14,7 @@ class DelayFunction extends BaseSwitchFunction {
List<SwitchOperationalValue> getOperationalValues() => [
SwitchOperationalValue(
icon: '',
description: "Duration in seconds",
description: 'Duration in seconds',
value: 0.0,
minValue: 0,
maxValue: 43200,

View File

@ -24,8 +24,7 @@ class FlushPresenceDelayFunction extends FlushFunctions {
required super.deviceId,
required super.deviceName,
required super.type,
}) :
super(
}) : super(
code: FlushMountedPresenceSensorModel.codePresenceState,
operationName: 'Presence State',
icon: Assets.presenceStateIcon,
@ -37,7 +36,7 @@ class FlushPresenceDelayFunction extends FlushFunctions {
FlushOperationalValue(
icon: Assets.nobodyTime,
description: 'None',
value: "none",
value: 'none',
),
FlushOperationalValue(
icon: Assets.presenceStateIcon,
@ -49,8 +48,11 @@ class FlushPresenceDelayFunction extends FlushFunctions {
}
class FlushSensiReduceFunction extends FlushFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
FlushSensiReduceFunction({
@ -79,8 +81,11 @@ class FlushSensiReduceFunction extends FlushFunctions {
}
class FlushNoneDelayFunction extends FlushFunctions {
@override
final double min;
@override
final double max;
@override
final String unit;
FlushNoneDelayFunction({
@ -109,8 +114,11 @@ class FlushNoneDelayFunction extends FlushFunctions {
}
class FlushIlluminanceFunction extends FlushFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
FlushIlluminanceFunction({
@ -128,11 +136,11 @@ class FlushIlluminanceFunction extends FlushFunctions {
@override
List<FlushOperationalValue> getOperationalValues() {
List<FlushOperationalValue> values = [];
for (int lux = min.toInt(); lux <= max; lux += step.toInt()) {
final values = <FlushOperationalValue>[];
for (var lux = min.toInt(); lux <= max; lux += step.toInt()) {
values.add(FlushOperationalValue(
icon: Assets.IlluminanceIcon,
description: "$lux Lux",
description: '$lux Lux',
value: lux,
));
}
@ -141,8 +149,11 @@ class FlushIlluminanceFunction extends FlushFunctions {
}
class FlushOccurDistReduceFunction extends FlushFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
FlushOccurDistReduceFunction({
@ -172,8 +183,11 @@ class FlushOccurDistReduceFunction extends FlushFunctions {
// ==== then functions ====
class FlushSensitivityFunction extends FlushFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
FlushSensitivityFunction({
@ -202,9 +216,13 @@ class FlushSensitivityFunction extends FlushFunctions {
}
class FlushNearDetectionFunction extends FlushFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
@override
final String unit;
FlushNearDetectionFunction({
@ -224,7 +242,7 @@ class FlushNearDetectionFunction extends FlushFunctions {
@override
List<FlushOperationalValue> getOperationalValues() {
final values = <FlushOperationalValue>[];
for (var value = min.toDouble(); value <= max; value += step) {
for (var value = min; value <= max; value += step) {
values.add(FlushOperationalValue(
icon: Assets.nobodyTime,
description: '$value $unit',
@ -236,9 +254,13 @@ class FlushNearDetectionFunction extends FlushFunctions {
}
class FlushMaxDetectDistFunction extends FlushFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
@override
final String unit;
FlushMaxDetectDistFunction({
@ -270,9 +292,13 @@ class FlushMaxDetectDistFunction extends FlushFunctions {
}
class FlushTargetConfirmTimeFunction extends FlushFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
@override
final String unit;
FlushTargetConfirmTimeFunction({
@ -292,7 +318,7 @@ class FlushTargetConfirmTimeFunction extends FlushFunctions {
@override
List<FlushOperationalValue> getOperationalValues() {
final values = <FlushOperationalValue>[];
for (var value = min.toDouble(); value <= max; value += step) {
for (var value = min; value <= max; value += step) {
values.add(FlushOperationalValue(
icon: Assets.nobodyTime,
description: '$value $unit',
@ -304,9 +330,13 @@ class FlushTargetConfirmTimeFunction extends FlushFunctions {
}
class FlushDisappeDelayFunction extends FlushFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
@override
final String unit;
FlushDisappeDelayFunction({
@ -326,7 +356,7 @@ class FlushDisappeDelayFunction extends FlushFunctions {
@override
List<FlushOperationalValue> getOperationalValues() {
final values = <FlushOperationalValue>[];
for (var value = min.toDouble(); value <= max; value += step) {
for (var value = min; value <= max; value += step) {
values.add(FlushOperationalValue(
icon: Assets.nobodyTime,
description: '$value $unit',
@ -338,9 +368,13 @@ class FlushDisappeDelayFunction extends FlushFunctions {
}
class FlushIndentLevelFunction extends FlushFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
@override
final String unit;
FlushIndentLevelFunction({
@ -360,7 +394,7 @@ class FlushIndentLevelFunction extends FlushFunctions {
@override
List<FlushOperationalValue> getOperationalValues() {
final values = <FlushOperationalValue>[];
for (var value = min.toDouble(); value <= max; value += step) {
for (var value = min; value <= max; value += step) {
values.add(FlushOperationalValue(
icon: Assets.nobodyTime,
description: '$value $unit',
@ -372,9 +406,13 @@ class FlushIndentLevelFunction extends FlushFunctions {
}
class FlushTriggerLevelFunction extends FlushFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
@override
final String unit;
FlushTriggerLevelFunction({
@ -394,7 +432,7 @@ class FlushTriggerLevelFunction extends FlushFunctions {
@override
List<FlushOperationalValue> getOperationalValues() {
final values = <FlushOperationalValue>[];
for (var value = min.toDouble(); value <= max; value += step) {
for (var value = min; value <= max; value += step) {
values.add(FlushOperationalValue(
icon: Assets.nobodyTime,
description: '$value $unit',

View File

@ -14,12 +14,12 @@ class OneGangSwitchFunction extends BaseSwitchFunction {
List<SwitchOperationalValue> getOperationalValues() => [
SwitchOperationalValue(
icon: Assets.assetsAcPower,
description: "ON",
description: 'ON',
value: true,
),
SwitchOperationalValue(
icon: Assets.assetsAcPowerOFF,
description: "OFF",
description: 'OFF',
value: false,
),
];
@ -37,7 +37,7 @@ class OneGangCountdownFunction extends BaseSwitchFunction {
List<SwitchOperationalValue> getOperationalValues() => [
SwitchOperationalValue(
icon: '',
description: "sec",
description: 'sec',
value: 0.0,
minValue: 0,
maxValue: 43200,

View File

@ -3,8 +3,11 @@ import 'package:syncrow_web/pages/routines/models/gang_switches/switch_operation
import 'package:syncrow_web/utils/constants/assets.dart';
class ThreeGangSwitch1Function extends BaseSwitchFunction {
ThreeGangSwitch1Function({required super.deviceId, required super.deviceName ,required type})
: super(
ThreeGangSwitch1Function({
required super.deviceId,
required super.deviceName,
required String type,
}) : super(
code: 'switch_1',
operationName: 'Light 1 Switch',
icon: Assets.assetsAcPower,
@ -14,20 +17,23 @@ class ThreeGangSwitch1Function extends BaseSwitchFunction {
List<SwitchOperationalValue> getOperationalValues() => [
SwitchOperationalValue(
icon: Assets.assetsAcPower,
description: "ON",
description: 'ON',
value: true,
),
SwitchOperationalValue(
icon: Assets.assetsAcPowerOFF,
description: "OFF",
description: 'OFF',
value: false,
),
];
}
class ThreeGangCountdown1Function extends BaseSwitchFunction {
ThreeGangCountdown1Function({required super.deviceId, required super.deviceName ,required type})
: super(
ThreeGangCountdown1Function({
required super.deviceId,
required super.deviceName,
required String type,
}) : super(
code: 'countdown_1',
operationName: 'Light 1 Countdown',
icon: Assets.assetsLightCountdown,
@ -37,7 +43,7 @@ class ThreeGangCountdown1Function extends BaseSwitchFunction {
List<SwitchOperationalValue> getOperationalValues() => [
SwitchOperationalValue(
icon: '',
description: "sec",
description: 'sec',
value: 0.0,
minValue: 0,
maxValue: 43200,
@ -47,8 +53,11 @@ class ThreeGangCountdown1Function extends BaseSwitchFunction {
}
class ThreeGangSwitch2Function extends BaseSwitchFunction {
ThreeGangSwitch2Function({required super.deviceId, required super.deviceName, required type})
: super(
ThreeGangSwitch2Function({
required super.deviceId,
required super.deviceName,
required String type,
}) : super(
code: 'switch_2',
operationName: 'Light 2 Switch',
icon: Assets.assetsAcPower,
@ -58,20 +67,23 @@ class ThreeGangSwitch2Function extends BaseSwitchFunction {
List<SwitchOperationalValue> getOperationalValues() => [
SwitchOperationalValue(
icon: Assets.assetsAcPower,
description: "ON",
description: 'ON',
value: true,
),
SwitchOperationalValue(
icon: Assets.assetsAcPowerOFF,
description: "OFF",
description: 'OFF',
value: false,
),
];
}
class ThreeGangCountdown2Function extends BaseSwitchFunction {
ThreeGangCountdown2Function({required super.deviceId, required super.deviceName ,required type})
: super(
ThreeGangCountdown2Function({
required super.deviceId,
required super.deviceName,
required String type,
}) : super(
code: 'countdown_2',
operationName: 'Light 2 Countdown',
icon: Assets.assetsLightCountdown,
@ -81,7 +93,7 @@ class ThreeGangCountdown2Function extends BaseSwitchFunction {
List<SwitchOperationalValue> getOperationalValues() => [
SwitchOperationalValue(
icon: '',
description: "sec",
description: 'sec',
value: 0.0,
minValue: 0,
maxValue: 43200,
@ -91,8 +103,11 @@ class ThreeGangCountdown2Function extends BaseSwitchFunction {
}
class ThreeGangSwitch3Function extends BaseSwitchFunction {
ThreeGangSwitch3Function({required super.deviceId, required super.deviceName ,required type})
: super(
ThreeGangSwitch3Function({
required super.deviceId,
required super.deviceName,
required String type,
}) : super(
code: 'switch_3',
operationName: 'Light 3 Switch',
icon: Assets.assetsAcPower,
@ -102,20 +117,23 @@ class ThreeGangSwitch3Function extends BaseSwitchFunction {
List<SwitchOperationalValue> getOperationalValues() => [
SwitchOperationalValue(
icon: Assets.assetsAcPower,
description: "ON",
description: 'ON',
value: true,
),
SwitchOperationalValue(
icon: Assets.assetsAcPowerOFF,
description: "OFF",
description: 'OFF',
value: false,
),
];
}
class ThreeGangCountdown3Function extends BaseSwitchFunction {
ThreeGangCountdown3Function({required super.deviceId, required super.deviceName ,required type})
: super(
ThreeGangCountdown3Function({
required super.deviceId,
required super.deviceName,
required String type,
}) : super(
code: 'countdown_3',
operationName: 'Light 3 Countdown',
icon: Assets.assetsLightCountdown,
@ -125,7 +143,7 @@ class ThreeGangCountdown3Function extends BaseSwitchFunction {
List<SwitchOperationalValue> getOperationalValues() => [
SwitchOperationalValue(
icon: '',
description: "sec",
description: 'sec',
value: 0.0,
minValue: 0,
maxValue: 43200,

View File

@ -14,12 +14,12 @@ class TwoGangSwitch1Function extends BaseSwitchFunction {
List<SwitchOperationalValue> getOperationalValues() => [
SwitchOperationalValue(
icon: Assets.assetsAcPower,
description: "ON",
description: 'ON',
value: true,
),
SwitchOperationalValue(
icon: Assets.assetsAcPowerOFF,
description: "OFF",
description: 'OFF',
value: false,
),
];
@ -37,19 +37,20 @@ class TwoGangSwitch2Function extends BaseSwitchFunction {
List<SwitchOperationalValue> getOperationalValues() => [
SwitchOperationalValue(
icon: Assets.assetsAcPower,
description: "ON",
description: 'ON',
value: true,
),
SwitchOperationalValue(
icon: Assets.assetsAcPowerOFF,
description: "OFF",
description: 'OFF',
value: false,
),
];
}
class TwoGangCountdown1Function extends BaseSwitchFunction {
TwoGangCountdown1Function({required super.deviceId, required super.deviceName})
TwoGangCountdown1Function(
{required super.deviceId, required super.deviceName})
: super(
code: 'countdown_1',
operationName: 'Light 1 Countdown',
@ -60,7 +61,7 @@ class TwoGangCountdown1Function extends BaseSwitchFunction {
List<SwitchOperationalValue> getOperationalValues() => [
SwitchOperationalValue(
icon: '',
description: "sec",
description: 'sec',
value: 0.0,
minValue: 0,
maxValue: 43200,
@ -70,7 +71,8 @@ class TwoGangCountdown1Function extends BaseSwitchFunction {
}
class TwoGangCountdown2Function extends BaseSwitchFunction {
TwoGangCountdown2Function({required super.deviceId, required super.deviceName})
TwoGangCountdown2Function(
{required super.deviceId, required super.deviceName})
: super(
code: 'countdown_2',
operationName: 'Light 2 Countdown',
@ -81,7 +83,7 @@ class TwoGangCountdown2Function extends BaseSwitchFunction {
List<SwitchOperationalValue> getOperationalValues() => [
SwitchOperationalValue(
icon: '',
description: "sec",
description: 'sec',
value: 0.0,
minValue: 0,
maxValue: 43200,

View File

@ -13,7 +13,8 @@ class GatewayOperationalValue {
});
}
abstract class GatewayFunctions extends DeviceFunction<GatewayOperationalValue> {
abstract class GatewayFunctions
extends DeviceFunction<GatewayOperationalValue> {
final String type;
GatewayFunctions({
@ -43,12 +44,12 @@ final class GatewaySwitchAlarmSound extends GatewayFunctions {
List<GatewayOperationalValue> getOperationalValues() => [
GatewayOperationalValue(
icon: Assets.assetsAcPower,
description: "ON",
description: 'ON',
value: true,
),
GatewayOperationalValue(
icon: Assets.assetsAcPowerOFF,
description: "OFF",
description: 'OFF',
value: false,
),
];
@ -70,12 +71,12 @@ final class GatewayMasterState extends GatewayFunctions {
return [
GatewayOperationalValue(
icon: Assets.assetsAcPower,
description: "Normal",
description: 'Normal',
value: 'normal',
),
GatewayOperationalValue(
icon: Assets.assetsAcPowerOFF,
description: "Alarm",
description: 'Alarm',
value: 'alarm',
),
];
@ -98,12 +99,12 @@ final class GatewayFactoryReset extends GatewayFunctions {
return [
GatewayOperationalValue(
icon: Assets.assetsAcPower,
description: "ON",
description: 'ON',
value: true,
),
GatewayOperationalValue(
icon: Assets.assetsAcPowerOFF,
description: "OFF",
description: 'OFF',
value: false,
),
];

View File

@ -35,7 +35,7 @@ class TotalEnergyConsumedStatusFunction extends EnergyClampFunctions {
min: 0.00,
max: 20000000.00,
step: 1,
unit: "kWh",
unit: 'kWh',
);
@override
@ -54,7 +54,7 @@ class TotalActivePowerConsumedStatusFunction extends EnergyClampFunctions {
min: -19800000,
max: 19800000,
step: 0.1,
unit: "kW",
unit: 'kW',
);
@override
@ -101,7 +101,7 @@ class TotalCurrentStatusFunction extends EnergyClampFunctions {
min: 0.000,
max: 9000.000,
step: 1,
unit: "A",
unit: 'A',
);
@override
@ -120,7 +120,7 @@ class FrequencyStatusFunction extends EnergyClampFunctions {
min: 0,
max: 80,
step: 1,
unit: "Hz",
unit: 'Hz',
);
@override
@ -140,7 +140,7 @@ class EnergyConsumedAStatusFunction extends EnergyClampFunctions {
min: 0.00,
max: 20000000.00,
step: 1,
unit: "kWh",
unit: 'kWh',
);
@override
@ -159,7 +159,7 @@ class ActivePowerAStatusFunction extends EnergyClampFunctions {
min: 200,
max: 300,
step: 1,
unit: "kW",
unit: 'kW',
);
@override
@ -178,7 +178,7 @@ class VoltageAStatusFunction extends EnergyClampFunctions {
min: 0.0,
max: 500,
step: 1,
unit: "V",
unit: 'V',
);
@override
@ -197,7 +197,7 @@ class PowerFactorAStatusFunction extends EnergyClampFunctions {
min: 0.00,
max: 1.00,
step: 0.1,
unit: "",
unit: '',
);
@override
@ -216,7 +216,7 @@ class CurrentAStatusFunction extends EnergyClampFunctions {
min: 0.000,
max: 3000.000,
step: 1,
unit: "A",
unit: 'A',
);
@override
@ -236,7 +236,7 @@ class EnergyConsumedBStatusFunction extends EnergyClampFunctions {
min: 0.00,
max: 20000000.00,
step: 1,
unit: "kWh",
unit: 'kWh',
);
@override
@ -255,7 +255,7 @@ class ActivePowerBStatusFunction extends EnergyClampFunctions {
min: -6600000,
max: 6600000,
step: 1,
unit: "kW",
unit: 'kW',
);
@override
@ -274,7 +274,7 @@ class VoltageBStatusFunction extends EnergyClampFunctions {
min: 0.0,
max: 500,
step: 1,
unit: "V",
unit: 'V',
);
@override
@ -293,7 +293,7 @@ class CurrentBStatusFunction extends EnergyClampFunctions {
min: 0.000,
max: 3000.000,
step: 1,
unit: "A",
unit: 'A',
);
@override
@ -312,7 +312,7 @@ class PowerFactorBStatusFunction extends EnergyClampFunctions {
min: 0.0,
max: 1.0,
step: 0.1,
unit: "",
unit: '',
);
@override
@ -332,7 +332,7 @@ class EnergyConsumedCStatusFunction extends EnergyClampFunctions {
min: 0.00,
max: 20000000.00,
step: 1,
unit: "kWh",
unit: 'kWh',
);
@override
@ -351,7 +351,7 @@ class ActivePowerCStatusFunction extends EnergyClampFunctions {
min: -6600000,
max: 6600000,
step: 1,
unit: "kW",
unit: 'kW',
);
@override
@ -370,7 +370,7 @@ class VoltageCStatusFunction extends EnergyClampFunctions {
min: 0.00,
max: 500,
step: 0.1,
unit: "V",
unit: 'V',
);
@override
@ -389,7 +389,7 @@ class CurrentCStatusFunction extends EnergyClampFunctions {
min: 0.000,
max: 3000.000,
step: 0.1,
unit: "A",
unit: 'A',
);
@override
@ -408,7 +408,7 @@ class PowerFactorCStatusFunction extends EnergyClampFunctions {
min: 0.00,
max: 1.00,
step: 0.1,
unit: "",
unit: '',
);
@override

View File

@ -48,7 +48,8 @@ class RoutineDetailsModel {
spaceUuid: spaceUuid,
automationName: name,
decisionExpr: decisionExpr,
effectiveTime: effectiveTime ?? EffectiveTime(start: '', end: '', loops: ''),
effectiveTime:
effectiveTime ?? EffectiveTime(start: '', end: '', loops: ''),
conditions: conditions?.map((c) => c.toCondition()).toList() ?? [],
actions: actions.map((a) => a.toAutomationAction()).toList(),
);
@ -63,7 +64,8 @@ class RoutineDetailsModel {
if (iconId != null) 'iconUuid': iconId,
if (showInDevice != null) 'showInDevice': showInDevice,
if (effectiveTime != null) 'effectiveTime': effectiveTime!.toMap(),
if (conditions != null) 'conditions': conditions!.map((x) => x.toMap()).toList(),
if (conditions != null)
'conditions': conditions!.map((x) => x.toMap()).toList(),
if (type != null) 'type': type,
if (sceneId != null) 'sceneId': sceneId,
if (automationId != null) 'automationId': automationId,
@ -80,10 +82,12 @@ class RoutineDetailsModel {
),
iconId: map['iconUuid'],
showInDevice: map['showInDevice'],
effectiveTime:
map['effectiveTime'] != null ? EffectiveTime.fromMap(map['effectiveTime']) : null,
effectiveTime: map['effectiveTime'] != null
? EffectiveTime.fromMap(map['effectiveTime'])
: null,
conditions: map['conditions'] != null
? List<RoutineCondition>.from(map['conditions'].map((x) => RoutineCondition.fromMap(x)))
? List<RoutineCondition>.from(
map['conditions'].map((x) => RoutineCondition.fromMap(x)))
: null,
type: map['type'],
sceneId: map['sceneId'],
@ -137,7 +141,8 @@ class RoutineAction {
'actionExecutor': actionExecutor,
if (type != null) 'type': type,
if (name != null) 'name': name,
if (executorProperty != null) 'executorProperty': executorProperty!.toMap(),
if (executorProperty != null)
'executorProperty': executorProperty!.toMap(),
};
}

View File

@ -42,27 +42,27 @@ class ScenesModel {
factory ScenesModel.fromJson(Map<String, dynamic> json,
{bool? isAutomation}) {
return ScenesModel(
id: json["id"] ?? json["uuid"] ?? '',
sceneTuyaId: json["sceneTuyaId"] as String?,
name: json["name"] ?? '',
status: json["status"] ?? '',
type: json["type"] ?? '',
spaceName: json["spaceName"] ?? '',
spaceId: json["spaceId"] ?? '',
communityId: json["communityId"] ?? '',
id: json['id'] ?? json['uuid'] ?? '',
sceneTuyaId: json['sceneTuyaId'] as String?,
name: json['name'] ?? '',
status: json['status'] ?? '',
type: json['type'] ?? '',
spaceName: json['spaceName'] ?? '',
spaceId: json['spaceId'] ?? '',
communityId: json['communityId'] ?? '',
icon:
isAutomation == true ? Assets.automation : (json["icon"] as String?),
isAutomation == true ? Assets.automation : (json['icon'] as String?),
);
}
Map<String, dynamic> toJson() => {
"id": id,
"sceneTuyaId": sceneTuyaId ?? '',
"name": name,
"status": status,
"type": type,
"spaceName": spaceName,
"spaceId": spaceId,
"communityId": communityId,
'id': id,
'sceneTuyaId': sceneTuyaId ?? '',
'name': name,
'status': status,
'type': type,
'spaceName': spaceName,
'spaceId': spaceId,
'communityId': communityId,
};
}

View File

@ -29,7 +29,6 @@ class WHRestartStatusFunction extends WaterHeaterFunctions {
operationName: 'Restart Status',
icon: Assets.refreshStatusIcon,
);
@override
List<WaterHeaterOperationalValue> getOperationalValues() {
@ -37,7 +36,7 @@ class WHRestartStatusFunction extends WaterHeaterFunctions {
WaterHeaterOperationalValue(
icon: Assets.assetsAcPowerOFF,
description: 'Power OFF',
value: "off",
value: 'off',
),
WaterHeaterOperationalValue(
icon: Assets.assetsAcPower,
@ -46,7 +45,7 @@ class WHRestartStatusFunction extends WaterHeaterFunctions {
),
WaterHeaterOperationalValue(
icon: Assets.refreshStatusIcon,
description: "Restart Memory",
description: 'Restart Memory',
value: 'memory',
),
];
@ -105,8 +104,7 @@ class BacklightFunction extends WaterHeaterFunctions {
required super.deviceId,
required super.deviceName,
required super.type,
}) :
super(
}) : super(
code: 'switch_backlight',
operationName: 'Backlight',
icon: Assets.indicator,

View File

@ -24,11 +24,11 @@ abstract class WpsFunctions extends DeviceFunction<WallSensorModel> {
// For far_detection (75-600cm in 75cm steps)
class FarDetectionFunction extends WpsFunctions {
@override
final double min;
@override
@override
final double max;
@override
@override
final double step;
@override
final String unit;
@ -62,9 +62,13 @@ class FarDetectionFunction extends WpsFunctions {
// For presence_time (0-65535 minutes)
class PresenceTimeFunction extends WpsFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
@override
final String unit;
PresenceTimeFunction(
@ -94,8 +98,11 @@ class PresenceTimeFunction extends WpsFunctions {
// For motion_sensitivity_value (1-5 levels)
class MotionSensitivityFunction extends WpsFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
MotionSensitivityFunction(
@ -124,8 +131,11 @@ class MotionSensitivityFunction extends WpsFunctions {
}
class MotionLessSensitivityFunction extends WpsFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
MotionLessSensitivityFunction(
@ -167,20 +177,23 @@ class IndicatorFunction extends WpsFunctions {
List<WpsOperationalValue> getOperationalValues() => [
WpsOperationalValue(
icon: Assets.assetsAcPower,
description: "ON",
description: 'ON',
value: true,
),
WpsOperationalValue(
icon: Assets.assetsAcPowerOFF,
description: "OFF",
description: 'OFF',
value: false,
),
];
}
class NoOneTimeFunction extends WpsFunctions {
@override
final double min;
@override
final double max;
@override
final String unit;
NoOneTimeFunction(
@ -221,20 +234,23 @@ class PresenceStateFunction extends WpsFunctions {
List<WpsOperationalValue> getOperationalValues() => [
WpsOperationalValue(
icon: Assets.assetsAcPower,
description: "None",
description: 'None',
value: 'none',
),
WpsOperationalValue(
icon: Assets.presenceStateIcon,
description: "Presence",
description: 'Presence',
value: 'presence',
),
];
}
class CurrentDistanceFunction extends WpsFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
CurrentDistanceFunction(
@ -251,11 +267,11 @@ class CurrentDistanceFunction extends WpsFunctions {
@override
List<WpsOperationalValue> getOperationalValues() {
List<WpsOperationalValue> values = [];
for (int cm = min.toInt(); cm <= max; cm += step.toInt()) {
final values = <WpsOperationalValue>[];
for (var cm = min.toInt(); cm <= max; cm += step.toInt()) {
values.add(WpsOperationalValue(
icon: Assets.assetsTempreture,
description: "${cm}CM",
description: '${cm}CM',
value: cm,
));
}
@ -264,8 +280,11 @@ class CurrentDistanceFunction extends WpsFunctions {
}
class IlluminanceValueFunction extends WpsFunctions {
@override
final double min;
@override
final double max;
@override
final double step;
IlluminanceValueFunction({
@ -283,11 +302,11 @@ class IlluminanceValueFunction extends WpsFunctions {
@override
List<WpsOperationalValue> getOperationalValues() {
List<WpsOperationalValue> values = [];
for (int lux = min.toInt(); lux <= max; lux += step.toInt()) {
final values = <WpsOperationalValue>[];
for (var lux = min.toInt(); lux <= max; lux += step.toInt()) {
values.add(WpsOperationalValue(
icon: Assets.IlluminanceIcon,
description: "$lux Lux",
description: '$lux Lux',
value: lux,
));
}

View File

@ -1,7 +1,7 @@
import 'package:flutter/material.dart';
import 'package:syncrow_web/pages/routines/widgets/routine_dialogs/effictive_period_dialog.dart';
import 'package:syncrow_web/pages/routines/widgets/period_option.dart';
import 'package:syncrow_web/pages/routines/widgets/repeat_days.dart';
import 'package:syncrow_web/pages/routines/widgets/routine_dialogs/effictive_period_dialog.dart';
import 'package:syncrow_web/utils/color_manager.dart';
class EffectivePeriodView extends StatelessWidget {

View File

@ -19,7 +19,7 @@ class RoutinesView extends StatefulWidget {
}
class _RoutinesViewState extends State<RoutinesView> {
void _handleRoutineCreation(BuildContext context) async {
Future<void> _handleRoutineCreation(BuildContext context) async {
final result = await showDialog<Map<String, dynamic>>(
context: context,
builder: (context) => const CreateNewRoutinesDialog(),
@ -69,7 +69,7 @@ class _RoutinesViewState extends State<RoutinesView> {
spacing: 16,
children: [
Text(
"Create New Routines",
'Create New Routines',
style:
Theme.of(context).textTheme.titleLarge?.copyWith(
color: ColorsManager.grayColor,

View File

@ -11,8 +11,8 @@ class ConditionToggle extends StatelessWidget {
super.key,
});
static const _conditions = ["<", "==", ">"];
static const _icons = [
static const _conditions = ['<', '==', '>'];
static const List<IconData> _icons = [
Icons.chevron_left,
Icons.drag_handle,
Icons.chevron_right
@ -20,13 +20,13 @@ class ConditionToggle extends StatelessWidget {
@override
Widget build(BuildContext context) {
final selectedIndex = _conditions.indexOf(currentCondition ?? "==");
final selectedIndex = _conditions.indexOf(currentCondition ?? '==');
return Container(
height: 30,
width: MediaQuery.of(context).size.width * 0.1,
decoration: BoxDecoration(
color: ColorsManager.softGray.withOpacity(0.5),
color: ColorsManager.softGray.withValues(alpha: 0.5),
borderRadius: BorderRadius.circular(50),
),
clipBehavior: Clip.antiAlias,

View File

@ -1,4 +1,5 @@
import 'dart:math';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:syncrow_web/pages/routines/widgets/condition_toggle.dart';
@ -45,10 +46,10 @@ class _CustomRoutinesTextboxState extends State<CustomRoutinesTextbox> {
String? errorMessage;
int getDecimalPlaces(double step) {
String stepStr = step.toString();
final stepStr = step.toString();
if (stepStr.contains('.')) {
List<String> parts = stepStr.split('.');
String decimalPart = parts[1];
final parts = stepStr.split('.');
var decimalPart = parts[1];
decimalPart = decimalPart.replaceAll(RegExp(r'0+$'), '');
return decimalPart.isEmpty ? 0 : decimalPart.length;
} else {
@ -111,13 +112,11 @@ class _CustomRoutinesTextboxState extends State<CustomRoutinesTextbox> {
}
}
void _validateInput(String value) {
final doubleValue = double.tryParse(value);
if (doubleValue == null) {
setState(() {
errorMessage = "Invalid number";
errorMessage = 'Invalid number';
hasError = true;
});
return;
@ -128,23 +127,23 @@ class _CustomRoutinesTextboxState extends State<CustomRoutinesTextbox> {
if (doubleValue < min) {
setState(() {
errorMessage = "Value must be at least $min";
errorMessage = 'Value must be at least $min';
hasError = true;
});
} else if (doubleValue > max) {
setState(() {
errorMessage = "Value must be at most $max";
errorMessage = 'Value must be at most $max';
hasError = true;
});
} else {
int decimalPlaces = getDecimalPlaces(widget.stepIncreaseAmount);
int factor = pow(10, decimalPlaces).toInt();
int scaledStep = (widget.stepIncreaseAmount * factor).round();
int scaledValue = (doubleValue * factor).round();
final decimalPlaces = getDecimalPlaces(widget.stepIncreaseAmount);
final factor = pow(10, decimalPlaces).toInt();
final scaledStep = (widget.stepIncreaseAmount * factor).round();
final scaledValue = (doubleValue * factor).round();
if (scaledValue % scaledStep != 0) {
setState(() {
errorMessage = "must be a multiple of ${widget.stepIncreaseAmount}";
errorMessage = 'must be a multiple of ${widget.stepIncreaseAmount}';
hasError = true;
});
} else {
@ -156,11 +155,10 @@ class _CustomRoutinesTextboxState extends State<CustomRoutinesTextbox> {
}
}
void _correctAndUpdateValue(String value) {
final doubleValue = double.tryParse(value) ?? 0.0;
int decimalPlaces = getDecimalPlaces(widget.stepIncreaseAmount);
double rounded = (doubleValue / widget.stepIncreaseAmount).round() *
final decimalPlaces = getDecimalPlaces(widget.stepIncreaseAmount);
var rounded = (doubleValue / widget.stepIncreaseAmount).round() *
widget.stepIncreaseAmount;
rounded = rounded.clamp(widget.sliderRange.$1, widget.sliderRange.$2);
rounded = double.parse(rounded.toStringAsFixed(decimalPlaces));
@ -179,9 +177,9 @@ class _CustomRoutinesTextboxState extends State<CustomRoutinesTextbox> {
@override
Widget build(BuildContext context) {
int decimalPlaces = getDecimalPlaces(widget.stepIncreaseAmount);
final decimalPlaces = getDecimalPlaces(widget.stepIncreaseAmount);
List<TextInputFormatter> formatters = [];
final formatters = <TextInputFormatter>[];
if (decimalPlaces == 0) {
formatters.add(FilteringTextInputFormatter.digitsOnly);
} else {
@ -233,7 +231,7 @@ class _CustomRoutinesTextboxState extends State<CustomRoutinesTextbox> {
color: ColorsManager.lightGrayBorderColor, width: 1),
boxShadow: [
BoxShadow(
color: ColorsManager.blackColor.withOpacity(0.05),
color: ColorsManager.blackColor.withValues(alpha: 0.05),
blurRadius: 8,
offset: const Offset(0, 4),
),

View File

@ -33,13 +33,17 @@ class DeleteSceneWidget extends StatelessWidget {
alignment: AlignmentDirectional.center,
child: Text(
'Cancel',
style: Theme.of(context).textTheme.bodyMedium!.copyWith(
style: Theme.of(context)
.textTheme
.bodyMedium!
.copyWith(
color: ColorsManager.textGray,
),
),
),
),
Container(width: 1, height: 50, color: ColorsManager.greyColor),
Container(
width: 1, height: 50, color: ColorsManager.greyColor),
InkWell(
onTap: () {
context.read<RoutineBloc>().add(const DeleteScene());
@ -50,7 +54,10 @@ class DeleteSceneWidget extends StatelessWidget {
alignment: AlignmentDirectional.center,
child: Text(
'Confirm',
style: Theme.of(context).textTheme.bodyMedium!.copyWith(
style: Theme.of(context)
.textTheme
.bodyMedium!
.copyWith(
color: ColorsManager.primaryColorWithOpacity,
),
),

View File

@ -33,17 +33,18 @@ class DraggableCard extends StatelessWidget {
Widget build(BuildContext context) {
return BlocBuilder<RoutineBloc, RoutineState>(
builder: (context, state) {
final deviceFunctions = state.selectedFunctions[deviceData['uniqueCustomId']] ?? [];
final deviceFunctions =
state.selectedFunctions[deviceData['uniqueCustomId']] ?? [];
int index = state.thenItems
.indexWhere((item) => item['uniqueCustomId'] == deviceData['uniqueCustomId']);
final index = state.thenItems.indexWhere(
(item) => item['uniqueCustomId'] == deviceData['uniqueCustomId']);
if (index != -1) {
return _buildCardContent(context, deviceFunctions, padding: padding);
}
int ifIndex = state.ifItems
.indexWhere((item) => item['uniqueCustomId'] == deviceData['uniqueCustomId']);
final ifIndex = state.ifItems.indexWhere(
(item) => item['uniqueCustomId'] == deviceData['uniqueCustomId']);
if (ifIndex != -1) {
return _buildCardContent(context, deviceFunctions, padding: padding);
@ -53,7 +54,8 @@ class DraggableCard extends StatelessWidget {
data: deviceData,
feedback: Transform.rotate(
angle: -0.1,
child: _buildCardContent(context, deviceFunctions, padding: padding),
child:
_buildCardContent(context, deviceFunctions, padding: padding),
),
childWhenDragging: _buildGreyContainer(),
child: _buildCardContent(context, deviceFunctions, padding: padding),
@ -62,7 +64,8 @@ class DraggableCard extends StatelessWidget {
);
}
Widget _buildCardContent(BuildContext context, List<DeviceFunctionData> deviceFunctions,
Widget _buildCardContent(
BuildContext context, List<DeviceFunctionData> deviceFunctions,
{EdgeInsetsGeometry? padding}) {
return Stack(
children: [
@ -92,7 +95,8 @@ class DraggableCard extends StatelessWidget {
),
),
padding: const EdgeInsets.all(8),
child: deviceData['type'] == 'tap_to_run' || deviceData['type'] == 'scene'
child: deviceData['type'] == 'tap_to_run' ||
deviceData['type'] == 'scene'
? Image.memory(
base64Decode(deviceData['icon']),
)
@ -118,12 +122,15 @@ class DraggableCard extends StatelessWidget {
height: 4,
),
Visibility(
visible: deviceData['tag'] != null && deviceData['tag'] != '',
visible:
deviceData['tag'] != null && deviceData['tag'] != '',
child: Row(
spacing: 2,
children: [
SizedBox(
width: 8, height: 8, child: SvgPicture.asset(Assets.deviceTagIcon)),
width: 8,
height: 8,
child: SvgPicture.asset(Assets.deviceTagIcon)),
Flexible(
child: Text(
deviceData['tag'] ?? '',
@ -141,20 +148,23 @@ class DraggableCard extends StatelessWidget {
),
),
Visibility(
visible: deviceData['subSpace'] != null && deviceData['subSpace'] != '',
visible: deviceData['subSpace'] != null &&
deviceData['subSpace'] != '',
child: const SizedBox(
height: 4,
),
),
Visibility(
visible: deviceData['subSpace'] != null && deviceData['subSpace'] != '',
visible: deviceData['subSpace'] != null &&
deviceData['subSpace'] != '',
child: Row(
spacing: 2,
children: [
SizedBox(
width: 8,
height: 8,
child: SvgPicture.asset(Assets.spaceLocationIcon)),
child:
SvgPicture.asset(Assets.spaceLocationIcon)),
Flexible(
child: Text(
deviceData['subSpace'] ?? '',
@ -222,7 +232,8 @@ class DraggableCard extends StatelessWidget {
}
String _formatFunctionValue(DeviceFunctionData function) {
if (function.functionCode == 'temp_set' || function.functionCode == 'temp_current') {
if (function.functionCode == 'temp_set' ||
function.functionCode == 'temp_current') {
return '${(function.value / 10).toStringAsFixed(0)}°C';
} else if (function.functionCode.contains('countdown')) {
final seconds = function.value?.toInt() ?? 0;

View File

@ -17,12 +17,13 @@ class FunctionSlider extends StatelessWidget {
@override
Widget build(BuildContext context) {
final (min, max) = range;
final bool isValidRange = max > min;
final double value = initialValue is int
final isValidRange = max > min;
final value = initialValue is int
? (initialValue as int).toDouble()
: (initialValue as double);
final int? divisions = isValidRange ? ((max - min) / dividendOfRange).round() : null;
final divisions =
isValidRange ? ((max - min) / dividendOfRange).round() : null;
return Slider(
value: value.clamp(min, max),

View File

@ -62,7 +62,7 @@ class IfContainer extends StatelessWidget {
context: context,
data: state.ifItems[index],
removeComparetors: false,
dialogType: "IF");
dialogType: 'IF');
if (result != null) {
context.read<RoutineBloc>().add(

View File

@ -16,8 +16,9 @@ class FetchRoutineScenesAutomation extends StatelessWidget
Widget build(BuildContext context) {
return BlocBuilder<RoutineBloc, RoutineState>(
builder: (context, state) {
if (state.isLoading)
if (state.isLoading) {
return const Center(child: CircularProgressIndicator());
}
return SingleChildScrollView(
child: Padding(
@ -26,23 +27,23 @@ class FetchRoutineScenesAutomation extends StatelessWidget
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisSize: MainAxisSize.min,
children: [
_buildListTitle(context, "Scenes (Tap to Run)"),
_buildListTitle(context, 'Scenes (Tap to Run)'),
const SizedBox(height: 10),
Visibility(
visible: state.scenes.isNotEmpty,
replacement: _buildEmptyState(context, "No scenes found"),
replacement: _buildEmptyState(context, 'No scenes found'),
child: SizedBox(
height: 200,
child: _buildScenes(state),
),
),
const SizedBox(height: 10),
_buildListTitle(context, "Automations"),
_buildListTitle(context, 'Automations'),
const SizedBox(height: 3),
Visibility(
visible: state.automations.isNotEmpty,
replacement:
_buildEmptyState(context, "No automations found"),
_buildEmptyState(context, 'No automations found'),
child: SizedBox(
height: 200,
child: _buildAutomations(state),

View File

@ -67,15 +67,15 @@ class _RoutineViewCardState extends State<RoutineViewCard> {
@override
Widget build(BuildContext context) {
final double cardWidth = widget.isSmallScreenSize(context)
final cardWidth = widget.isSmallScreenSize(context)
? 120
: widget.isMediumScreenSize(context)
? 135
: 150;
final double cardHeight = widget.isSmallScreenSize(context) ? 190 : 200;
final cardHeight = widget.isSmallScreenSize(context) ? 190 : 200;
final double iconSize = widget.isSmallScreenSize(context)
final iconSize = widget.isSmallScreenSize(context)
? 70
: widget.isMediumScreenSize(context)
? 80
@ -99,41 +99,42 @@ class _RoutineViewCardState extends State<RoutineViewCard> {
child: Column(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: [
widget.cardType != ''
? Row(
mainAxisAlignment: MainAxisAlignment.end,
children: [
if (widget.isFromScenes ?? false)
InkWell(
onTap: _handleSceneTap,
child: Image.asset(
_showTemporaryCheck
? Assets.scenesPlayIcon
: Assets.scenesPlayIconCheck,
fit: BoxFit.contain,
),
)
else if (widget.isLoading)
const SizedBox(
width: 49,
height: 20,
child: Center(
child: SizedBox(
width: 16,
height: 16,
child: CircularProgressIndicator(strokeWidth: 2),
),
),
)
else
CupertinoSwitch(
activeTrackColor: ColorsManager.primaryColor,
value: widget.status == 'enable',
onChanged: widget.onChanged,
)
],
)
: const SizedBox(),
if (widget.cardType != '')
Row(
mainAxisAlignment: MainAxisAlignment.end,
children: [
if (widget.isFromScenes ?? false)
InkWell(
onTap: _handleSceneTap,
child: Image.asset(
_showTemporaryCheck
? Assets.scenesPlayIcon
: Assets.scenesPlayIconCheck,
fit: BoxFit.contain,
),
)
else if (widget.isLoading)
const SizedBox(
width: 49,
height: 20,
child: Center(
child: SizedBox(
width: 16,
height: 16,
child: CircularProgressIndicator(strokeWidth: 2),
),
),
)
else
CupertinoSwitch(
activeTrackColor: ColorsManager.primaryColor,
value: widget.status == 'enable',
onChanged: widget.onChanged,
)
],
)
else
const SizedBox(),
Column(
children: [
Center(
@ -159,8 +160,9 @@ class _RoutineViewCardState extends State<RoutineViewCard> {
height: iconSize,
width: iconSize,
fit: BoxFit.contain,
errorBuilder: (context, error, stackTrace) =>
Image.asset(
errorBuilder:
(context, error, stackTrace) =>
Image.asset(
Assets.logo,
height: iconSize,
width: iconSize,
@ -203,7 +205,8 @@ class _RoutineViewCardState extends State<RoutineViewCard> {
maxLines: 1,
style: context.textTheme.bodySmall?.copyWith(
color: ColorsManager.blackColor,
fontSize: widget.isSmallScreenSize(context) ? 10 : 12,
fontSize:
widget.isSmallScreenSize(context) ? 10 : 12,
),
),
if (widget.spaceName != '')
@ -222,8 +225,9 @@ class _RoutineViewCardState extends State<RoutineViewCard> {
maxLines: 1,
style: context.textTheme.bodySmall?.copyWith(
color: ColorsManager.blackColor,
fontSize:
widget.isSmallScreenSize(context) ? 10 : 12,
fontSize: widget.isSmallScreenSize(context)
? 10
: 12,
),
),
],

View File

@ -21,9 +21,12 @@ class PeriodOptions extends StatelessWidget {
builder: (context, state) {
return Column(
children: [
_buildRadioOption(context, EnumEffectivePeriodOptions.allDay, '24 Hours'),
_buildRadioOption(context, EnumEffectivePeriodOptions.daytime, 'Sunrise to Sunset'),
_buildRadioOption(context, EnumEffectivePeriodOptions.night, 'Sunset to Sunrise'),
_buildRadioOption(
context, EnumEffectivePeriodOptions.allDay, '24 Hours'),
_buildRadioOption(context, EnumEffectivePeriodOptions.daytime,
'Sunrise to Sunset'),
_buildRadioOption(
context, EnumEffectivePeriodOptions.night, 'Sunset to Sunrise'),
ListTile(
contentPadding: EdgeInsets.zero,
onTap: () => showCustomTimePicker(context),
@ -34,7 +37,8 @@ class PeriodOptions extends StatelessWidget {
fontWeight: FontWeight.w400,
fontSize: 14),
),
subtitle: state.customStartTime != null && state.customEndTime != null
subtitle: state.customStartTime != null &&
state.customEndTime != null
? Text(
'${"${state.customStartTime}"} - ${"${state.customEndTime}"}',
style: Theme.of(context).textTheme.bodyMedium!.copyWith(
@ -78,12 +82,16 @@ class PeriodOptions extends StatelessWidget {
title: Text(
EffectPeriodHelper.formatEnumValue(value),
style: Theme.of(context).textTheme.bodyMedium!.copyWith(
color: ColorsManager.blackColor, fontWeight: FontWeight.w400, fontSize: 12),
color: ColorsManager.blackColor,
fontWeight: FontWeight.w400,
fontSize: 12),
),
subtitle: Text(
subtitle,
style: Theme.of(context).textTheme.bodyMedium!.copyWith(
color: ColorsManager.textPrimaryColor, fontWeight: FontWeight.w400, fontSize: 10),
color: ColorsManager.textPrimaryColor,
fontWeight: FontWeight.w400,
fontSize: 10),
),
trailing: Radio<EnumEffectivePeriodOptions>(
value: value,

View File

@ -16,7 +16,9 @@ class RepeatDays extends StatelessWidget {
children: [
Text('Repeat',
style: Theme.of(context).textTheme.bodyMedium!.copyWith(
color: ColorsManager.textPrimaryColor, fontWeight: FontWeight.w400, fontSize: 14)),
color: ColorsManager.textPrimaryColor,
fontWeight: FontWeight.w400,
fontSize: 14)),
const SizedBox(width: 8),
BlocBuilder<EffectPeriodBloc, EffectPeriodState>(
builder: (context, state) {
@ -31,7 +33,8 @@ class RepeatDays extends StatelessWidget {
final day = entry.key;
final abbreviation = entry.value;
final dayIndex = effectiveBloc.getDayIndex(day);
final isSelected = state.selectedDaysBinary[dayIndex] == '1';
final isSelected =
state.selectedDaysBinary[dayIndex] == '1';
return Padding(
padding: const EdgeInsets.symmetric(horizontal: 3.0),
child: GestureDetector(
@ -42,7 +45,9 @@ class RepeatDays extends StatelessWidget {
decoration: BoxDecoration(
shape: BoxShape.circle,
border: Border.all(
color: isSelected ? Colors.grey : Colors.grey.shade300,
color: isSelected
? Colors.grey
: Colors.grey.shade300,
width: 1,
),
),
@ -53,7 +58,9 @@ class RepeatDays extends StatelessWidget {
abbreviation,
style: TextStyle(
fontSize: 16,
color: isSelected ? Colors.grey : Colors.grey.shade300,
color: isSelected
? Colors.grey
: Colors.grey.shade300,
),
),
),

View File

@ -74,15 +74,15 @@ class _RoutineDevicesState extends State<RoutineDevices> {
.toLowerCase()
.contains(state.searchText!.toLowerCase())
? DraggableCard(
imagePath: deviceData['imagePath'] as String,
title: deviceData['title'] as String,
imagePath: deviceData['imagePath']! as String,
title: deviceData['title']! as String,
deviceData: deviceData,
)
: const SizedBox.shrink();
} else {
return DraggableCard(
imagePath: deviceData['imagePath'] as String,
title: deviceData['title'] as String,
imagePath: deviceData['imagePath']! as String,
title: deviceData['title']! as String,
deviceData: deviceData,
);
}

View File

@ -24,8 +24,7 @@ class ACHelper {
required bool? removeComparetors,
required String dialogType,
}) async {
List<ACFunction> acFunctions =
functions.whereType<ACFunction>().where((function) {
final acFunctions = functions.whereType<ACFunction>().where((function) {
if (dialogType == 'THEN') {
return function.type == 'THEN' || function.type == 'BOTH';
}
@ -371,7 +370,7 @@ class ACHelper {
// return Container(
// padding: const EdgeInsets.symmetric(horizontal: 20, vertical: 10),
// decoration: BoxDecoration(
// color: ColorsManager.primaryColorWithOpacity.withOpacity(0.1),
// color: ColorsManager.primaryColorWithOpacity.withValues(alpha:0.1),
// borderRadius: BorderRadius.circular(10),
// ),
// child: Text(

View File

@ -3,8 +3,8 @@ import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:flutter_svg/flutter_svg.dart';
import 'package:syncrow_web/pages/routines/bloc/routine_bloc/routine_bloc.dart';
import 'package:syncrow_web/pages/routines/models/device_functions.dart';
import 'package:syncrow_web/pages/routines/widgets/dialog_header.dart';
import 'package:syncrow_web/pages/routines/widgets/dialog_footer.dart';
import 'package:syncrow_web/pages/routines/widgets/dialog_header.dart';
import 'package:syncrow_web/utils/constants/assets.dart';
class AutomationDialog extends StatefulWidget {
@ -31,9 +31,11 @@ class _AutomationDialogState extends State<AutomationDialog> {
@override
void initState() {
super.initState();
List<DeviceFunctionData>? functions =
context.read<RoutineBloc>().state.selectedFunctions[widget.uniqueCustomId];
for (DeviceFunctionData data in functions ?? []) {
final functions = context
.read<RoutineBloc>()
.state
.selectedFunctions[widget.uniqueCustomId];
for (final data in functions ?? []) {
if (data.entityId == widget.automationId) {
selectedAutomationActionExecutor = data.value;
}
@ -65,7 +67,8 @@ class _AutomationDialogState extends State<AutomationDialog> {
}),
),
ListTile(
leading: SvgPicture.asset(Assets.acPowerOff, width: 24, height: 24),
leading:
SvgPicture.asset(Assets.acPowerOff, width: 24, height: 24),
title: const Text('Disable'),
trailing: Radio<String?>(
value: 'rule_disable',

View File

@ -45,7 +45,8 @@ class CpsDialogValueSelector extends StatelessWidget {
operationName: operationName,
value: operation.value,
condition: selectedFunctionData?.condition,
valueDescription: selectedFunctionData?.valueDescription,
valueDescription:
selectedFunctionData?.valueDescription,
),
),
);

View File

@ -57,7 +57,7 @@ class CpsFunctionsList extends StatelessWidget {
'moving_max_dis',
'moving_range',
'presence_range',
if (dialogType == "IF") 'sensitivity',
if (dialogType == 'IF') 'sensitivity',
],
);
});

View File

@ -1,5 +1,6 @@
abstract final class CpsSliderHelpers {
static (double min, double max, double step) mappedRange(String functionCode) {
static (double min, double max, double step) mappedRange(
String functionCode) {
final (defaultMin, defaultMax) = sliderRange(functionCode);
final defaultDivdidend = dividendOfRange(functionCode);
return switch (functionCode) {
@ -62,7 +63,10 @@ abstract final class CpsSliderHelpers {
'perceptual_boundary' ||
'moving_boundary' =>
'M',
'moving_rigger_time' || 'moving_static_time' || 'none_body_time' => 'sec',
'moving_rigger_time' ||
'moving_static_time' ||
'none_body_time' =>
'sec',
_ => '',
};

View File

@ -9,14 +9,14 @@ import 'package:syncrow_web/pages/routines/widgets/dialog_header.dart';
class DelayHelper {
static Future<Map<String, dynamic>?> showDelayPickerDialog(
BuildContext context, Map<String, dynamic> data) async {
int hours = 0;
int minutes = 0;
var hours = 0;
var minutes = 0;
return showDialog<Map<String, dynamic>?>(
context: context,
builder: (BuildContext context) {
final routineBloc = context.read<RoutineBloc>();
int totalSec = 0;
var totalSec = 0;
final selectedFunctionData =
routineBloc.state.selectedFunctions[data['uniqueCustomId']] ?? [];
@ -43,7 +43,8 @@ class DelayHelper {
Expanded(
child: CupertinoTimerPicker(
mode: CupertinoTimerPickerMode.hm,
initialTimerDuration: Duration(hours: hours, minutes: minutes),
initialTimerDuration:
Duration(hours: hours, minutes: minutes),
onTimerDurationChanged: (Duration newDuration) {
hours = newDuration.inHours;
minutes = newDuration.inMinutes % 60;
@ -55,7 +56,7 @@ class DelayHelper {
Navigator.of(context).pop();
},
onConfirm: () {
int totalSeconds = (hours * 3600) + (minutes * 60);
final totalSeconds = (hours * 3600) + (minutes * 60);
context.read<RoutineBloc>().add(AddFunctionToRoutine(
[
DeviceFunctionData(

View File

@ -38,10 +38,10 @@ class DiscardDialog {
color: ColorsManager.red,
fontWeight: FontWeight.bold,
),
onDismissText: "Dont Close",
onConfirmText: "Close",
onDismissText: 'Dont Close',
onConfirmText: 'Close',
onDismissColor: ColorsManager.grayColor,
onConfirmColor: ColorsManager.red.withOpacity(0.8),
onConfirmColor: ColorsManager.red.withValues(alpha: 0.8),
onDismiss: () {
Navigator.pop(context);
},

View File

@ -8,13 +8,14 @@ import 'package:syncrow_web/utils/extension/build_context_x.dart';
import 'package:time_picker_spinner/time_picker_spinner.dart';
class EffectPeriodHelper {
static Future<List<String>?> showCustomTimePicker(BuildContext context) async {
String selectedStartTime = "00:00";
String selectedEndTime = "23:59";
PageController pageController = PageController(initialPage: 0);
static Future<List<String>?> showCustomTimePicker(
BuildContext context) async {
var selectedStartTime = '00:00';
var selectedEndTime = '23:59';
final pageController = PageController(initialPage: 0);
DateTime startDateTime = DateTime(2022, 1, 1, 0, 0);
DateTime endDateTime = DateTime(2022, 1, 1, 23, 59);
final startDateTime = DateTime(2022, 1, 1, 0, 0);
final endDateTime = DateTime(2022, 1, 1, 23, 59);
context.customAlertDialog(
alertBody: SizedBox(
@ -46,7 +47,7 @@ class EffectPeriodHelper {
],
),
),
title: "Custom",
title: 'Custom',
onConfirm: () {
context.read<EffectPeriodBloc>().add(
SetCustomTime(selectedStartTime, selectedEndTime),
@ -88,7 +89,7 @@ class EffectPeriodHelper {
),
TextButton(
onPressed: () {},
child: Text(isStartTime ? "Start" : "End",
child: Text(isStartTime ? 'Start' : 'End',
style: Theme.of(context).textTheme.bodyMedium!.copyWith(
color: ColorsManager.textPrimaryColor,
fontWeight: FontWeight.w400,
@ -135,17 +136,17 @@ class EffectPeriodHelper {
static String formatEnumValue(EnumEffectivePeriodOptions value) {
switch (value) {
case EnumEffectivePeriodOptions.allDay:
return "All Day";
return 'All Day';
case EnumEffectivePeriodOptions.daytime:
return "Daytime";
return 'Daytime';
case EnumEffectivePeriodOptions.night:
return "Night";
return 'Night';
case EnumEffectivePeriodOptions.custom:
return "Custom";
return 'Custom';
case EnumEffectivePeriodOptions.none:
return "None";
return 'None';
default:
return "";
return '';
}
}
}

View File

@ -7,7 +7,6 @@ import 'package:syncrow_web/pages/routines/models/device_functions.dart';
import 'package:syncrow_web/pages/routines/models/flush/flush_functions.dart';
import 'package:syncrow_web/pages/routines/widgets/custom_routines_textbox.dart';
import 'package:syncrow_web/pages/routines/widgets/routine_dialogs/flush_presence_sensor/flush_operational_values_list.dart';
import 'package:syncrow_web/pages/routines/widgets/slider_value_selector.dart';
class FlushValueSelectorWidget extends StatelessWidget {
final String selectedFunction;
@ -62,7 +61,7 @@ class FlushValueSelectorWidget extends StatelessWidget {
selectedFunction == FlushMountedPresenceSensorModel.codeFarDetection;
final isDistanceDetection = isNearDetection || isFarDetection;
double initialValue = (functionData.value as num?)?.toDouble() ?? 0.0;
var initialValue = (functionData.value as num?)?.toDouble() ?? 0.0;
if (isDistanceDetection) {
initialValue = initialValue / 100;
@ -157,7 +156,7 @@ class FlushValueSelectorWidget extends StatelessWidget {
String get getDisplayText {
final num? value = functionData.value;
double displayValue = value?.toDouble() ?? 0.0;
var displayValue = value?.toDouble() ?? 0.0;
if (functionData.functionCode ==
FlushMountedPresenceSensorModel.codeNearDetection ||

View File

@ -49,8 +49,6 @@ class _TimeWheelPickerState extends State<TimeWheelPicker> {
}
}
@override
void dispose() {
_hoursController.dispose();
@ -103,7 +101,7 @@ class _TimeWheelPickerState extends State<TimeWheelPicker> {
}
void _handleTimeChange(int hours, int minutes, int seconds) {
int total = hours * 3600 + minutes * 60 + seconds;
var total = hours * 3600 + minutes * 60 + seconds;
if (total > 10000) {
hours = 2;
minutes = 46;

View File

@ -45,7 +45,8 @@ class GatewayDialogValueSelector extends StatelessWidget {
operationName: operationName,
value: operation.value,
condition: selectedFunctionData?.condition,
valueDescription: selectedFunctionData?.valueDescription,
valueDescription:
selectedFunctionData?.valueDescription,
),
),
);

View File

@ -25,8 +25,7 @@ class OneGangSwitchHelper {
required String uniqueCustomId,
required bool removeComparetors,
}) async {
List<BaseSwitchFunction> oneGangFunctions =
functions.whereType<BaseSwitchFunction>().toList();
final oneGangFunctions = functions.whereType<BaseSwitchFunction>().toList();
return showDialog<Map<String, dynamic>?>(
context: context,
@ -246,9 +245,9 @@ class OneGangSwitchHelper {
withSpecialChar: false,
currentCondition: selectedFunctionData?.condition,
dialogType: dialogType,
sliderRange: (0, 43200),
sliderRange: (0, 43200),
displayedValue: (initialValue ?? 0).toString(),
initialValue: (initialValue ?? 0).toString(),
initialValue: (initialValue ?? 0).toString(),
onConditionChanged: (condition) {
context.read<FunctionBloc>().add(
AddFunction(

View File

@ -81,6 +81,4 @@ class EnergyOperationalValuesList extends StatelessWidget {
),
);
}
}

View File

@ -27,13 +27,11 @@ class EnergyValueSelectorWidget extends StatelessWidget {
@override
Widget build(BuildContext context) {
final selectedFn =
functions.firstWhere((f) => f.code == selectedFunction);
final selectedFn = functions.firstWhere((f) => f.code == selectedFunction);
final values = selectedFn.getOperationalValues();
final step = selectedFn.step ?? 1.0;
final _unit = selectedFn.unit ?? '';
final (double, double) sliderRange =
(selectedFn.min ?? 0.0, selectedFn.max ?? 100.0);
final step = selectedFn.step ?? 1.0;
final unit = selectedFn.unit ?? '';
final sliderRange = (selectedFn.min ?? 0.0, selectedFn.max ?? 100.0);
if (_isSliderFunction(selectedFunction)) {
return CustomRoutinesTextbox(
@ -65,7 +63,7 @@ class EnergyValueSelectorWidget extends StatelessWidget {
),
),
),
unit: _unit,
unit: unit,
dividendOfRange: 1,
stepIncreaseAmount: step,
);

View File

@ -1,3 +1,4 @@
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:syncrow_web/pages/routines/bloc/effective_period/effect_period_bloc.dart';
@ -13,7 +14,6 @@ import 'package:syncrow_web/pages/routines/view/effective_period_view.dart';
import 'package:syncrow_web/pages/routines/widgets/delete_scene.dart';
import 'package:syncrow_web/pages/routines/widgets/dialog_header.dart';
import 'package:syncrow_web/utils/color_manager.dart';
import 'package:flutter/cupertino.dart';
class SettingHelper {
static Future<String?> showSettingDialog({
@ -30,14 +30,16 @@ class SettingHelper {
providers: [
if (effectiveTime != null)
BlocProvider(
create: (_) => EffectPeriodBloc()..add(InitialEffectPeriodEvent(effectiveTime)),
create: (_) => EffectPeriodBloc()
..add(InitialEffectPeriodEvent(effectiveTime)),
),
if (effectiveTime == null)
BlocProvider(
create: (_) => EffectPeriodBloc(),
),
BlocProvider(
create: (_) => SettingBloc()..add(InitialEvent(selectedIcon: iconId ?? ''))),
create: (_) => SettingBloc()
..add(InitialEvent(selectedIcon: iconId ?? ''))),
],
child: AlertDialog(
contentPadding: EdgeInsets.zero,
@ -45,15 +47,18 @@ class SettingHelper {
builder: (context, effectPeriodState) {
return BlocBuilder<SettingBloc, SettingState>(
builder: (context, settingState) {
String selectedIcon = '';
List<IconModel> list = [];
var selectedIcon = '';
var list = <IconModel>[];
if (settingState is TabToRunSettingLoaded) {
selectedIcon = settingState.selectedIcon;
list = settingState.iconList;
}
return Container(
width: context.read<SettingBloc>().isExpanded ? 800 : 400,
height: context.read<SettingBloc>().isExpanded && isAutomation ? 500 : 350,
height:
context.read<SettingBloc>().isExpanded && isAutomation
? 500
: 350,
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.circular(20),
@ -76,14 +81,18 @@ class SettingHelper {
children: [
Container(
padding: const EdgeInsets.only(
top: 10, left: 10, right: 10, bottom: 10),
top: 10,
left: 10,
right: 10,
bottom: 10),
child: Column(
children: [
InkWell(
onTap: () {},
child: Row(
mainAxisAlignment:
MainAxisAlignment.spaceBetween,
MainAxisAlignment
.spaceBetween,
children: [
Text(
'Validity',
@ -91,14 +100,18 @@ class SettingHelper {
.textTheme
.bodyMedium!
.copyWith(
color:
ColorsManager.textPrimaryColor,
fontWeight: FontWeight.w400,
color: ColorsManager
.textPrimaryColor,
fontWeight:
FontWeight
.w400,
fontSize: 14),
),
const Icon(
Icons.arrow_forward_ios_outlined,
color: ColorsManager.textGray,
Icons
.arrow_forward_ios_outlined,
color: ColorsManager
.textGray,
size: 15,
)
],
@ -108,22 +121,27 @@ class SettingHelper {
height: 5,
),
const Divider(
color: ColorsManager.graysColor,
color:
ColorsManager.graysColor,
),
const SizedBox(
height: 5,
),
InkWell(
onTap: () {
BlocProvider.of<SettingBloc>(context).add(
FetchIcons(
BlocProvider.of<
SettingBloc>(
context)
.add(FetchIcons(
expanded: !context
.read<SettingBloc>()
.read<
SettingBloc>()
.isExpanded));
},
child: Row(
mainAxisAlignment:
MainAxisAlignment.spaceBetween,
MainAxisAlignment
.spaceBetween,
children: [
Text(
'Effective Period',
@ -131,14 +149,18 @@ class SettingHelper {
.textTheme
.bodyMedium!
.copyWith(
color:
ColorsManager.textPrimaryColor,
fontWeight: FontWeight.w400,
color: ColorsManager
.textPrimaryColor,
fontWeight:
FontWeight
.w400,
fontSize: 14),
),
const Icon(
Icons.arrow_forward_ios_outlined,
color: ColorsManager.textGray,
Icons
.arrow_forward_ios_outlined,
color: ColorsManager
.textGray,
size: 15,
)
],
@ -148,13 +170,16 @@ class SettingHelper {
height: 5,
),
const Divider(
color: ColorsManager.graysColor,
color:
ColorsManager.graysColor,
),
const SizedBox(
height: 5,
),
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
mainAxisAlignment:
MainAxisAlignment
.spaceBetween,
children: [
Text(
'Executed by',
@ -162,8 +187,11 @@ class SettingHelper {
.textTheme
.bodyMedium!
.copyWith(
color: ColorsManager.textPrimaryColor,
fontWeight: FontWeight.w400,
color: ColorsManager
.textPrimaryColor,
fontWeight:
FontWeight
.w400,
fontSize: 14),
),
Text('Cloud',
@ -171,12 +199,19 @@ class SettingHelper {
.textTheme
.bodyMedium!
.copyWith(
color: ColorsManager.textGray,
fontWeight: FontWeight.w400,
color:
ColorsManager
.textGray,
fontWeight:
FontWeight
.w400,
fontSize: 14)),
],
),
if (context.read<RoutineBloc>().state.isUpdate ??
if (context
.read<RoutineBloc>()
.state
.isUpdate ??
false)
const DeleteSceneWidget()
],
@ -188,20 +223,27 @@ class SettingHelper {
children: [
Container(
padding: const EdgeInsets.only(
top: 10, left: 10, right: 10, bottom: 10),
top: 10,
left: 10,
right: 10,
bottom: 10),
child: Column(
children: [
InkWell(
onTap: () {
BlocProvider.of<SettingBloc>(context).add(
FetchIcons(
BlocProvider.of<
SettingBloc>(
context)
.add(FetchIcons(
expanded: !context
.read<SettingBloc>()
.read<
SettingBloc>()
.isExpanded));
},
child: Row(
mainAxisAlignment:
MainAxisAlignment.spaceBetween,
MainAxisAlignment
.spaceBetween,
children: [
Text(
'Icons',
@ -209,14 +251,18 @@ class SettingHelper {
.textTheme
.bodyMedium!
.copyWith(
color:
ColorsManager.textPrimaryColor,
fontWeight: FontWeight.w400,
color: ColorsManager
.textPrimaryColor,
fontWeight:
FontWeight
.w400,
fontSize: 14),
),
const Icon(
Icons.arrow_forward_ios_outlined,
color: ColorsManager.textGray,
Icons
.arrow_forward_ios_outlined,
color: ColorsManager
.textGray,
size: 15,
)
],
@ -226,13 +272,16 @@ class SettingHelper {
height: 5,
),
const Divider(
color: ColorsManager.graysColor,
color:
ColorsManager.graysColor,
),
const SizedBox(
height: 5,
),
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
mainAxisAlignment:
MainAxisAlignment
.spaceBetween,
children: [
Text(
'Show on devices page',
@ -240,23 +289,30 @@ class SettingHelper {
.textTheme
.bodyMedium!
.copyWith(
color: ColorsManager.textPrimaryColor,
fontWeight: FontWeight.w400,
color: ColorsManager
.textPrimaryColor,
fontWeight:
FontWeight
.w400,
fontSize: 14),
),
Row(
mainAxisAlignment: MainAxisAlignment.end,
mainAxisAlignment:
MainAxisAlignment.end,
children: [
Container(
height: 30,
width: 1,
color: ColorsManager.graysColor,
color: ColorsManager
.graysColor,
),
Transform.scale(
scale: .8,
child: CupertinoSwitch(
child:
CupertinoSwitch(
value: true,
onChanged: (value) {},
onChanged:
(value) {},
applyTheme: true,
),
),
@ -268,13 +324,16 @@ class SettingHelper {
height: 5,
),
const Divider(
color: ColorsManager.graysColor,
color:
ColorsManager.graysColor,
),
const SizedBox(
height: 5,
),
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
mainAxisAlignment:
MainAxisAlignment
.spaceBetween,
children: [
Text(
'Executed by',
@ -282,8 +341,11 @@ class SettingHelper {
.textTheme
.bodyMedium!
.copyWith(
color: ColorsManager.textPrimaryColor,
fontWeight: FontWeight.w400,
color: ColorsManager
.textPrimaryColor,
fontWeight:
FontWeight
.w400,
fontSize: 14),
),
Text('Cloud',
@ -291,12 +353,19 @@ class SettingHelper {
.textTheme
.bodyMedium!
.copyWith(
color: ColorsManager.textGray,
fontWeight: FontWeight.w400,
color:
ColorsManager
.textGray,
fontWeight:
FontWeight
.w400,
fontSize: 14)),
],
),
if (context.read<RoutineBloc>().state.isUpdate ??
if (context
.read<RoutineBloc>()
.state
.isUpdate ??
false)
const DeleteSceneWidget()
],
@ -304,12 +373,14 @@ class SettingHelper {
],
),
),
if (context.read<SettingBloc>().isExpanded && !isAutomation)
if (context.read<SettingBloc>().isExpanded &&
!isAutomation)
SizedBox(
width: 400,
height: 150,
child: settingState is LoadingState
? const Center(child: CircularProgressIndicator())
? const Center(
child: CircularProgressIndicator())
: GridView.builder(
gridDelegate:
const SliverGridDelegateWithFixedCrossAxisCount(
@ -326,7 +397,8 @@ class SettingHelper {
height: 35,
child: InkWell(
onTap: () {
BlocProvider.of<SettingBloc>(context)
BlocProvider.of<SettingBloc>(
context)
.add(SelectIcon(
iconId: iconModel.uuid,
));
@ -335,13 +407,17 @@ class SettingHelper {
child: SizedBox(
child: ClipOval(
child: Container(
padding: const EdgeInsets.all(1),
padding:
const EdgeInsets.all(
1),
decoration: BoxDecoration(
border: Border.all(
color: selectedIcon == iconModel.uuid
color: selectedIcon ==
iconModel.uuid
? ColorsManager
.primaryColorWithOpacity
: Colors.transparent,
: Colors
.transparent,
width: 2,
),
shape: BoxShape.circle,
@ -356,8 +432,12 @@ class SettingHelper {
);
},
)),
if (context.read<SettingBloc>().isExpanded && isAutomation)
const SizedBox(height: 350, width: 400, child: EffectivePeriodView())
if (context.read<SettingBloc>().isExpanded &&
isAutomation)
const SizedBox(
height: 350,
width: 400,
child: EffectivePeriodView())
],
),
Container(
@ -381,23 +461,33 @@ class SettingHelper {
alignment: AlignmentDirectional.center,
child: Text(
'Cancel',
style: Theme.of(context).textTheme.bodyMedium!.copyWith(
style: Theme.of(context)
.textTheme
.bodyMedium!
.copyWith(
color: ColorsManager.textGray,
),
),
),
),
),
Container(width: 1, height: 50, color: ColorsManager.greyColor),
Container(
width: 1,
height: 50,
color: ColorsManager.greyColor),
Expanded(
child: InkWell(
onTap: () {
if (isAutomation) {
BlocProvider.of<RoutineBloc>(context).add(
EffectiveTimePeriodEvent(EffectiveTime(
start: effectPeriodState.customStartTime!,
end: effectPeriodState.customEndTime!,
loops: effectPeriodState.selectedDaysBinary)));
EffectiveTimePeriodEvent(
EffectiveTime(
start: effectPeriodState
.customStartTime!,
end: effectPeriodState
.customEndTime!,
loops: effectPeriodState
.selectedDaysBinary)));
Navigator.of(context).pop();
} else {
Navigator.of(context).pop(selectedIcon);
@ -407,8 +497,12 @@ class SettingHelper {
alignment: AlignmentDirectional.center,
child: Text(
'Confirm',
style: Theme.of(context).textTheme.bodyMedium!.copyWith(
color: ColorsManager.primaryColorWithOpacity,
style: Theme.of(context)
.textTheme
.bodyMedium!
.copyWith(
color: ColorsManager
.primaryColorWithOpacity,
),
),
),

View File

@ -24,8 +24,7 @@ class ThreeGangSwitchHelper {
required String dialogType,
required bool removeComparetors,
}) async {
List<BaseSwitchFunction> switchFunctions =
functions.whereType<BaseSwitchFunction>().toList();
final switchFunctions = functions.whereType<BaseSwitchFunction>().toList();
return showDialog<Map<String, dynamic>?>(
context: context,

View File

@ -25,8 +25,7 @@ class TwoGangSwitchHelper {
required bool removeComparetors,
required String dialogType,
}) async {
List<BaseSwitchFunction> switchFunctions =
functions.whereType<BaseSwitchFunction>().toList();
final switchFunctions = functions.whereType<BaseSwitchFunction>().toList();
return showDialog<Map<String, dynamic>?>(
context: context,
@ -237,7 +236,7 @@ class TwoGangSwitchHelper {
DeviceFunctionData? selectedFunctionData,
// Function(String) onConditionChanged,
) {
final conditions = ["<", "==", ">"];
final conditions = ['<', '==', '>'];
return ToggleButtons(
onPressed: (int index) {
@ -264,8 +263,8 @@ class TwoGangSwitchHelper {
minWidth: 40.0,
),
isSelected:
conditions.map((c) => c == (currentCondition ?? "==")).toList(),
children: conditions.map((c) => Text(c)).toList(),
conditions.map((c) => c == (currentCondition ?? '==')).toList(),
children: conditions.map(Text.new).toList(),
);
}
@ -280,7 +279,7 @@ class TwoGangSwitchHelper {
return Container(
padding: const EdgeInsets.symmetric(horizontal: 20, vertical: 10),
decoration: BoxDecoration(
color: ColorsManager.primaryColorWithOpacity.withOpacity(0.1),
color: ColorsManager.primaryColorWithOpacity.withValues(alpha: 0.1),
borderRadius: BorderRadius.circular(10),
),
child: Text(

View File

@ -49,8 +49,6 @@ class _TimeWheelPickerState extends State<TimeWheelPicker> {
}
}
@override
void dispose() {
_hoursController.dispose();
@ -103,7 +101,7 @@ class _TimeWheelPickerState extends State<TimeWheelPicker> {
}
void _handleTimeChange(int hours, int minutes, int seconds) {
int total = hours * 3600 + minutes * 60 + seconds;
var total = hours * 3600 + minutes * 60 + seconds;
if (total > 10000) {
hours = 2;
minutes = 46;

View File

@ -63,7 +63,8 @@ class _WallPresenceSensorState extends State<WallPresenceSensor> {
@override
void initState() {
super.initState();
_wpsFunctions = widget.functions.whereType<WpsFunctions>().where((function) {
_wpsFunctions =
widget.functions.whereType<WpsFunctions>().where((function) {
if (widget.dialogType == 'THEN') {
return function.type == 'THEN' || function.type == 'BOTH';
}

View File

@ -30,7 +30,8 @@ class WpsOperationalValuesList extends StatelessWidget {
: ListView.builder(
padding: const EdgeInsets.all(20),
itemCount: values.length,
itemBuilder: (context, index) => _buildValueItem(context, values[index]),
itemBuilder: (context, index) =>
_buildValueItem(context, values[index]),
);
}
@ -61,7 +62,8 @@ class WpsOperationalValuesList extends StatelessWidget {
Widget _buildValueIcon(context, WpsOperationalValue value) {
return Column(
children: [
if (_shouldShowTextDescription) Text(value.description.replaceAll("cm", '')),
if (_shouldShowTextDescription)
Text(value.description.replaceAll('cm', '')),
SvgPicture.asset(value.icon, width: 25, height: 25),
],
);

View File

@ -61,5 +61,4 @@ class WaterHeaterOperationalValuesList extends StatelessWidget {
groupValue: selectedValue,
onChanged: (_) => onSelect(value));
}
}

View File

@ -12,7 +12,7 @@ class WaterHeaterValueSelectorWidget extends StatelessWidget {
final DeviceFunctionData functionData;
final List<WaterHeaterFunctions> whFunctions;
final AllDevicesModel? device;
final String dialogType;
final String dialogType;
const WaterHeaterValueSelectorWidget({
required this.selectedFunction,
@ -39,14 +39,13 @@ class WaterHeaterValueSelectorWidget extends StatelessWidget {
mainAxisAlignment: MainAxisAlignment.center,
children: [
_buildCountDownSlider(
context,
functionData.value,
device,
selectedFn.operationName,
functionData,
selectedFunction,
dialogType
),
context,
functionData.value,
device,
selectedFn.operationName,
functionData,
selectedFunction,
dialogType),
const SizedBox(height: 10),
],
);

View File

@ -15,7 +15,8 @@ class RoutineSearchAndButtons extends StatefulWidget {
});
@override
State<RoutineSearchAndButtons> createState() => _RoutineSearchAndButtonsState();
State<RoutineSearchAndButtons> createState() =>
_RoutineSearchAndButtonsState();
}
class _RoutineSearchAndButtonsState extends State<RoutineSearchAndButtons> {
@ -61,8 +62,9 @@ class _RoutineSearchAndButtonsState extends State<RoutineSearchAndButtons> {
children: [
ConstrainedBox(
constraints: BoxConstraints(
maxWidth:
constraints.maxWidth > 700 ? 450 : constraints.maxWidth - 32),
maxWidth: constraints.maxWidth > 700
? 450
: constraints.maxWidth - 32),
child: Column(
mainAxisAlignment: MainAxisAlignment.start,
crossAxisAlignment: CrossAxisAlignment.start,
@ -71,10 +73,13 @@ class _RoutineSearchAndButtonsState extends State<RoutineSearchAndButtons> {
children: [
Text('* ',
style: context.textTheme.bodyMedium!
.copyWith(color: ColorsManager.red, fontSize: 13)),
.copyWith(
color: ColorsManager.red,
fontSize: 13)),
Text(
'Routine Name',
style: context.textTheme.bodyMedium!.copyWith(
style: context.textTheme.bodyMedium!
.copyWith(
fontSize: 13,
fontWeight: FontWeight.w600,
color: ColorsManager.blackColor,
@ -88,20 +93,23 @@ class _RoutineSearchAndButtonsState extends State<RoutineSearchAndButtons> {
decoration: containerWhiteDecoration,
child: TextFormField(
style: context.textTheme.bodyMedium!
.copyWith(color: ColorsManager.blackColor),
.copyWith(
color: ColorsManager.blackColor),
controller: _nameController,
decoration: InputDecoration(
hintText: 'Please enter the name',
hintStyle: context.textTheme.bodyMedium!
.copyWith(fontSize: 12, color: ColorsManager.grayColor),
.copyWith(
fontSize: 12,
color: ColorsManager.grayColor),
contentPadding:
const EdgeInsets.symmetric(horizontal: 12, vertical: 10),
const EdgeInsets.symmetric(
horizontal: 12, vertical: 10),
border: InputBorder.none,
),
onTapOutside: (_) {
context
.read<RoutineBloc>()
.add(SetRoutineName(_nameController.text));
context.read<RoutineBloc>().add(
SetRoutineName(_nameController.text));
},
validator: (value) {
if (value == null || value.isEmpty) {
@ -114,41 +122,44 @@ class _RoutineSearchAndButtonsState extends State<RoutineSearchAndButtons> {
],
),
),
(constraints.maxWidth <= 1000)
? const SizedBox()
: SizedBox(
height: 40,
width: 200,
child: Center(
child: DefaultButton(
onPressed: state.isAutomation || state.isTabToRun
? () async {
final result = await SettingHelper.showSettingDialog(
context: context,
iconId: state.selectedIcon ?? '',
);
if (result != null) {
context
.read<RoutineBloc>()
.add(AddSelectedIcon(result));
}
}
: null,
borderRadius: 15,
elevation: 0,
borderColor: ColorsManager.greyColor,
backgroundColor: ColorsManager.boxColor,
child: const Text(
'Settings',
textAlign: TextAlign.center,
style: TextStyle(
fontSize: 12,
color: ColorsManager.primaryColor,
),
),
if (constraints.maxWidth <= 1000)
const SizedBox()
else
SizedBox(
height: 40,
width: 200,
child: Center(
child: DefaultButton(
onPressed: state.isAutomation ||
state.isTabToRun
? () async {
final result = await SettingHelper
.showSettingDialog(
context: context,
iconId: state.selectedIcon ?? '',
);
if (result != null) {
context
.read<RoutineBloc>()
.add(AddSelectedIcon(result));
}
}
: null,
borderRadius: 15,
elevation: 0,
borderColor: ColorsManager.greyColor,
backgroundColor: ColorsManager.boxColor,
child: const Text(
'Settings',
textAlign: TextAlign.center,
style: TextStyle(
fontSize: 12,
color: ColorsManager.primaryColor,
),
),
),
),
),
],
),
),
@ -186,10 +197,12 @@ class _RoutineSearchAndButtonsState extends State<RoutineSearchAndButtons> {
child: Center(
child: DefaultButton(
onPressed: () async {
if (state.routineName == null || state.routineName!.isEmpty) {
if (state.routineName == null ||
state.routineName!.isEmpty) {
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(
content: const Text('Please enter the routine name'),
content: const Text(
'Please enter the routine name'),
duration: const Duration(seconds: 2),
backgroundColor: ColorsManager.red,
action: SnackBarAction(
@ -203,10 +216,12 @@ class _RoutineSearchAndButtonsState extends State<RoutineSearchAndButtons> {
return;
}
if (state.ifItems.isEmpty || state.thenItems.isEmpty) {
if (state.ifItems.isEmpty ||
state.thenItems.isEmpty) {
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(
content: const Text('Please add if and then condition'),
content: const Text(
'Please add if and then condition'),
duration: const Duration(seconds: 2),
backgroundColor: ColorsManager.red,
action: SnackBarAction(
@ -221,8 +236,10 @@ class _RoutineSearchAndButtonsState extends State<RoutineSearchAndButtons> {
}
// final result =
// await
BlocProvider.of<RoutineBloc>(context).add(ResetErrorMessage());
SaveRoutineHelper.showSaveRoutineDialog(context);
BlocProvider.of<RoutineBloc>(context)
.add(ResetErrorMessage());
SaveRoutineHelper.showSaveRoutineDialog(
context);
// if (result != null && result) {
// BlocProvider.of<RoutineBloc>(context).add(
// const CreateNewRoutineViewEvent(createRoutineView: false),
@ -261,10 +278,14 @@ class _RoutineSearchAndButtonsState extends State<RoutineSearchAndButtons> {
child: DefaultButton(
onPressed: state.isAutomation || state.isTabToRun
? () async {
final result = await SettingHelper.showSettingDialog(
context: context, iconId: state.selectedIcon ?? '');
final result =
await SettingHelper.showSettingDialog(
context: context,
iconId: state.selectedIcon ?? '');
if (result != null) {
context.read<RoutineBloc>().add(AddSelectedIcon(result));
context
.read<RoutineBloc>()
.add(AddSelectedIcon(result));
}
}
: null,
@ -314,10 +335,12 @@ class _RoutineSearchAndButtonsState extends State<RoutineSearchAndButtons> {
child: Center(
child: DefaultButton(
onPressed: () async {
if (state.routineName == null || state.routineName!.isEmpty) {
if (state.routineName == null ||
state.routineName!.isEmpty) {
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(
content: const Text('Please enter the routine name'),
content: const Text(
'Please enter the routine name'),
duration: const Duration(seconds: 2),
backgroundColor: ColorsManager.red,
action: SnackBarAction(
@ -331,10 +354,12 @@ class _RoutineSearchAndButtonsState extends State<RoutineSearchAndButtons> {
return;
}
if (state.ifItems.isEmpty || state.thenItems.isEmpty) {
if (state.ifItems.isEmpty ||
state.thenItems.isEmpty) {
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(
content: const Text('Please add if and then condition'),
content: const Text(
'Please add if and then condition'),
duration: const Duration(seconds: 2),
backgroundColor: ColorsManager.red,
action: SnackBarAction(
@ -349,7 +374,8 @@ class _RoutineSearchAndButtonsState extends State<RoutineSearchAndButtons> {
}
// final result =
// await
BlocProvider.of<RoutineBloc>(context).add(ResetErrorMessage());
BlocProvider.of<RoutineBloc>(context)
.add(ResetErrorMessage());
SaveRoutineHelper.showSaveRoutineDialog(context);
// if (result != null && result) {
// BlocProvider.of<RoutineBloc>(context).add(

View File

@ -27,14 +27,16 @@ class _ScenesAndAutomationsState extends State<ScenesAndAutomations> {
return BlocBuilder<RoutineBloc, RoutineState>(
builder: (context, state) {
if (!state.isLoading) {
var scenes = [...state.scenes, ...state.automations];
final scenes = [...state.scenes, ...state.automations];
return Wrap(
spacing: 10,
runSpacing: 10,
children: scenes.asMap().entries.map((entry) {
final scene = entry.value;
if (state.searchText != null && state.searchText!.isNotEmpty) {
return scene.name.toLowerCase().contains(state.searchText!.toLowerCase())
return scene.name
.toLowerCase()
.contains(state.searchText!.toLowerCase())
? DraggableCard(
imagePath: scene.icon ?? Assets.loginLogo,
title: scene.name,

View File

@ -6,7 +6,8 @@ import 'package:syncrow_web/pages/routines/widgets/routines_title_widget.dart';
import 'package:syncrow_web/utils/color_manager.dart';
import 'package:syncrow_web/utils/helpers/responsice_layout_helper/responsive_layout_helper.dart';
class ConditionTitleAndSearchBar extends StatelessWidget with HelperResponsiveLayout {
class ConditionTitleAndSearchBar extends StatelessWidget
with HelperResponsiveLayout {
const ConditionTitleAndSearchBar({
super.key,
});

View File

@ -30,123 +30,118 @@ class ThenContainer extends StatelessWidget {
style: TextStyle(
fontSize: 18, fontWeight: FontWeight.bold)),
const SizedBox(height: 16),
state.isLoading && state.isUpdate == true
? const Center(
child: CircularProgressIndicator(),
)
: Wrap(
spacing: 8,
runSpacing: 8,
children: List.generate(
state.thenItems.length,
(index) => GestureDetector(
onTap: () async {
if (state.thenItems[index]
['deviceId'] ==
'delay') {
final result = await DelayHelper
.showDelayPickerDialog(context,
state.thenItems[index]);
if (result != null) {
context
.read<RoutineBloc>()
.add(AddToThenContainer({
...state.thenItems[index],
'imagePath': Assets.delay,
'title': 'Delay',
}));
}
return;
}
if (state.thenItems[index]['type'] ==
'automation') {
final result = await showDialog<bool>(
context: context,
builder: (BuildContext context) =>
AutomationDialog(
automationName:
state.thenItems[index]
['name'] ??
'Automation',
automationId:
state.thenItems[index]
['deviceId'] ??
'',
uniqueCustomId:
state.thenItems[index]
['uniqueCustomId'],
),
);
if (result != null) {
context
.read<RoutineBloc>()
.add(AddToThenContainer({
...state.thenItems[index],
'imagePath':
Assets.automation,
'title':
state.thenItems[index]
['name'] ??
state.thenItems[index]
['title'],
}));
}
return;
}
final result = await DeviceDialogHelper
.showDeviceDialog(
context: context,
data: state.thenItems[index],
removeComparetors: true,
dialogType: "THEN");
if (state.isLoading && state.isUpdate == true)
const Center(
child: CircularProgressIndicator(),
)
else
Wrap(
spacing: 8,
runSpacing: 8,
children: List.generate(
state.thenItems.length,
(index) => GestureDetector(
onTap: () async {
if (state.thenItems[index]['deviceId'] ==
'delay') {
final result = await DelayHelper
.showDelayPickerDialog(context,
state.thenItems[index]);
if (result != null) {
context.read<RoutineBloc>().add(
AddToThenContainer(
state.thenItems[index]));
} else if (![
'AC',
'1G',
'2G',
'3G',
'WPS',
'CPS',
"GW",
"NCPS",
'WH',
].contains(state.thenItems[index]
['productType'])) {
context.read<RoutineBloc>().add(
AddToThenContainer(
state.thenItems[index]));
context
.read<RoutineBloc>()
.add(AddToThenContainer({
...state.thenItems[index],
'imagePath': Assets.delay,
'title': 'Delay',
}));
}
return;
}
if (state.thenItems[index]['type'] ==
'automation') {
final result = await showDialog<bool>(
context: context,
builder: (BuildContext context) =>
AutomationDialog(
automationName: state
.thenItems[index]['name'] ??
'Automation',
automationId: state.thenItems[index]
['deviceId'] ??
'',
uniqueCustomId:
state.thenItems[index]
['uniqueCustomId'],
),
);
if (result != null) {
context
.read<RoutineBloc>()
.add(AddToThenContainer({
...state.thenItems[index],
'imagePath': Assets.automation,
'title': state.thenItems[index]
['name'] ??
state.thenItems[index]
['title'],
}));
}
return;
}
final result = await DeviceDialogHelper
.showDeviceDialog(
context: context,
data: state.thenItems[index],
removeComparetors: true,
dialogType: 'THEN');
if (result != null) {
context.read<RoutineBloc>().add(
AddToThenContainer(
state.thenItems[index]));
} else if (![
'AC',
'1G',
'2G',
'3G',
'WPS',
'CPS',
'GW',
'NCPS',
'WH',
].contains(state.thenItems[index]
['productType'])) {
context.read<RoutineBloc>().add(
AddToThenContainer(
state.thenItems[index]));
}
},
child: DraggableCard(
imagePath: state.thenItems[index]
['imagePath'] ??
'',
title:
state.thenItems[index]['title'] ?? '',
deviceData: state.thenItems[index],
padding: const EdgeInsets.symmetric(
horizontal: 4, vertical: 8),
isFromThen: true,
isFromIf: false,
onRemove: () {
context.read<RoutineBloc>().add(
RemoveDragCard(
index: index,
isFromThen: true,
key: state.thenItems[index]
['uniqueCustomId']));
},
child: DraggableCard(
imagePath: state.thenItems[index]
['imagePath'] ??
'',
title: state.thenItems[index]
['title'] ??
'',
deviceData: state.thenItems[index],
padding: const EdgeInsets.symmetric(
horizontal: 4, vertical: 8),
isFromThen: true,
isFromIf: false,
onRemove: () {
context.read<RoutineBloc>().add(
RemoveDragCard(
index: index,
isFromThen: true,
key: state.thenItems[index]
['uniqueCustomId']));
},
),
))),
),
))),
],
),
),
@ -168,7 +163,7 @@ class ThenContainer extends StatelessWidget {
}
if (mutableData['type'] == 'automation') {
int index = state.thenItems.indexWhere(
final index = state.thenItems.indexWhere(
(item) => item['deviceId'] == mutableData['deviceId']);
if (index != -1) {
return;
@ -194,7 +189,7 @@ class ThenContainer extends StatelessWidget {
}
if (mutableData['type'] == 'tap_to_run' && state.isAutomation) {
int index = state.thenItems.indexWhere(
final index = state.thenItems.indexWhere(
(item) => item['deviceId'] == mutableData['deviceId']);
if (index != -1) {
return;
@ -230,7 +225,7 @@ class ThenContainer extends StatelessWidget {
context: context,
data: mutableData,
removeComparetors: true,
dialogType: "THEN");
dialogType: 'THEN');
if (result != null) {
context.read<RoutineBloc>().add(AddToThenContainer(mutableData));
} else if (![
@ -241,8 +236,8 @@ class ThenContainer extends StatelessWidget {
'WPS',
'GW',
'CPS',
"NCPS",
"WH",
'NCPS',
'WH',
'PC',
].contains(mutableData['productType'])) {
context.read<RoutineBloc>().add(AddToThenContainer(mutableData));

View File

@ -19,7 +19,7 @@ class ValueDisplay extends StatelessWidget {
return Container(
padding: const EdgeInsets.symmetric(horizontal: 20, vertical: 10),
decoration: BoxDecoration(
color: ColorsManager.primaryColorWithOpacity.withOpacity(0.1),
color: ColorsManager.primaryColorWithOpacity.withValues(alpha: 0.1),
borderRadius: BorderRadius.circular(10),
),
child: Text(