import 'package:fcs/helpers/theme.dart'; import 'package:fcs/pages/main/model/language_model.dart'; import 'package:fcs/pages/main/model/main_model.dart'; import 'package:fcs/pages/main/util.dart'; import 'package:fcs/pages/widgets/local_button.dart'; import 'package:fcs/pages/widgets/local_text.dart'; import 'package:fcs/pages/widgets/progress.dart'; import 'package:flutter/material.dart'; import 'package:pin_input_text_field/pin_input_text_field.dart'; import 'package:provider/provider.dart'; import '../../helpers/shared_pref.dart'; import '../../localization/app_translations.dart'; class PinLoginPage extends StatefulWidget { const PinLoginPage({super.key}); @override State createState() => _PinLoginPageState(); } class _PinLoginPageState extends State { bool _isLoading = false; String pin = ""; String prefixText = "FCS-"; final _formKey = GlobalKey(); TextEditingController _fcsIdCtl = new TextEditingController(); @override void initState() { _init(); super.initState(); } _init() async { await SharedPref.setPinLockOn(true); } Future _onWillPop() async { // Show the confirmation dialog return (await showDialog( context: context, builder: (context) => AlertDialog( title: Center( child: LocalText(context, 'btn.exit_confirm', color: primaryColor), ), content: Container( child: Row( mainAxisAlignment: MainAxisAlignment.spaceAround, crossAxisAlignment: CrossAxisAlignment.center, children: [ TextButton( style: TextButton.styleFrom( backgroundColor: Colors.grey[300], shape: RoundedRectangleBorder( borderRadius: BorderRadius.circular(5.0))), child: Text( AppTranslations.of(context)!.text('btn.cancel'), style: Provider.of(context).isEng ? TextStyle(color: primaryColor) : TextStyle( fontFamily: 'Myanmar3', color: primaryColor), ), onPressed: () { Navigator.of(context).pop(false); }), SizedBox( width: 0, ), TextButton( style: TextButton.styleFrom( backgroundColor: primaryColor, shape: RoundedRectangleBorder( borderRadius: BorderRadius.circular(5.0))), child: Text(AppTranslations.of(context)!.text('btn.ok'), style: Provider.of(context).isEng ? TextStyle( color: Colors.white, fontWeight: FontWeight.bold) : TextStyle( color: Colors.white, fontWeight: FontWeight.bold, fontFamily: 'Myanmar3')), onPressed: () { Navigator.of(context).pop(true); }) ], ), ), ), )) ?? false; } Widget build(BuildContext context) { final fcsIdBox = TextFormField( controller: _fcsIdCtl, onChanged: (value) { _fcsIdCtl.value = TextEditingValue( text: value.toUpperCase(), selection: _fcsIdCtl.selection, ); }, autofocus: true, autovalidateMode: AutovalidateMode.onUserInteraction, validator: (value) { if (value == null || value.isEmpty) { return 'Please enter FCS ID'; } return null; }, style: TextStyle( fontSize: 15, color: Colors.black87, fontWeight: FontWeight.w500), cursorColor: primaryColor, keyboardType: TextInputType.text, decoration: new InputDecoration( prefixIcon: Text( prefixText, style: TextStyle(color: Colors.black), ), prefixIconConstraints: BoxConstraints(minWidth: 0, minHeight: 0), contentPadding: EdgeInsets.all(0), labelStyle: newLabelStyle(color: Colors.black54, fontSize: 17), enabledBorder: UnderlineInputBorder( borderSide: BorderSide(color: primaryColor, width: 1.0)), border: UnderlineInputBorder( borderSide: BorderSide(color: primaryColor, width: 1.0)), focusedBorder: UnderlineInputBorder( borderSide: BorderSide(color: primaryColor, width: 1.0)), disabledBorder: UnderlineInputBorder( borderSide: BorderSide(color: primaryColor, width: 1.0)), errorStyle: TextStyle(color: dangerColor), ), ); final pinLoginLogo = Container( width: 70, height: 70, child: FittedBox( child: Image.asset( "assets/logo.jpg", ), fit: BoxFit.fitHeight, ), ); final pinInputBox = FormField( validator: (value) { if (pin == "") { return "Please enter PIN"; } if (pin.length < 6) { return "PIN must be 6 digit"; } return null; }, autovalidateMode: AutovalidateMode.onUserInteraction, builder: (state) { return Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ PinInputTextField( cursor: Cursor( color: primaryColor, enabled: true, width: 2, height: 23), pinLength: 6, decoration: BoxLooseDecoration( strokeColorBuilder: PinListenColorBuilder( primaryColor, Colors.grey.shade400), errorTextStyle: TextStyle(color: dangerColor)), textInputAction: TextInputAction.done, autoFocus: false, onChanged: _pinChange, ), Padding( padding: const EdgeInsets.only(top: 8), child: pin == "" || pin.length < 6 ? SizedBox( height: 20, child: Text(state.errorText ?? "", style: TextStyle(color: dangerColor, fontSize: 12)), ) : const SizedBox(height: 20), ) ], ); }); final loginBtn = Padding( padding: EdgeInsets.only(top: 30), child: LocalButton( textKey: "welcome.pinlogin", callBack: _login, ), ); // ignore: deprecated_member_use return WillPopScope( onWillPop: _onWillPop, child: LocalProgress( inAsyncCall: _isLoading, child: new Scaffold( body: Form( key: _formKey, child: ListView( padding: EdgeInsets.only(top: 80, left: 15, right: 15, bottom: 20), children: [ pinLoginLogo, Padding( padding: EdgeInsets.only(top: 20, bottom: 20), child: Center( child: LocalText(context, "welcome.pinlogin", color: Colors.black, fontSize: 18), ), ), LocalText( context, "welcome.pinlogin.fcsid", color: Colors.black54, fontSize: 15, ), fcsIdBox, Padding( padding: EdgeInsets.only(top: 25, bottom: 20), child: LocalText( context, "welcome.pinlogin.pin", color: Colors.black54, fontSize: 15, )), pinInputBox, loginBtn, ], ), )), ), ); } _pinChange(pin) { setState(() { this.pin = pin; }); } _login() async { if (!_formKey.currentState!.validate()) { return; } String fcsId = "$prefixText${_fcsIdCtl.text}"; setState(() { _isLoading = true; }); try { await context.read().pinLogin(fcsID: fcsId, pin: pin); Navigator.pushNamedAndRemoveUntil(context, "/home", (r) => false); } catch (e) { showMsgDialog(context, "Error", e.toString()); } finally { setState(() { _isLoading = false; }); } } }