Bug fixes

This commit is contained in:
Abdullah Alassaf
2024-11-12 00:15:26 +03:00
parent faf294bb10
commit b547a126ed
23 changed files with 342 additions and 510 deletions

View File

@ -1,7 +1,7 @@
import UIKit
import Flutter
@main
@UIApplicationMain
@objc class AppDelegate: FlutterAppDelegate {
override func application(
_ application: UIApplication,

View File

@ -55,8 +55,7 @@ class HomeCubit extends Cubit<HomeState> {
Future fetchUserInfo() async {
try {
var uuid =
await const FlutterSecureStorage().read(key: UserModel.userUuidKey);
var uuid = await const FlutterSecureStorage().read(key: UserModel.userUuidKey);
user = await ProfileApi().fetchUserInfo(uuid);
emit(HomeUserInfoLoaded(user!)); // Emit state after fetching user info
} catch (e) {
@ -77,12 +76,9 @@ class HomeCubit extends Cubit<HomeState> {
selectedSpace = null;
selectedRoom = null;
pageIndex = 0;
OneSignal.User.pushSubscription
.removeObserver((stateChanges) => oneSignalSubscriptionObserver);
OneSignal.Notifications.removePermissionObserver(
(permission) => oneSignalPermissionObserver);
OneSignal.Notifications.removeClickListener(
(event) => oneSignalClickListenerObserver);
OneSignal.User.pushSubscription.removeObserver((stateChanges) => oneSignalSubscriptionObserver);
OneSignal.Notifications.removePermissionObserver((permission) => oneSignalPermissionObserver);
OneSignal.Notifications.removeClickListener((event) => oneSignalClickListenerObserver);
return super.close();
}
@ -124,9 +120,7 @@ class HomeCubit extends Cubit<HomeState> {
return;
}
var userUuid =
await const FlutterSecureStorage().read(key: UserModel.userUuidKey) ??
'';
var userUuid = await const FlutterSecureStorage().read(key: UserModel.userUuidKey) ?? '';
if (userUuid.isNotEmpty) {
await OneSignal.login(userUuid);
}
@ -134,24 +128,21 @@ class HomeCubit extends Cubit<HomeState> {
await OneSignal.User.pushSubscription.optIn();
//this function will be called once a user is subscribed
oneSignalSubscriptionObserver =
OneSignal.User.pushSubscription.addObserver((state) async {
oneSignalSubscriptionObserver = OneSignal.User.pushSubscription.addObserver((state) async {
if (state.current.optedIn) {
await _sendSubscriptionId();
}
});
// Send the player id when a user allows notifications
oneSignalPermissionObserver =
OneSignal.Notifications.addPermissionObserver((state) async {
oneSignalPermissionObserver = OneSignal.Notifications.addPermissionObserver((state) async {
await _sendSubscriptionId();
});
//check if the player id is sent, if not send it again
await _sendSubscriptionId();
oneSignalClickListenerObserver =
OneSignal.Notifications.addClickListener((event) async {
oneSignalClickListenerObserver = OneSignal.Notifications.addClickListener((event) async {
//Once the user clicks on the notification
});
} catch (err) {
@ -222,8 +213,7 @@ class HomeCubit extends Cubit<HomeState> {
//////////////////////////////////////// API ////////////////////////////////////////
generateInvitation(SpaceModel unit) async {
try {
final invitationCode =
await SpacesAPI.generateInvitationCode(unit.id, unit.community.uuid);
final invitationCode = await SpacesAPI.generateInvitationCode(unit.id, unit.community.uuid);
if (invitationCode.isNotEmpty) {
Share.share('The invitation code is $invitationCode');
CustomSnackBar.displaySnackBar(
@ -239,9 +229,7 @@ class HomeCubit extends Cubit<HomeState> {
Future<bool> joinAUnit(String code) async {
try {
var userUuid =
await const FlutterSecureStorage().read(key: UserModel.userUuidKey) ??
'';
var userUuid = await const FlutterSecureStorage().read(key: UserModel.userUuidKey) ?? '';
Map<String, String> body = {'inviteCode': code};
final success = await SpacesAPI.joinUnit(userUuid, body);
@ -277,14 +265,13 @@ class HomeCubit extends Cubit<HomeState> {
fetchRoomsByUnitId(SpaceModel space) async {
emitSafe(GetSpaceRoomsLoading());
try {
space.subspaces =
await SpacesAPI.getSubSpaceBySpaceId(space.community.uuid, space.id);
space.subspaces = await SpacesAPI.getSubSpaceBySpaceId(space.community.uuid, space.id);
} catch (failure) {
emitSafe(GetSpaceRoomsError(failure.toString()));
return;
}
if (space.subspaces != null && space.subspaces!.isNotEmpty) {
emitSafe(GetSpaceRoomsSuccess(space.subspaces!));
if (space.subspaces.isNotEmpty) {
emitSafe(GetSpaceRoomsSuccess(space.subspaces));
} else {
emitSafe(GetSpaceRoomsError("No rooms found"));
}
@ -360,8 +347,7 @@ class HomeCubit extends Cubit<HomeState> {
size: 32,
),
style: ButtonStyle(
foregroundColor:
WidgetStateProperty.all(ColorsManager.textPrimaryColor),
foregroundColor: WidgetStateProperty.all(ColorsManager.textPrimaryColor),
),
onPressed: () {
Navigator.pushNamed(
@ -382,8 +368,7 @@ class HomeCubit extends Cubit<HomeState> {
NavigationService.navigatorKey.currentContext!
.read<SmartSceneSelectBloc>()
.add(const SmartSceneClearEvent());
BlocProvider.of<EffectPeriodBloc>(
NavigationService.navigatorKey.currentState!.context)
BlocProvider.of<EffectPeriodBloc>(NavigationService.navigatorKey.currentState!.context)
.add(ResetEffectivePeriod());
NavigationService.navigatorKey.currentContext!
.read<CreateSceneBloc>()
@ -396,8 +381,7 @@ class HomeCubit extends Cubit<HomeState> {
size: 28,
),
style: ButtonStyle(
foregroundColor:
WidgetStateProperty.all(ColorsManager.textPrimaryColor),
foregroundColor: WidgetStateProperty.all(ColorsManager.textPrimaryColor),
),
onPressed: () {},
),
@ -430,8 +414,7 @@ class HomeCubit extends Cubit<HomeState> {
};
static var bottomNavItems = [
defaultBottomNavBarItem(
icon: Assets.assetsIconsDashboard, label: 'Dashboard'),
defaultBottomNavBarItem(icon: Assets.assetsIconsDashboard, label: 'Dashboard'),
// defaultBottomNavBarItem(icon: Assets.assetsIconslayout, label: 'Layout'),
defaultBottomNavBarItem(icon: Assets.assetsIconsDevices, label: 'Devices'),
defaultBottomNavBarItem(icon: Assets.assetsIconsRoutines, label: 'Routine'),
@ -457,8 +440,7 @@ class HomeCubit extends Cubit<HomeState> {
void updateDevice(String deviceId) async {
try {
final response = await DevicesAPI.firmwareDevice(
deviceId: deviceId, firmwareVersion: '0');
final response = await DevicesAPI.firmwareDevice(deviceId: deviceId, firmwareVersion: '0');
if (response['success'] ?? false) {
CustomSnackBar.displaySnackBar('No updates available');
}
@ -466,8 +448,7 @@ class HomeCubit extends Cubit<HomeState> {
}
}
BottomNavigationBarItem defaultBottomNavBarItem(
{required String icon, required String label}) {
BottomNavigationBarItem defaultBottomNavBarItem({required String icon, required String label}) {
return BottomNavigationBarItem(
icon: SvgPicture.asset(icon),
activeIcon: SvgPicture.asset(

View File

@ -46,7 +46,7 @@ class AppBarHomeDropdown extends StatelessWidget {
const SizedBox(width: 5),
Flexible(
child: BodyMedium(
text: space.name ?? "??",
text: space.name,
style: context.bodyMedium.copyWith(
fontSize: 15,
color: ColorsManager.textPrimaryColor,

View File

@ -14,16 +14,15 @@ import 'package:syncrow_app/utils/resource_manager/constants.dart';
import 'package:syncrow_app/utils/resource_manager/font_manager.dart';
import 'package:syncrow_app/utils/resource_manager/styles_manager.dart';
class checkEmailPage extends StatelessWidget {
bool? forget;
checkEmailPage({super.key, this.forget});
class CheckEmailPage extends StatelessWidget {
final bool? forget;
const CheckEmailPage({super.key, this.forget});
@override
Widget build(BuildContext context) {
final formKey = AuthCubit.get(context).checkEmailFormKey;
SystemChrome.setSystemUIOverlayStyle(const SystemUiOverlayStyle(
statusBarBrightness: Brightness.light,
statusBarIconBrightness: Brightness.light));
statusBarBrightness: Brightness.light, statusBarIconBrightness: Brightness.light));
return BlocConsumer<AuthCubit, AuthState>(
listener: (context, state) {
if (state is AuthError) {
@ -93,9 +92,7 @@ class checkEmailPage extends StatelessWidget {
crossAxisAlignment: CrossAxisAlignment.start,
children: [
SizedBox(
height:
MediaQuery.sizeOf(context).height /
5.5,
height: MediaQuery.sizeOf(context).height / 5.5,
),
TitleMedium(
text: 'Forgot password?',
@ -117,39 +114,32 @@ class checkEmailPage extends StatelessWidget {
scrollPadding: EdgeInsets.zero,
autocorrect: false,
enableSuggestions: false,
autofillHints: const [
AutofillHints.email
],
validator: AuthCubit.get(context)
.emailAddressValidator,
autofillHints: const [AutofillHints.email],
validator: AuthCubit.get(context).emailAddressValidator,
onTapOutside: (event) {
FocusScope.of(context).unfocus();
},
onChanged: (value) {
AuthCubit.get(context).email = value;
},
decoration: defaultInputDecoration(
context,
decoration: defaultInputDecoration(context,
hint: "Example@email.com"),
),
const SizedBox(
height: 20,
),
Row(
mainAxisAlignment:
MainAxisAlignment.center,
mainAxisAlignment: MainAxisAlignment.center,
children: [
Expanded(
child: DefaultButton(
isDone: state is AuthLoginSuccess,
isLoading: state is AuthLoading,
customButtonStyle: ButtonStyle(
backgroundColor:
MaterialStateProperty.all(
backgroundColor: MaterialStateProperty.all(
Colors.black.withOpacity(.25),
),
foregroundColor:
MaterialStateProperty.all(
foregroundColor: MaterialStateProperty.all(
Colors.white,
),
),
@ -157,16 +147,11 @@ class checkEmailPage extends StatelessWidget {
'Send Code',
),
onPressed: () {
AuthCubit.get(context)
.showValidationMessage = true;
if (formKey.currentState!
.validate()) {
AuthCubit.get(context).showValidationMessage = true;
if (formKey.currentState!.validate()) {
if ((state is! AuthLoading)) {
AuthCubit.get(context)
.sendOtp(
isforget: forget);
FocusScope.of(context)
.unfocus();
AuthCubit.get(context).sendOtp(isforget: forget);
FocusScope.of(context).unfocus();
}
}
},
@ -176,17 +161,14 @@ class checkEmailPage extends StatelessWidget {
),
Padding(
padding: EdgeInsets.only(
top: MediaQuery.sizeOf(context)
.height /
5.5),
top: MediaQuery.sizeOf(context).height / 5.5),
child: Row(
mainAxisAlignment:
MainAxisAlignment.center,
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
BodyLarge(
text: "Do you have an account? ",
style: context.displaySmall
.copyWith(color: Colors.white),
style:
context.displaySmall.copyWith(color: Colors.white),
),
TextButton(
onPressed: () {
@ -194,8 +176,7 @@ class checkEmailPage extends StatelessWidget {
},
child: BodyLarge(
text: "Sign in",
style:
context.displaySmall.copyWith(
style: context.displaySmall.copyWith(
color: Colors.black,
fontWeight: FontsManager.bold,
),

View File

@ -19,7 +19,7 @@ class ForgetPassword extends StatelessWidget {
Navigator.push(
context,
MaterialPageRoute(
builder: (context) => checkEmailPage(forget: isforget),
builder: (context) => CheckEmailPage(forget: isforget),
));
},
child: BodyMedium(

View File

@ -25,12 +25,12 @@ part 'devices_state.dart';
class DevicesCubit extends Cubit<DevicesState> {
Future<void> _initializeDevices(SpaceModel selectedSpace) async {
// Fetch devices for each room in the selected space
for (var room in selectedSpace.subspaces ?? []) {
for (var room in selectedSpace.subspaces) {
await fetchDevicesByRoomId(selectedSpace, room.id!);
}
// Fetch groups based on the selected space ID
await fetchGroups(selectedSpace.id ?? '');
await fetchGroups(selectedSpace.id);
}
DevicesCubit._() : super(DevicesInitial()) {
@ -111,9 +111,8 @@ class DevicesCubit extends Cubit<DevicesState> {
// Getter to retrieve all devices from HomeCubit
List<DeviceModel> get allDevices {
List<DeviceModel> devices = [];
if (HomeCubit.getInstance().selectedSpace != null &&
HomeCubit.getInstance().selectedSpace!.subspaces != null) {
for (var room in HomeCubit.getInstance().selectedSpace!.subspaces!) {
if (HomeCubit.getInstance().selectedSpace != null) {
for (var room in HomeCubit.getInstance().selectedSpace!.subspaces) {
if (room.devices != null) {
devices.addAll(room.devices!);
}
@ -278,15 +277,15 @@ class DevicesCubit extends Cubit<DevicesState> {
if (response['success'] ?? false) {
emitSafe(DeviceControlSuccess(code: control.code));
//this delay is to give tuya server time to update the status
Future.delayed(const Duration(milliseconds: 400), () {
// Future.delayed(const Duration(milliseconds: 400), () {
fetchDevicesStatues(
deviceId,
HomeCubit.getInstance()
.selectedSpace!
.subspaces!
.subspaces
.indexOf(HomeCubit.getInstance().selectedRoom!),
code: control.code);
});
// });
} else {
emitSafe(DeviceControlError('Failed to control the device'));
}
@ -317,20 +316,17 @@ class DevicesCubit extends Cubit<DevicesState> {
emitSafe(GetDevicesLoading());
int roomIndex = HomeCubit.getInstance()
.selectedSpace!
.subspaces!
.subspaces
.indexWhere((element) => element.id == roomId);
try {
HomeCubit.getInstance().selectedSpace!.subspaces![roomIndex].devices =
HomeCubit.getInstance().selectedSpace!.subspaces[roomIndex].devices =
await DevicesAPI.getDevicesByRoomId(
communityUuid: unit!.community.uuid,
spaceUuid: unit.id,
roomId: roomId);
communityUuid: unit!.community.uuid, spaceUuid: unit.id, roomId: roomId);
} catch (e) {
emitSafe(GetDevicesError(e.toString()));
return;
}
final devices =
HomeCubit.getInstance().selectedSpace!.subspaces![roomIndex].devices;
final devices = HomeCubit.getInstance().selectedSpace!.subspaces[roomIndex].devices;
emitSafe(GetDevicesSuccess(devices));
//get status for each device
@ -347,7 +343,7 @@ class DevicesCubit extends Cubit<DevicesState> {
emitSafe(GetDeviceStatusLoading(code: code));
int deviceIndex = HomeCubit.getInstance()
.selectedSpace!
.subspaces![roomIndex]
.subspaces[roomIndex]
.devices!
.indexWhere((element) => element.uuid == deviceUuid);
List<StatusModel> statuses = [];
@ -360,11 +356,8 @@ class DevicesCubit extends Cubit<DevicesState> {
emitSafe(GetDeviceStatusError(e.toString()));
return;
}
HomeCubit.getInstance()
.selectedSpace!
.subspaces![roomIndex]
.devices![deviceIndex]
.status = statuses;
HomeCubit.getInstance().selectedSpace!.subspaces[roomIndex].devices![deviceIndex].status =
statuses;
emitSafe(GetDeviceStatusSuccess(code: code));
}

View File

@ -14,8 +14,7 @@ class PowerClampSwitch extends PowerClampEvent {
final bool switchD;
final String deviceId;
final String productId;
const PowerClampSwitch(
{required this.switchD, this.deviceId = '', this.productId = ''});
const PowerClampSwitch({required this.switchD, this.deviceId = '', this.productId = ''});
@override
List<Object> get props => [switchD, deviceId, productId];
@ -26,8 +25,8 @@ class PowerClampUpdated extends PowerClampEvent {}
class FetchEnergyData extends PowerClampEvent {}
class SelectDateEvent extends PowerClampEvent {
BuildContext context;
SelectDateEvent({required this.context});
final BuildContext context;
const SelectDateEvent({required this.context});
}
class PowerClampInitial extends PowerClampEvent {
@ -108,12 +107,9 @@ class StopTimer extends PowerClampEvent {}
class OnClose extends PowerClampEvent {}
class FilterRecordsByDateEvent extends PowerClampEvent {
final DateTime selectedDate;
final String viewType; // 'Day', 'Month', 'Year'
const FilterRecordsByDateEvent(
{required this.selectedDate, required this.viewType});
const FilterRecordsByDateEvent({required this.selectedDate, required this.viewType});
}

View File

@ -13,6 +13,7 @@ import 'package:syncrow_app/features/shared_widgets/text_widgets/body_large.dart
import 'package:syncrow_app/features/shared_widgets/text_widgets/title_medium.dart';
import 'package:syncrow_app/utils/context_extension.dart';
import 'package:syncrow_app/utils/resource_manager/strings_manager.dart';
class DevicesViewPage extends StatelessWidget {
const DevicesViewPage({super.key});
@ -57,8 +58,9 @@ class DevicesViewBody extends StatelessWidget {
),
SizedBox(
height: MediaQuery.of(context).size.height * 0.1,
child: const SceneView(pageType: true,)
),
child: const SceneView(
pageType: true,
)),
const SizedBox(
height: 20,
),
@ -66,10 +68,8 @@ class DevicesViewBody extends StatelessWidget {
const SizedBox(
height: 10,
),
Expanded(
child: PageView(
controller: HomeCubit.getInstance().devicesPageController,
onPageChanged: (index) {
HomeCubit.getInstance().devicesPageChanged(index);
@ -79,8 +79,8 @@ class DevicesViewBody extends StatelessWidget {
groupsList: DevicesCubit.getInstance().allCategories ?? [],
),
if (HomeCubit.getInstance().selectedSpace != null)
if (HomeCubit.getInstance().selectedSpace!.subspaces != null)
...HomeCubit.getInstance().selectedSpace!.subspaces!.map((room) {
...HomeCubit.getInstance().selectedSpace!.subspaces.map(
(room) {
return RoomPage(
room: room,
);
@ -96,7 +96,7 @@ class DevicesViewBody extends StatelessWidget {
),
child: SmoothPageIndicator(
controller: HomeCubit.getInstance().devicesPageController,
count: HomeCubit.getInstance().selectedSpace!.subspaces!.length + 1,
count: HomeCubit.getInstance().selectedSpace!.subspaces.length + 1,
effect: const WormEffect(
paintStyle: PaintingStyle.stroke,
dotHeight: 8,

View File

@ -1,7 +1,6 @@
import 'package:flutter/material.dart';
import 'package:syncrow_app/features/devices/model/subspace_model.dart';
import 'package:flutter_svg/flutter_svg.dart';
import 'package:syncrow_app/features/devices/model/room_model.dart';
import 'package:syncrow_app/features/devices/view/widgets/room_page_switch.dart';
import 'package:syncrow_app/generated/assets.dart';
import 'package:syncrow_app/utils/resource_manager/color_manager.dart';
@ -52,9 +51,7 @@ class _RoomPageState extends State<RoomPage> {
decoration: InputDecoration(
hintText: 'Search',
hintStyle: const TextStyle(
color: ColorsManager.textGray,
fontSize: 16,
fontWeight: FontWeight.w400),
color: ColorsManager.textGray, fontSize: 16, fontWeight: FontWeight.w400),
prefixIcon: Container(
padding: const EdgeInsets.all(5.0),
margin: const EdgeInsets.all(10.0),

View File

@ -39,25 +39,19 @@ class RoomsSlider extends StatelessWidget {
),
),
if (HomeCubit.getInstance().selectedSpace != null)
if (HomeCubit.getInstance().selectedSpace!.subspaces != null)
...HomeCubit.getInstance().selectedSpace!.subspaces!.map(
...HomeCubit.getInstance().selectedSpace!.subspaces.map(
(room) => InkWell(
onTap: () {
HomeCubit.getInstance().roomSliderPageChanged(
HomeCubit.getInstance()
.selectedSpace!
.subspaces!
.indexOf(room));
HomeCubit.getInstance().selectedSpace!.subspaces.indexOf(room));
},
child: TitleMedium(
text: room.name!,
style: context.titleMedium.copyWith(
fontSize: 25,
color:
HomeCubit.getInstance().selectedRoom == room
color: HomeCubit.getInstance().selectedRoom == room
? ColorsManager.textPrimaryColor
: ColorsManager.textPrimaryColor
.withOpacity(.2),
: ColorsManager.textPrimaryColor.withOpacity(.2),
),
),
),

View File

@ -40,13 +40,10 @@ class SceneListview extends StatelessWidget {
sceneName: scene.name,
),
);
context
.read<SmartSceneSelectBloc>()
.add(const SmartSceneClearEvent());
context.read<SmartSceneSelectBloc>().add(const SmartSceneClearEvent());
BlocProvider.of<CreateSceneBloc>(context).add(
FetchSceneTasksEvent(
sceneId: scene.id, isAutomation: false));
BlocProvider.of<CreateSceneBloc>(context)
.add(FetchSceneTasksEvent(sceneId: scene.id, isAutomation: false));
/// the state to set the scene type must be after the fetch
BlocProvider.of<CreateSceneBloc>(context)
@ -59,15 +56,13 @@ class SceneListview extends StatelessWidget {
children: [
Padding(
padding: const EdgeInsets.all(8.0),
child: scene.iconInBytes != null &&
scene.iconInBytes.isNotEmpty
child: scene.iconInBytes.isNotEmpty
? Image.memory(
scene.iconInBytes,
height: 32,
width: 32,
fit: BoxFit.fill,
errorBuilder: (context, error, stackTrace) =>
Image.asset(
errorBuilder: (context, error, stackTrace) => Image.asset(
Assets.assetsIconsLogo,
height: 32,
width: 32,

View File

@ -1,6 +1,5 @@
import 'package:equatable/equatable.dart';
import 'package:syncrow_app/features/devices/model/device_model.dart';
import 'package:syncrow_app/features/devices/model/room_model.dart';
import 'package:syncrow_app/features/devices/model/subspace_model.dart';
abstract class ManageUnitState extends Equatable {

View File

@ -44,8 +44,7 @@ class ManageHomeView extends StatelessWidget {
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
BodyMedium(
text: StringHelpers.toTitleCase(spaces[index].name ?? "")),
BodyMedium(text: StringHelpers.toTitleCase(spaces[index].name)),
const Icon(
Icons.arrow_forward_ios,
color: ColorsManager.greyColor,
@ -75,8 +74,7 @@ class ManageHomeView extends StatelessWidget {
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
BodyMedium(
text: HomeCubit.getInstance().spaces![index].name ?? ""),
BodyMedium(text: HomeCubit.getInstance().spaces![index].name),
const Icon(
Icons.arrow_forward_ios,
color: ColorsManager.greyColor,

View File

@ -60,7 +60,7 @@ mixin SceneLogicHelper {
if (isAutomation) {
final createAutomationModel = CreateAutomationModel(
unitUuid: HomeCubit.getInstance().selectedSpace!.id ?? '',
unitUuid: HomeCubit.getInstance().selectedSpace?.id ?? '',
automationName: sceneName.text,
decisionExpr: sceneBloc.conditionRule,
effectiveTime: sceneBloc.effectiveTime ??
@ -124,7 +124,7 @@ mixin SceneLogicHelper {
));
} else {
final createSceneModel = CreateSceneModel(
spaceUuid: HomeCubit.getInstance().selectedSpace!.id ?? '',
spaceUuid: HomeCubit.getInstance().selectedSpace?.id ?? '',
iconId: sceneBloc.selectedIcon,
showInDevice: sceneBloc.showInDeviceScreen,
sceneName: sceneName.text,

View File

@ -7,24 +7,19 @@ import 'package:syncrow_app/features/devices/model/subspace_model.dart';
import 'package:syncrow_app/features/scene/bloc/tab_change/tab_change_bloc.dart';
import 'package:syncrow_app/features/scene/bloc/tab_change/tab_change_event.dart';
import 'package:syncrow_app/features/scene/widgets/scene_devices/scene_devices_body.dart';
import 'package:syncrow_app/features/shared_widgets/default_scaffold.dart';
import 'package:syncrow_app/navigation/navigate_to_route.dart';
import 'package:syncrow_app/navigation/routing_constants.dart';
import 'package:syncrow_app/utils/resource_manager/constants.dart';
import 'package:syncrow_app/utils/resource_manager/strings_manager.dart';
class SceneRoomsTabBarDevicesView extends StatefulWidget {
const SceneRoomsTabBarDevicesView({super.key});
@override
State<SceneRoomsTabBarDevicesView> createState() =>
_SceneRoomsTabBarDevicesViewState();
State<SceneRoomsTabBarDevicesView> createState() => _SceneRoomsTabBarDevicesViewState();
}
class _SceneRoomsTabBarDevicesViewState
extends State<SceneRoomsTabBarDevicesView>
class _SceneRoomsTabBarDevicesViewState extends State<SceneRoomsTabBarDevicesView>
with SingleTickerProviderStateMixin {
late final TabController _tabController;
List<SubSpaceModel>? rooms = [];
@ -47,8 +42,7 @@ class _SceneRoomsTabBarDevicesViewState
}
}
_tabController =
TabController(length: rooms!.length, vsync: this, initialIndex: 0);
_tabController = TabController(length: rooms!.length, vsync: this, initialIndex: 0);
_tabController.addListener(_handleTabSwitched);
super.initState();
}
@ -58,10 +52,8 @@ class _SceneRoomsTabBarDevicesViewState
final value = _tabController.index;
/// select tab
context.read<TabBarBloc>().add(TabChanged(
selectedIndex: value,
roomId: rooms?[value].id ?? '',
unit: selectedSpace));
context.read<TabBarBloc>().add(
TabChanged(selectedIndex: value, roomId: rooms?[value].id ?? '', unit: selectedSpace));
return;
}
}

View File

@ -1,13 +1,9 @@
import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:flutter_svg/flutter_svg.dart';
import 'package:syncrow_app/features/app_layout/bloc/home_cubit.dart';
import 'package:syncrow_app/features/scene/bloc/create_scene/create_scene_bloc.dart';
import 'package:syncrow_app/features/scene/bloc/scene_bloc/scene_bloc.dart';
import 'package:syncrow_app/features/scene/bloc/scene_bloc/scene_event.dart';
import 'package:syncrow_app/features/scene/enum/create_scene_enum.dart';
import 'package:syncrow_app/features/scene/model/scene_settings_route_arguments.dart';
import 'package:syncrow_app/features/scene/widgets/alert_dialogs/delete_routine_dialog.dart';
import 'package:syncrow_app/features/scene/widgets/create_scene_save_button.dart';
import 'package:syncrow_app/features/scene/widgets/if_then_containers/if_container.dart';
import 'package:syncrow_app/features/scene/widgets/if_then_containers/then_container.dart';
@ -24,19 +20,16 @@ class SceneTasksView extends StatelessWidget {
@override
Widget build(BuildContext context) {
final sceneSettings = ModalRoute.of(context)!.settings.arguments
as SceneSettingsRouteArguments;
final sceneSettings = ModalRoute.of(context)!.settings.arguments as SceneSettingsRouteArguments;
final isAutomation =
sceneSettings.sceneType == CreateSceneEnum.deviceStatusChanges.name;
final isAutomation = sceneSettings.sceneType == CreateSceneEnum.deviceStatusChanges.name;
// context.read<CreateSceneBloc>().add(SceneTypeEvent(isAutomation
// ? CreateSceneEnum.deviceStatusChanges
// : CreateSceneEnum.tabToRun));
return DefaultScaffold(
title: sceneSettings.sceneName.isNotEmpty
? sceneSettings.sceneName
: StringsManager.createScene,
title:
sceneSettings.sceneName.isNotEmpty ? sceneSettings.sceneName : StringsManager.createScene,
padding: EdgeInsets.zero,
leading: IconButton(
onPressed: () {

View File

@ -22,7 +22,22 @@ class SceneView extends StatelessWidget {
@override
Widget build(BuildContext context) {
return BlocProvider(
create: (BuildContext context) => SceneBloc()
create: (BuildContext context) {
if (pageType) {
return SceneBloc()
..add(LoadScenes(
HomeCubit.getInstance().selectedSpace?.id ?? '',
HomeCubit.getInstance().selectedSpace ??
SpaceModel(
id: '-1',
name: '',
community: Community(
uuid: '-1',
name: '',
)),
showInDevice: pageType));
} else {
return SceneBloc()
..add(LoadScenes(
HomeCubit.getInstance().selectedSpace?.id ?? '',
HomeCubit.getInstance().selectedSpace ??
@ -34,36 +49,35 @@ class SceneView extends StatelessWidget {
name: '',
)),
showInDevice: pageType))
..add(LoadAutomation(HomeCubit.getInstance().selectedSpace?.id ?? '')),
..add(LoadAutomation(HomeCubit.getInstance().selectedSpace?.id ?? ''));
}
},
child: BlocBuilder<CreateSceneBloc, CreateSceneState>(
builder: (context, state) {
if (state is DeleteSceneSuccess) {
if (state.success) {
BlocProvider.of<SceneBloc>(context).add(LoadScenes(
HomeCubit.getInstance().selectedSpace!.id!,HomeCubit.getInstance().selectedSpace!,
HomeCubit.getInstance().selectedSpace!.id, HomeCubit.getInstance().selectedSpace!,
showInDevice: pageType));
BlocProvider.of<SceneBloc>(context).add(
LoadAutomation(HomeCubit.getInstance().selectedSpace!.id!));
BlocProvider.of<SceneBloc>(context)
.add(LoadAutomation(HomeCubit.getInstance().selectedSpace!.id));
}
}
if (state is CreateSceneWithTasks) {
if (state.success == true) {
BlocProvider.of<SceneBloc>(context).add(LoadScenes(
HomeCubit.getInstance().selectedSpace!.id!,HomeCubit.getInstance().selectedSpace!,
HomeCubit.getInstance().selectedSpace!.id, HomeCubit.getInstance().selectedSpace!,
showInDevice: pageType));
BlocProvider.of<SceneBloc>(context).add(
LoadAutomation(HomeCubit.getInstance().selectedSpace!.id!));
context
.read<SmartSceneSelectBloc>()
.add(const SmartSceneClearEvent());
BlocProvider.of<SceneBloc>(context)
.add(LoadAutomation(HomeCubit.getInstance().selectedSpace!.id));
context.read<SmartSceneSelectBloc>().add(const SmartSceneClearEvent());
}
}
return BlocListener<SceneBloc, SceneState>(
listener: (context, state) {
if (state is SceneTriggerSuccess) {
context.showCustomSnackbar(
message:
'Scene ${state.sceneName} triggered successfully!');
message: 'Scene ${state.sceneName} triggered successfully!');
}
},
child: HomeCubit.getInstance().spaces?.isEmpty ?? true
@ -100,30 +114,25 @@ class SceneView extends StatelessWidget {
child: ListView(
children: [
Theme(
data: ThemeData().copyWith(
dividerColor: Colors.transparent),
data: ThemeData()
.copyWith(dividerColor: Colors.transparent),
child: ExpansionTile(
tilePadding:
const EdgeInsets.symmetric(
horizontal: 6),
tilePadding: const EdgeInsets.symmetric(horizontal: 6),
initiallyExpanded: true,
iconColor: ColorsManager.grayColor,
title: const BodyMedium(
text: 'Tap to run routines'),
title: const BodyMedium(text: 'Tap to run routines'),
children: [
scenes.isNotEmpty
? SceneGrid(
scenes: scenes,
loadingSceneId:
state.loadingSceneId,
loadingSceneId: state.loadingSceneId,
disablePlayButton: false,
loadingStates: state
.loadingStates, // Add this line
loadingStates:
state.loadingStates, // Add this line
)
: const Center(
child: BodyMedium(
text:
'No scenes have been added yet',
text: 'No scenes have been added yet',
),
),
const SizedBox(
@ -133,30 +142,25 @@ class SceneView extends StatelessWidget {
),
),
Theme(
data: ThemeData().copyWith(
dividerColor: Colors.transparent),
data: ThemeData()
.copyWith(dividerColor: Colors.transparent),
child: ExpansionTile(
initiallyExpanded: true,
iconColor: ColorsManager.grayColor,
tilePadding:
const EdgeInsets.symmetric(
horizontal: 6),
title: const BodyMedium(
text: 'Automation'),
tilePadding: const EdgeInsets.symmetric(horizontal: 6),
title: const BodyMedium(text: 'Automation'),
children: [
automationList.isNotEmpty
? SceneGrid(
scenes: automationList,
loadingSceneId:
state.loadingSceneId,
loadingSceneId: state.loadingSceneId,
disablePlayButton: true,
loadingStates: state
.loadingStates, // Add this line
loadingStates:
state.loadingStates, // Add this line
)
: const Center(
child: BodyMedium(
text:
'No automations have been added yet',
text: 'No automations have been added yet',
),
),
const SizedBox(

View File

@ -10,8 +10,7 @@ import 'package:syncrow_app/navigation/routing_constants.dart';
import 'package:syncrow_app/utils/resource_manager/color_manager.dart';
class DeleteRoutineButton extends StatelessWidget {
const DeleteRoutineButton(
{super.key, required this.sceneId, required this.isAutomation});
const DeleteRoutineButton({super.key, required this.sceneId, required this.isAutomation});
final String sceneId;
final bool isAutomation;
@ -23,10 +22,10 @@ class DeleteRoutineButton extends StatelessWidget {
if (state is DeleteSceneSuccess) {
if (state.success) {
navigateToRoute(context, Routes.homeRoute);
BlocProvider.of<SceneBloc>(context).add(LoadScenes(
HomeCubit.getInstance().selectedSpace!.id, HomeCubit.getInstance().selectedSpace!));
BlocProvider.of<SceneBloc>(context)
.add(LoadScenes(HomeCubit.getInstance().selectedSpace!.id!,HomeCubit.getInstance().selectedSpace!));
BlocProvider.of<SceneBloc>(context).add(
LoadAutomation(HomeCubit.getInstance().selectedSpace!.id!));
.add(LoadAutomation(HomeCubit.getInstance().selectedSpace!.id));
}
}
},
@ -43,8 +42,7 @@ class DeleteRoutineButton extends StatelessWidget {
confirmTab: () {
context.read<CreateSceneBloc>().add(DeleteSceneEvent(
sceneId: sceneId,
unitUuid:
HomeCubit.getInstance().selectedSpace!.id!,
unitUuid: HomeCubit.getInstance().selectedSpace!.id,
));
Navigator.of(context).pop();
},

View File

@ -3,7 +3,6 @@ import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:flutter_svg/flutter_svg.dart';
import 'package:syncrow_app/features/devices/bloc/device_manager_bloc/device_manager_bloc.dart';
import 'package:syncrow_app/features/devices/bloc/device_manager_bloc/device_manager_state.dart';
import 'package:syncrow_app/features/devices/model/room_model.dart';
import 'package:syncrow_app/features/devices/model/subspace_model.dart';
import 'package:syncrow_app/features/scene/bloc/tab_change/tab_change_bloc.dart';
import 'package:syncrow_app/features/scene/bloc/tab_change/tab_change_state.dart';
@ -29,10 +28,8 @@ class SceneDevicesBody extends StatelessWidget {
@override
Widget build(BuildContext context) {
final isAutomationDeviceStatus = ((ModalRoute.of(context)
?.settings
.arguments as SceneSettingsRouteArguments?)
?.sceneType ==
final isAutomationDeviceStatus =
((ModalRoute.of(context)?.settings.arguments as SceneSettingsRouteArguments?)?.sceneType ==
CreateSceneEnum.deviceStatusChanges.name);
return BlocBuilder<TabBarBloc, TabBarState>(
builder: (context, tabState) {
@ -49,8 +46,7 @@ class SceneDevicesBody extends StatelessWidget {
text: e.name ?? '',
textAlign: TextAlign.start,
style: context.bodyLarge.copyWith(
color: (tabState is TabSelected) &&
tabState.roomId == e.id
color: (tabState is TabSelected) && tabState.roomId == e.id
? ColorsManager.textPrimaryColor
: ColorsManager.textPrimaryColor.withOpacity(0.2),
),
@ -64,10 +60,8 @@ class SceneDevicesBody extends StatelessWidget {
child: TabBarView(
controller: _tabController,
physics: const NeverScrollableScrollPhysics(),
children: rooms!
.map((e) =>
_buildRoomTab(e, context, isAutomationDeviceStatus))
.toList(),
children:
rooms!.map((e) => _buildRoomTab(e, context, isAutomationDeviceStatus)).toList(),
),
),
],
@ -76,8 +70,7 @@ class SceneDevicesBody extends StatelessWidget {
);
}
Widget _buildRoomTab(
SubSpaceModel room, BuildContext context, bool isAutomationDeviceStatus) {
Widget _buildRoomTab(SubSpaceModel room, BuildContext context, bool isAutomationDeviceStatus) {
return BlocBuilder<DeviceManagerBloc, DeviceManagerState>(
builder: (context, state) {
if (state.loading && state.devices == null) {

View File

@ -38,8 +38,8 @@ class SceneItem extends StatelessWidget {
onTap: () {
context.read<SmartSceneSelectBloc>().add(const SmartSceneClearEvent());
if (disablePlayButton == false) {
BlocProvider.of<CreateSceneBloc>(context).add(
FetchSceneTasksEvent(sceneId: scene.id, isAutomation: false));
BlocProvider.of<CreateSceneBloc>(context)
.add(FetchSceneTasksEvent(sceneId: scene.id, isAutomation: false));
/// the state to set the scene type must be after the fetch
BlocProvider.of<CreateSceneBloc>(context)
@ -73,19 +73,16 @@ class SceneItem extends StatelessWidget {
crossAxisAlignment: CrossAxisAlignment.center,
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
if (!disablePlayButton && scene.iconInBytes != null && scene.iconInBytes.isNotEmpty)
if (!disablePlayButton && scene.iconInBytes.isNotEmpty)
Image.memory(
scene.iconInBytes,
height: 32,
width: 32,
fit: BoxFit.fill,
errorBuilder: (context, error, stackTrace) => Image.asset(
Assets.assetsIconsLogo,
height: 32,
width: 32,
fit: BoxFit.fill),
errorBuilder: (context, error, stackTrace) =>
Image.asset(Assets.assetsIconsLogo, height: 32, width: 32, fit: BoxFit.fill),
),
if (disablePlayButton || scene.iconInBytes == null || scene.iconInBytes.isEmpty)
if (disablePlayButton || scene.iconInBytes.isEmpty)
SvgPicture.asset(
Assets.automationIcon,
height: 32,
@ -96,9 +93,7 @@ class SceneItem extends StatelessWidget {
? IconButton(
padding: EdgeInsets.zero,
onPressed: () {
context
.read<SceneBloc>()
.add(SceneTrigger(scene.id, scene.name));
context.read<SceneBloc>().add(SceneTrigger(scene.id, scene.name));
},
icon: isLoading
? const Center(
@ -120,14 +115,10 @@ class SceneItem extends StatelessWidget {
activeColor: ColorsManager.primaryColor,
value: scene.status == 'enable' ? true : false,
onChanged: (value) {
context.read<SceneBloc>().add(
UpdateAutomationStatus(
automationStatusUpdate:
AutomationStatusUpdate(
context.read<SceneBloc>().add(UpdateAutomationStatus(
automationStatusUpdate: AutomationStatusUpdate(
isEnable: value,
spaceUuid: HomeCubit.getInstance()
.selectedSpace!
.id!),
spaceUuid: HomeCubit.getInstance().selectedSpace!.id),
automationId: scene.id));
},
),

View File

@ -1,50 +1,51 @@
import 'package:flutter/material.dart';
import 'package:flutter_svg/svg.dart';
import 'package:syncrow_app/features/shared_widgets/text_widgets/title_medium.dart';
import 'package:syncrow_app/generated/assets.dart';
import 'package:syncrow_app/navigation/routing_constants.dart';
// import 'package:flutter_svg/svg.dart';
// import 'package:syncrow_app/features/shared_widgets/text_widgets/title_medium.dart';
// import 'package:syncrow_app/generated/assets.dart';
// import 'package:syncrow_app/navigation/routing_constants.dart';
class CreateUnitWidget extends StatelessWidget {
const CreateUnitWidget({super.key});
@override
Widget build(BuildContext context) {
return SizedBox(
width: MediaQuery.sizeOf(context).width,
height: MediaQuery.sizeOf(context).height,
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
SvgPicture.asset(
Assets.noUnitsIconDashboard,
width: 100,
height: 100,
),
const SizedBox(
height: 50,
),
Flexible(
child: GestureDetector(
onTap: () {
Navigator.pushNamed(context, Routes.createUnit);
},
child: Container(
padding: const EdgeInsets.symmetric(horizontal: 34, vertical: 14),
decoration: ShapeDecoration(
color: const Color(0x99023DFE),
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(20),
),
),
child: const TitleMedium(
text: 'Create a unit',
style: TextStyle(fontSize: 16, fontWeight: FontWeight.w400, color: Colors.white),
),
),
),
),
],
),
);
return Container();
// return SizedBox(
// width: MediaQuery.sizeOf(context).width,
// height: MediaQuery.sizeOf(context).height,
// child: Column(
// mainAxisAlignment: MainAxisAlignment.center,
// children: [
// SvgPicture.asset(
// Assets.noUnitsIconDashboard,
// width: 100,
// height: 100,
// ),
// const SizedBox(
// height: 50,
// ),
// Flexible(
// child: GestureDetector(
// onTap: () {
// Navigator.pushNamed(context, Routes.createUnit);
// },
// child: Container(
// padding: const EdgeInsets.symmetric(horizontal: 34, vertical: 14),
// decoration: ShapeDecoration(
// color: const Color(0x99023DFE),
// shape: RoundedRectangleBorder(
// borderRadius: BorderRadius.circular(20),
// ),
// ),
// child: const TitleMedium(
// text: 'Create a unit',
// style: TextStyle(fontSize: 16, fontWeight: FontWeight.w400, color: Colors.white),
// ),
// ),
// ),
// ),
// ],
// ),
// );
}
}

View File

@ -1,7 +1,7 @@
//ignore_for_file: constant_identifier_names
import 'dart:ui';
import 'package:syncrow_app/features/devices/model/function_model.dart';
import 'package:syncrow_app/features/menu/view/widgets/create_home/create_home_view.dart';
// import 'package:syncrow_app/features/menu/view/widgets/create_home/create_home_view.dart';
import 'package:syncrow_app/features/menu/view/widgets/join_home/join_home_view.dart';
import 'package:syncrow_app/features/menu/view/widgets/manage_home/manage_home_view.dart';
import 'package:syncrow_app/features/menu/view/widgets/privacy/privacy_view.dart';
@ -92,9 +92,7 @@ Map<String, DeviceType> devicesTypesMap = {
Map<DeviceType, List<FunctionModel>> devicesFunctionsMap = {
DeviceType.AC: [
FunctionModel(
code: 'switch',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'mode',
type: functionTypesMap['Enum'],
@ -117,9 +115,7 @@ Map<DeviceType, List<FunctionModel>> devicesFunctionsMap = {
// "range": ["low", "middle", "high", "auto"]
})),
FunctionModel(
code: 'child_lock',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'child_lock', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
],
DeviceType.Gateway: [
FunctionModel(
@ -133,9 +129,7 @@ Map<DeviceType, List<FunctionModel>> devicesFunctionsMap = {
"range": ["normal", "alarm"]
})),
FunctionModel(
code: 'factory_reset',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'factory_reset', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'alarm_active',
type: functionTypesMap['String'],
@ -145,8 +139,7 @@ Map<DeviceType, List<FunctionModel>> devicesFunctionsMap = {
FunctionModel(
code: 'sensitivity',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "", "min": 1, "max": 10, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "", "min": 1, "max": 10, "scale": 0, "step": 1})),
],
DeviceType.DoorLock: [
FunctionModel(
@ -154,9 +147,7 @@ Map<DeviceType, List<FunctionModel>> devicesFunctionsMap = {
type: functionTypesMap['Raw'],
values: ValueModel.fromJson({})),
FunctionModel(
code: 'remote_no_dp_key',
type: functionTypesMap['Raw'],
values: ValueModel.fromJson({})),
code: 'remote_no_dp_key', type: functionTypesMap['Raw'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'normal_open_switch',
type: functionTypesMap['Boolean'],
@ -166,87 +157,64 @@ Map<DeviceType, List<FunctionModel>> devicesFunctionsMap = {
FunctionModel(
code: 'far_detection',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "cm", "min": 75, "max": 600, "scale": 0, "step": 75})),
values: ValueModel.fromJson({"unit": "cm", "min": 75, "max": 600, "scale": 0, "step": 75})),
FunctionModel(
code: 'presence_time',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "Min", "min": 0, "max": 65535, "scale": 0, "step": 1})),
values:
ValueModel.fromJson({"unit": "Min", "min": 0, "max": 65535, "scale": 0, "step": 1})),
FunctionModel(
code: 'motion_sensitivity_value',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "", "min": 1, "max": 5, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "", "min": 1, "max": 5, "scale": 0, "step": 1})),
FunctionModel(
code: 'motionless_sensitivity',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "", "min": 1, "max": 5, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "", "min": 1, "max": 5, "scale": 0, "step": 1})),
FunctionModel(
code: 'indicator',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'indicator', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
],
DeviceType.OneGang: [
FunctionModel(
code: 'switch_1',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_1', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'countdown_1',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
],
DeviceType.TwoGang: [
FunctionModel(
code: 'switch_1',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_1', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'switch_2',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_2', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'countdown_1',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
FunctionModel(
code: 'countdown_2',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
],
DeviceType.ThreeGang: [
FunctionModel(
code: 'switch_1',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_1', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'switch_2',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_2', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'switch_3',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_3', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'countdown_1',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
FunctionModel(
code: 'countdown_2',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
FunctionModel(
code: 'countdown_3',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
],
DeviceType.Curtain: [
FunctionModel(
@ -258,19 +226,15 @@ Map<DeviceType, List<FunctionModel>> devicesFunctionsMap = {
FunctionModel(
code: 'percent_control',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "%", "min": 0, "max": 100, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "%", "min": 0, "max": 100, "scale": 0, "step": 1})),
],
DeviceType.WH: [
FunctionModel(
code: 'switch_1',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_1', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'countdown_1',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
FunctionModel(
code: 'relay_status',
type: functionTypesMap['Enum'],
@ -294,9 +258,7 @@ Map<DeviceType, List<FunctionModel>> devicesFunctionsMap = {
],
DeviceType.DS: [
FunctionModel(
code: 'doorcontact_state',
type: functionTypesMap['Raw'],
values: ValueModel.fromJson({})),
code: 'doorcontact_state', type: functionTypesMap['Raw'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'battery_percentage',
type: functionTypesMap['Integer'],
@ -304,14 +266,11 @@ Map<DeviceType, List<FunctionModel>> devicesFunctionsMap = {
],
DeviceType.OneTouch: [
FunctionModel(
code: 'switch_1',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_1', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'countdown_1',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
FunctionModel(
code: 'relay_status',
type: functionTypesMap['Enum'],
@ -333,23 +292,17 @@ Map<DeviceType, List<FunctionModel>> devicesFunctionsMap = {
],
DeviceType.TowTouch: [
FunctionModel(
code: 'switch_1',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_1', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'switch_2',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_2', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'countdown_1',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
FunctionModel(
code: 'countdown_2',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
FunctionModel(
code: 'relay_status',
type: functionTypesMap['Enum'],
@ -377,32 +330,23 @@ Map<DeviceType, List<FunctionModel>> devicesFunctionsMap = {
],
DeviceType.ThreeTouch: [
FunctionModel(
code: 'switch_1',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_1', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'switch_2',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_2', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'switch_3',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_3', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'countdown_1',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
FunctionModel(
code: 'countdown_2',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
FunctionModel(
code: 'countdown_3',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 43200, "scale": 0, "step": 1})),
FunctionModel(
code: 'relay_status',
type: functionTypesMap['Enum'],
@ -436,24 +380,19 @@ Map<DeviceType, List<FunctionModel>> devicesFunctionsMap = {
],
DeviceType.GarageDoor: [
FunctionModel(
code: 'switch_1',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_1', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'countdown_1',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 86400, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 86400, "scale": 0, "step": 1})),
FunctionModel(
code: 'tr_timecon',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 120, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 120, "scale": 0, "step": 1})),
FunctionModel(
code: 'countdown_alarm',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 86400, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 86400, "scale": 0, "step": 1})),
FunctionModel(
code: 'door_control_1',
type: functionTypesMap['Enum'],
@ -474,24 +413,19 @@ Map<DeviceType, List<FunctionModel>> devicesFunctionsMap = {
DeviceType.WaterLeak: [],
DeviceType.PC: [
FunctionModel(
code: 'switch_1',
type: functionTypesMap['Boolean'],
values: ValueModel.fromJson({})),
code: 'switch_1', type: functionTypesMap['Boolean'], values: ValueModel.fromJson({})),
FunctionModel(
code: 'countdown_1',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 86400, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 86400, "scale": 0, "step": 1})),
FunctionModel(
code: 'tr_timecon',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 120, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 120, "scale": 0, "step": 1})),
FunctionModel(
code: 'countdown_alarm',
type: functionTypesMap['Integer'],
values: ValueModel.fromJson(
{"unit": "s", "min": 0, "max": 86400, "scale": 0, "step": 1})),
values: ValueModel.fromJson({"unit": "s", "min": 0, "max": 86400, "scale": 0, "step": 1})),
FunctionModel(
code: 'door_control_1',
type: functionTypesMap['Enum'],
@ -585,11 +519,11 @@ List<Map<String, Object>> menuSections = [
'title': 'Home Management',
'color': ColorsManager.primaryColor,
'buttons': [
{
'title': 'Create a Unit',
'Icon': Assets.assetsIconsMenuIconsHomeManagementIconsCreateHome,
'page': const CreateUnitView()
},
// {
// 'title': 'Create a Unit',
// 'Icon': Assets.assetsIconsMenuIconsHomeManagementIconsCreateHome,
// 'page': const CreateUnitView()
// },
{
'title': 'Join a Unit',
'Icon': Assets.assetsIconsMenuIconsHomeManagementIconsJoinAHome,
@ -654,11 +588,7 @@ List<Map<String, Object>> menuSections = [
'Icon': Assets.assetsIconsMenuIconsMessagesCenterIconsMessages,
'page': null
},
{
'title': 'FAQs',
'Icon': Assets.assetsIconsMenuIconsMessagesCenterIconsFAQs,
'page': null
},
{'title': 'FAQs', 'Icon': Assets.assetsIconsMenuIconsMessagesCenterIconsFAQs, 'page': null},
{
'title': 'Help & Feedback',
'Icon': Assets.assetsIconsMenuIconsMessagesCenterIconsHelpAndFeedback,
@ -688,11 +618,7 @@ List<Map<String, Object>> menuSections = [
'title': 'Legal Information',
'color': const Color(0xFF001B72),
'buttons': [
{
'title': 'About',
'Icon': Assets.assetsIconsMenuIconsLeagalInfoIconsAbout,
'page': null
},
{'title': 'About', 'Icon': Assets.assetsIconsMenuIconsLeagalInfoIconsAbout, 'page': null},
{
'title': 'Privacy Policy',
'Icon': Assets.assetsIconsMenuIconsLeagalInfoIconsPrivacyPolicy,

View File

@ -5,7 +5,7 @@ description: This is the mobile application project, developed with Flutter for
# pub.dev using `flutter pub publish`. This is preferred for private packages.
publish_to: "none" # Remove this line if you wish to publish to pub.dev
version: 1.0.5+35
version: 1.0.7+40
environment:
sdk: ">=3.0.6 <4.0.0"