import 'dart:io'; import 'package:firebase_auth/firebase_auth.dart'; import 'package:firebase_messaging/firebase_messaging.dart'; import 'package:flutter/cupertino.dart'; import 'package:flutter/gestures.dart'; import 'package:flutter/material.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; import 'package:news/cubits/Auth/authCubit.dart'; import 'package:news/cubits/Auth/registerTokenCubit.dart'; import 'package:news/cubits/appLocalizationCubit.dart'; import 'package:news/cubits/appSystemSettingCubit.dart'; import 'package:news/cubits/privacyTermsCubit.dart'; import 'package:news/cubits/settingCubit.dart'; import 'package:news/ui/screens/auth/Widgets/bottomComBtn.dart'; import 'package:news/ui/screens/auth/Widgets/fieldFocusChange.dart'; import 'package:news/ui/screens/auth/Widgets/setConfimPass.dart'; import 'package:news/ui/screens/auth/Widgets/setDivider.dart'; import 'package:news/ui/screens/auth/Widgets/setEmail.dart'; import 'package:news/ui/screens/auth/Widgets/setForgotPass.dart'; import 'package:news/ui/screens/auth/Widgets/setLoginAndSignUpBtn.dart'; import 'package:news/ui/screens/auth/Widgets/setName.dart'; import 'package:news/ui/screens/auth/Widgets/setPassword.dart'; import 'package:news/ui/screens/auth/Widgets/setTermPolicy.dart'; import 'package:news/ui/styles/colors.dart'; import 'package:news/ui/widgets/SnackBarWidget.dart'; import 'package:news/ui/widgets/customTextBtn.dart'; import 'package:news/ui/widgets/customTextLabel.dart'; import 'package:news/utils/constant.dart'; import 'package:news/utils/internetConnectivity.dart'; import 'package:news/utils/uiUtils.dart'; import 'package:news/app/routes.dart'; import 'package:news/cubits/Auth/socialSignUpCubit.dart'; import 'package:news/utils/validators.dart'; class LoginScreen extends StatefulWidget { final bool? isFromApp; const LoginScreen({super.key, this.isFromApp}); @override LoginScreenState createState() => LoginScreenState(); static Route route(RouteSettings routeSettings) { if (routeSettings.arguments == null) { return CupertinoPageRoute(builder: (_) => const LoginScreen()); } else { final arguments = routeSettings.arguments as Map; return CupertinoPageRoute(builder: (_) => LoginScreen(isFromApp: arguments['isFromApp'] ?? false)); } } } class LoginScreenState extends State with TickerProviderStateMixin { final GlobalKey _formkey = GlobalKey(); TabController? _tabController; FocusNode emailFocus = FocusNode(); FocusNode passFocus = FocusNode(); FocusNode nameFocus = FocusNode(); FocusNode emailSFocus = FocusNode(); FocusNode passSFocus = FocusNode(); FocusNode confPassFocus = FocusNode(); TextEditingController? emailC, passC, sEmailC, sPassC, sNameC, sConfPassC; String? name, email, pass, mobile, profile, confPass; bool isPolicyAvailable = false; bool isObscure = true; //setPassword widget @override void initState() { Future.delayed(Duration.zero, () { context.read().getPrivacyTerms(langId: context.read().state.id); }); _tabController = TabController(length: 2, vsync: this, initialIndex: 0); assignAllTextController(); _tabController!.addListener(() { FocusScope.of(context).unfocus(); //dismiss keyboard clearLoginTextFields(); clearSignUpTextFields(); }); super.initState(); } assignAllTextController() { emailC = TextEditingController(); passC = TextEditingController(); sEmailC = TextEditingController(); sPassC = TextEditingController(); sNameC = TextEditingController(); sConfPassC = TextEditingController(); } clearSignUpTextFields() { setState(() { sNameC!.clear(); sEmailC!.clear(); sPassC!.clear(); sConfPassC!.clear(); }); } clearLoginTextFields() { setState(() { emailC!.clear(); passC!.clear(); }); } disposeAllTextController() { emailC!.dispose(); passC!.dispose(); sEmailC!.dispose(); sPassC!.dispose(); sNameC!.dispose(); sConfPassC!.dispose(); } @override void dispose() { _tabController?.dispose(); disposeAllTextController(); super.dispose(); } showContent() { return BlocConsumer( bloc: context.read(), listener: (context, state) async { if (state is SocialSignUpFailure) { showSnackBar(state.errorMessage, context); } if (state is SocialSignUpSuccess) { context.read().checkAuthStatus(); if (state.authModel.status == "0") { showSnackBar(UiUtils.getTranslatedLabel(context, 'deactiveMsg'), context); } else { FirebaseMessaging.instance.getToken().then((token) async { if (token != null) { context.read().registerToken(fcmId: token, context: context); if (token != context.read().getSettings().token) { context.read().changeFcmToken(token); } if (state.authModel.isFirstLogin != null && state.authModel.isFirstLogin!.isNotEmpty && state.authModel.isFirstLogin == "0" && state.authModel.type != loginApple) { Navigator.of(context).pushNamedAndRemoveUntil(Routes.editUserProfile, (route) => false, arguments: {"from": "login"}); } else if (widget.isFromApp == true) { Navigator.pop(context); } else { Navigator.pushNamedAndRemoveUntil(context, Routes.home, (route) => false); } } }); } } }, builder: (context, state) { return Form( key: _formkey, child: Stack( children: [ Container( padding: const EdgeInsetsDirectional.only(top: 30.0, bottom: 5.0, start: 20.0, end: 20.0), width: MediaQuery.of(context).size.width, child: Column(crossAxisAlignment: CrossAxisAlignment.center, children: [skipBtn(), showTabs(), showTabBarView()]), ), if (state is SocialSignUpProgress) UiUtils.showCircularProgress(true, Theme.of(context).primaryColor), ], )); }); } skipBtn() { return Align( alignment: AlignmentDirectional.topEnd, child: CustomTextButton( onTap: () { Navigator.of(context).pushReplacementNamed(Routes.home, arguments: false); }, text: UiUtils.getTranslatedLabel(context, 'skip'), color: UiUtils.getColorScheme(context).primaryContainer.withOpacity(0.7), )); } showTabs() { return Align( alignment: Alignment.centerLeft, child: DefaultTabController( length: 2, child: Container( padding: const EdgeInsetsDirectional.only(start: 10.0), child: TabBar( overlayColor: WidgetStateProperty.all(Colors.transparent), controller: _tabController, labelStyle: Theme.of(context).textTheme.titleSmall?.copyWith(fontWeight: FontWeight.w600, letterSpacing: 0.5), labelPadding: EdgeInsets.zero, labelColor: backgroundColor, unselectedLabelColor: UiUtils.getColorScheme(context).primaryContainer, indicator: BoxDecoration(borderRadius: BorderRadius.circular(50), color: UiUtils.getColorScheme(context).secondaryContainer), tabs: [Tab(text: UiUtils.getTranslatedLabel(context, 'signInTab')), Tab(text: UiUtils.getTranslatedLabel(context, 'signupBtn'))])), )); } bool validateAndSave() { final form = _formkey.currentState; form!.save(); if (!isPolicyAvailable) { showSnackBar(UiUtils.getTranslatedLabel(context, 'addTCFirst'), context); return false; } return form.validate(); } Widget setPassword({required FocusNode currFocus, FocusNode? nextFocus, required TextEditingController passC, required String pass, required double topPad, required bool isLogin}) { return Padding( padding: EdgeInsets.only(top: topPad), child: TextFormField( focusNode: currFocus, textInputAction: isLogin ? TextInputAction.done : TextInputAction.next, controller: passC, obscureText: isObscure, style: Theme.of(context).textTheme.titleMedium?.copyWith( color: UiUtils.getColorScheme(context).primaryContainer, ), validator: (val) => Validators.passValidation(val!, context), onFieldSubmitted: (v) { if (!isLogin) { fieldFocusChange(context, currFocus, nextFocus!); } }, onChanged: (String value) { pass = value; setState(() {}); }, decoration: InputDecoration( hintText: UiUtils.getTranslatedLabel(context, 'passLbl'), hintStyle: Theme.of(context).textTheme.titleMedium?.copyWith( color: UiUtils.getColorScheme(context).primaryContainer.withOpacity(0.5), ), suffixIcon: Padding( padding: const EdgeInsetsDirectional.only(end: 12.0), child: IconButton( icon: isObscure ? Icon(Icons.visibility_rounded, size: 20, color: UiUtils.getColorScheme(context).primaryContainer.withOpacity(0.6)) : Icon(Icons.visibility_off_rounded, size: 20, color: UiUtils.getColorScheme(context).primaryContainer.withOpacity(0.6)), splashColor: Colors.transparent, onPressed: () { setState(() => isObscure = !isObscure); }, )), filled: true, fillColor: Theme.of(context).colorScheme.surface, contentPadding: const EdgeInsets.symmetric(horizontal: 25, vertical: 17), focusedBorder: OutlineInputBorder( borderSide: BorderSide(color: UiUtils.getColorScheme(context).outline.withOpacity(0.7)), borderRadius: BorderRadius.circular(10.0), ), enabledBorder: OutlineInputBorder( borderSide: BorderSide.none, borderRadius: BorderRadius.circular(10.0), ), ), ), ); } showTabBarView() { return Expanded( child: Container( alignment: Alignment.center, height: MediaQuery.of(context).size.height * 1.0, child: TabBarView( controller: _tabController, dragStartBehavior: DragStartBehavior.start, children: [ //Login SingleChildScrollView( child: Padding( padding: const EdgeInsets.symmetric(horizontal: 5.0), child: Column(children: [ loginTxt(), SetEmail(currFocus: emailFocus, nextFocus: passFocus, emailC: emailC!, email: email ?? '', topPad: 20), SetPassword(currFocus: passFocus, passC: passC!, pass: pass ?? '', topPad: 20, isLogin: true), setForgotPass(context), SetLoginAndSignUpBtn( onTap: () async { FocusScope.of(context).unfocus(); //dismiss keyboard if (validateAndSave()) { if (await InternetConnectivity.isNetworkAvailable()) { context.read().socialSignUpUser(email: emailC!.text.trim(), password: passC!.text, authProvider: AuthProviders.email, context: context); } else { showSnackBar(UiUtils.getTranslatedLabel(context, 'internetmsg'), context); } } }, text: 'loginTxt', topPad: 20), SetDividerOR(), bottomBtn(), BlocConsumer(listener: (context, state) { if (state is PrivacyTermsFetchSuccess) { isPolicyAvailable = true; } if (state is PrivacyTermsFetchFailure) { isPolicyAvailable = false; } }, builder: (context, state) { return (state is PrivacyTermsFetchSuccess) ? setTermPolicyTxt(context, state) : const SizedBox.shrink(); }) ]), )), //SignUp SingleChildScrollView( child: Padding( padding: const EdgeInsets.symmetric(horizontal: 5.0), child: Column( children: [ signUpTxt(), SetName(currFocus: nameFocus, nextFocus: emailSFocus, nameC: sNameC!, name: sNameC!.text), SetEmail(currFocus: emailSFocus, nextFocus: passSFocus, emailC: sEmailC!, email: sEmailC!.text, topPad: 20), setPassword(currFocus: passSFocus, nextFocus: confPassFocus, passC: sPassC!, pass: sPassC!.text, topPad: 20, isLogin: false), SetConfirmPass(currFocus: confPassFocus, confPassC: sConfPassC!, confPass: sConfPassC!.text, pass: sPassC!.text), SetLoginAndSignUpBtn( onTap: () async { FocusScope.of(context).unfocus(); //dismiss keyboard final form = _formkey.currentState; if (form!.validate()) { form.save(); if (await InternetConnectivity.isNetworkAvailable()) { registerWithEmailPassword(sEmailC!.text.trim(), sPassC!.text.trim()); } else { showSnackBar(UiUtils.getTranslatedLabel(context, 'internetmsg'), context); } } }, text: 'signupBtn', topPad: 25) ], ), )) ], )), ); } registerWithEmailPassword(String email, String password) async { try { final credential = await FirebaseAuth.instance.createUserWithEmailAndPassword(email: email, password: password); User? user = credential.user; user!.updateDisplayName(sNameC!.text.trim()).then((value) => debugPrint("updated name is - ${user.displayName}")); user.reload(); user.sendEmailVerification().then((value) => showSnackBar('${UiUtils.getTranslatedLabel(context, 'verifSentMail')} $email', context)); clearSignUpTextFields(); _tabController!.animateTo(0); FocusScope.of(context).requestFocus(emailFocus); } on FirebaseAuthException catch (e) { if (e.code == 'weakPassword') { showSnackBar(UiUtils.getTranslatedLabel(context, 'weakPassword'), context); } if (e.code == 'email-already-in-use') { showSnackBar(UiUtils.getTranslatedLabel(context, 'emailAlreadyInUse'), context); } } catch (e) {} } loginTxt() { return Align( alignment: Alignment.centerLeft, child: Padding( padding: const EdgeInsetsDirectional.only(top: 20.0, start: 10.0), child: CustomTextLabel( text: 'loginDescr', textStyle: Theme.of(context).textTheme.headlineSmall?.copyWith(color: UiUtils.getColorScheme(context).primaryContainer, fontWeight: FontWeight.w800, letterSpacing: 0.5), textAlign: TextAlign.left, ), )); } signUpTxt() { return Align( alignment: Alignment.centerLeft, child: Padding( padding: const EdgeInsetsDirectional.only(top: 35.0, start: 10.0), child: CustomTextLabel( text: 'signupDescr', textStyle: Theme.of(context).textTheme.headlineSmall?.copyWith(color: UiUtils.getColorScheme(context).primaryContainer, fontWeight: FontWeight.w800, letterSpacing: 0.5), textAlign: TextAlign.left, ), )); } bottomBtn() { return Padding( padding: const EdgeInsets.only(top: 20.0), child: Column( mainAxisAlignment: (fblogInEnabled) ? MainAxisAlignment.spaceBetween : MainAxisAlignment.spaceAround, children: [ BottomCommButton( btnCaption: 'google', onTap: () { if (!isPolicyAvailable) { showSnackBar(UiUtils.getTranslatedLabel(context, 'addTCFirst'), context); } else { context.read().socialSignUpUser(authProvider: AuthProviders.gmail, context: context); } }, img: 'google_button'), if (fblogInEnabled) BottomCommButton( onTap: () { if (!isPolicyAvailable) { showSnackBar(UiUtils.getTranslatedLabel(context, 'addTCFirst'), context); } else { context.read().socialSignUpUser(authProvider: AuthProviders.fb, context: context); } }, img: 'facebook_button', btnCaption: 'fb'), if (Platform.isIOS) BottomCommButton( onTap: () { if (!isPolicyAvailable) { showSnackBar(UiUtils.getTranslatedLabel(context, 'addTCFirst'), context); } else { context.read().socialSignUpUser(authProvider: AuthProviders.apple, context: context); } }, img: 'apple_logo', btnCaption: 'apple', btnColor: UiUtils.getColorScheme(context).primaryContainer), if (context.read().getMobileLoginMode() != "" && context.read().getMobileLoginMode() != "0") BottomCommButton( onTap: () { if (!isPolicyAvailable) { showSnackBar(UiUtils.getTranslatedLabel(context, 'addTCFirst'), context); } else { Navigator.of(context).pushNamed(Routes.requestOtp); } }, img: 'phone_button', btnCaption: 'mobileLbl', btnColor: UiUtils.getColorScheme(context).primaryContainer) ], ), ); } @override Widget build(BuildContext context) { return Scaffold( body: showContent(), ); } }