diff --git a/lib/features/devices/bloc/smart_door_bloc/smart_door_bloc.dart b/lib/features/devices/bloc/smart_door_bloc/smart_door_bloc.dart index e8c0f46..9553676 100644 --- a/lib/features/devices/bloc/smart_door_bloc/smart_door_bloc.dart +++ b/lib/features/devices/bloc/smart_door_bloc/smart_door_bloc.dart @@ -354,6 +354,7 @@ class SmartDoorBloc extends Bloc { Future selectTimeOnlinePassword( SelectTimeOnlinePasswordEvent event, Emitter emit) async { + effectiveTimeTimeStamp ??= DateTime.now().millisecondsSinceEpoch ~/ 1000; emit(ChangeTimeState()); final DateTime? picked = await showDatePicker( context: event.context, @@ -398,7 +399,13 @@ class SmartDoorBloc extends Bloc { selectedDateTime.minute, ).millisecondsSinceEpoch ~/ 1000; // Divide by 1000 to remove milliseconds + final currentTimestamp = DateTime.now().millisecondsSinceEpoch ~/ 1000; if (event.isEffective) { + if (selectedTimestamp < currentTimestamp) { + CustomSnackBar.displaySnackBar( + 'Effective Time cannot be later than Expiration Time.'); + return; + } if (expirationTimeTimeStamp != null && selectedTimestamp > expirationTimeTimeStamp!) { CustomSnackBar.displaySnackBar( diff --git a/lib/features/devices/view/widgets/name_time_widget.dart b/lib/features/devices/view/widgets/name_time_widget.dart index 5adbe2e..6c9815b 100644 --- a/lib/features/devices/view/widgets/name_time_widget.dart +++ b/lib/features/devices/view/widgets/name_time_widget.dart @@ -11,6 +11,9 @@ class NameTimeWidget extends StatelessWidget { @override Widget build(BuildContext context) { + DateTime now = DateTime.now(); + DateTime cleaned = + DateTime(now.year, now.month, now.day, now.hour, now.minute); return DefaultContainer( padding: const EdgeInsets.all(20), child: Column( @@ -59,19 +62,22 @@ class NameTimeWidget extends StatelessWidget { width: MediaQuery.of(context).size.width / 3.5, child: InkWell( onTap: () { - - BlocProvider.of(context).add(SelectTimeOnlinePasswordEvent(context: context, isEffective: true)); + BlocProvider.of(context).add( + SelectTimeOnlinePasswordEvent( + context: context, isEffective: true)); }, child: Text( - BlocProvider.of(context).effectiveTime, - style: TextStyle(fontSize: 14, - color: BlocProvider.of(context).effectiveTime == + BlocProvider.of(context) + .effectiveTime == 'Select Time' - ? ColorsManager.textGray - : null), + ? cleaned.toString() + : BlocProvider.of(context) + .effectiveTime, + style: TextStyle(fontSize: 14), ), )), - ],), + ], + ), ), const Divider( color: ColorsManager.graysColor, @@ -96,10 +102,13 @@ class NameTimeWidget extends StatelessWidget { context: context, isEffective: false)); }, child: Text( - BlocProvider.of(context).expirationTime, + BlocProvider.of(context) + .expirationTime, style: TextStyle( fontSize: 14, - color: BlocProvider.of(context).expirationTime == 'Select Time' + color: BlocProvider.of(context) + .expirationTime == + 'Select Time' ? ColorsManager.textGray : null), ), diff --git a/lib/features/devices/view/widgets/smart_door/offline_timeLimit_password_page.dart b/lib/features/devices/view/widgets/smart_door/offline_timeLimit_password_page.dart index 9a55e82..a75db32 100644 --- a/lib/features/devices/view/widgets/smart_door/offline_timeLimit_password_page.dart +++ b/lib/features/devices/view/widgets/smart_door/offline_timeLimit_password_page.dart @@ -18,7 +18,8 @@ import 'package:syncrow_app/utils/resource_manager/font_manager.dart'; class CreateOfflineTimeLimitPasswordPage extends StatelessWidget { final String? deviceId; final String? type; - const CreateOfflineTimeLimitPasswordPage({super.key, this.deviceId, this.type}); + const CreateOfflineTimeLimitPasswordPage( + {super.key, this.deviceId, this.type}); @override Widget build(BuildContext context) { bool isRepeat = false; @@ -28,9 +29,7 @@ class CreateOfflineTimeLimitPasswordPage extends StatelessWidget { child: BlocConsumer( listener: (context, state) { if (state is FailedState) { - CustomSnackBar.displaySnackBar( - state.errorMessage - ); + CustomSnackBar.displaySnackBar(state.errorMessage); } if (state is IsRepeatState) { isRepeat = state.repeat; @@ -39,6 +38,10 @@ class CreateOfflineTimeLimitPasswordPage extends StatelessWidget { generated = state.generated; } }, builder: (context, state) { + DateTime now = DateTime.now(); + DateTime cleaned = + DateTime(now.year, now.month, now.day, now.hour, now.minute); + final smartDoorBloc = BlocProvider.of(context); return DefaultScaffold( appBar: AppBar( @@ -85,46 +88,56 @@ class CreateOfflineTimeLimitPasswordPage extends StatelessWidget { Flexible( child: Row( mainAxisAlignment: MainAxisAlignment.center, - children: smartDoorBloc.passwordController.text.isEmpty ? - List.generate(10, (index) { - return const Padding( - padding: EdgeInsets.symmetric( - horizontal: 4.0, - vertical: 15), - child: Icon( - Icons.circle, - size: 20.0, - color: Colors.black, - ), - ); - }) : [ - Expanded( - child: Row( - children: [ + children: smartDoorBloc + .passwordController.text.isEmpty + ? List.generate(10, (index) { + return const Padding( + padding: EdgeInsets.symmetric( + horizontal: 4.0, + vertical: 15), + child: Icon( + Icons.circle, + size: 20.0, + color: Colors.black, + ), + ); + }) + : [ Expanded( - child: BodyLarge( - style: const TextStyle( - color: ColorsManager.primaryColor, - fontWeight: FontWeight.bold, - letterSpacing: 8.0, - fontSize: 25, - wordSpacing: 2), - textAlign: TextAlign.center, - text: smartDoorBloc.passwordController.text, - fontSize: 25, + child: Row( + children: [ + Expanded( + child: BodyLarge( + style: const TextStyle( + color: ColorsManager + .primaryColor, + fontWeight: + FontWeight.bold, + letterSpacing: 8.0, + fontSize: 25, + wordSpacing: 2), + textAlign: + TextAlign.center, + text: smartDoorBloc + .passwordController + .text, + fontSize: 25, + ), + ), + IconButton( + onPressed: () async { + await Clipboard.setData( + ClipboardData( + text: smartDoorBloc + .passwordController + .text)); + }, + icon: const Icon( + Icons.copy)), + ], ), ), - IconButton( - onPressed: () async { - await Clipboard.setData( - ClipboardData(text: smartDoorBloc.passwordController.text) - ); - }, - icon: const Icon(Icons.copy)), ], - ), - ), - ], )), const SizedBox( width: 10, @@ -135,91 +148,142 @@ class CreateOfflineTimeLimitPasswordPage extends StatelessWidget { padding: const EdgeInsets.all(20), child: Column( children: [ - Row( - mainAxisAlignment: MainAxisAlignment.spaceBetween, - children: [ - Expanded( - child: Container( - padding: const EdgeInsets.all(10.0), - child: const BodyMedium( - text: 'Password Name', - fontWeight: FontWeight.normal, - ), - ), - ), - SizedBox( - width: MediaQuery.of(context).size.width / 2.6, - child: TextFormField( - controller: BlocProvider.of(context).passwordNameController, - decoration: - const InputDecoration( - hintText: 'Enter The Name', - hintStyle: TextStyle( - fontSize: 14, - color: ColorsManager.textGray) - ), - )), - ], - ), - Column( - children: [ - const Divider(color: ColorsManager.graysColor,), - Padding( - padding: const EdgeInsets.all(10.0), - child: Row( - mainAxisAlignment: MainAxisAlignment.spaceBetween, - children: [ - const Expanded( - child: BodyMedium( - text: 'Effective Time', - fontWeight: FontWeight.normal, + Row( + mainAxisAlignment: + MainAxisAlignment.spaceBetween, + children: [ + Expanded( + child: Container( + padding: + const EdgeInsets.all(10.0), + child: const BodyMedium( + text: 'Password Name', + fontWeight: FontWeight.normal, + ), + ), ), - ), - SizedBox( - width: MediaQuery.of(context).size.width / 3.5, - child: InkWell( - onTap: () { - BlocProvider.of(context).add(SelectTimeEvent(context: context, isEffective: true)); - }, - child: Text( - BlocProvider.of(context).effectiveTime, - style: TextStyle( - fontSize: 14, - color: BlocProvider.of(context).effectiveTime == - 'Select Time' ? ColorsManager.textGray : null), - ), - )),], - ), - ), - const Divider( - color: ColorsManager.graysColor, - ), - Padding( - padding: const EdgeInsets.all(10.0), - child: Row(mainAxisAlignment: - MainAxisAlignment.spaceBetween, - children: [ - const Expanded( - child: BodyMedium( - text: 'Expiration Time', - fontWeight: FontWeight.normal, - ), - ), - SizedBox( - width: MediaQuery.of(context).size.width / 3.5, - child: InkWell( - onTap: () { - BlocProvider.of(context).add(SelectTimeEvent( - context: context, - isEffective: false)); - }, - child: Text( - BlocProvider.of(context).expirationTime, - style: TextStyle( - fontSize: 14, - color: BlocProvider.of(context) - .expirationTime == 'Select Time' ? ColorsManager - .textGray : null), + SizedBox( + width: MediaQuery.of(context) + .size + .width / + 2.6, + child: TextFormField( + controller: BlocProvider.of< + SmartDoorBloc>(context) + .passwordNameController, + decoration: + const InputDecoration( + hintText: + 'Enter The Name', + hintStyle: TextStyle( + fontSize: 14, + color: ColorsManager + .textGray)), + )), + ], + ), + Column( + children: [ + const Divider( + color: ColorsManager.graysColor, + ), + Padding( + padding: const EdgeInsets.all(10.0), + child: Row( + mainAxisAlignment: + MainAxisAlignment + .spaceBetween, + children: [ + const Expanded( + child: BodyMedium( + text: 'Effective Time', + fontWeight: + FontWeight.normal, + ), + ), + SizedBox( + width: + MediaQuery.of(context) + .size + .width / + 3.5, + child: InkWell( + onTap: () { + BlocProvider.of< + SmartDoorBloc>( + context) + .add( + SelectTimeEvent( + context: + context, + isEffective: + true)); + }, + child: Text( + BlocProvider.of( + context) + .effectiveTime == + 'Select Time' + ? cleaned.toString() + : BlocProvider.of< + SmartDoorBloc>( + context) + .effectiveTime, + style: TextStyle( + fontSize: 14, + ), + ), + )), + ], + ), + ), + const Divider( + color: ColorsManager.graysColor, + ), + Padding( + padding: const EdgeInsets.all(10.0), + child: Row( + mainAxisAlignment: + MainAxisAlignment + .spaceBetween, + children: [ + const Expanded( + child: BodyMedium( + text: 'Expiration Time', + fontWeight: + FontWeight.normal, + ), + ), + SizedBox( + width: MediaQuery.of(context) + .size + .width / + 3.5, + child: InkWell( + onTap: () { + BlocProvider.of< + SmartDoorBloc>( + context) + .add(SelectTimeEvent( + context: context, + isEffective: + false)); + }, + child: Text( + BlocProvider.of< + SmartDoorBloc>( + context) + .expirationTime, + style: TextStyle( + fontSize: 14, + color: BlocProvider.of< + SmartDoorBloc>( + context) + .expirationTime == + 'Select Time' + ? ColorsManager + .textGray + : null), ), ), ), @@ -238,7 +302,8 @@ class CreateOfflineTimeLimitPasswordPage extends StatelessWidget { ), const BodyMedium( textAlign: TextAlign.center, - text: 'Use the time-limited password at least once within 24 hours after the password takes effect. Otherwise, the password becomes invalid.', + text: + 'Use the time-limited password at least once within 24 hours after the password takes effect. Otherwise, the password becomes invalid.', fontWeight: FontWeight.normal, fontColor: ColorsManager.grayColor, ), @@ -256,10 +321,13 @@ class CreateOfflineTimeLimitPasswordPage extends StatelessWidget { backgroundColor: ColorsManager.primaryColor, onPressed: () async { if (generated == false) { - smartDoorBloc.add(GenerateAndSavePasswordTimeLimitEvent(context: context)); + smartDoorBloc.add( + GenerateAndSavePasswordTimeLimitEvent( + context: context)); } else { - if(smartDoorBloc.passwordNameController.text.isNotEmpty){ - smartDoorBloc.add(RenamePasswordEvent()); + if (smartDoorBloc + .passwordNameController.text.isNotEmpty) { + smartDoorBloc.add(RenamePasswordEvent()); } Navigator.of(context).pop(true); }