Skip to content
  • Home
  • Meet team
  • News
  • Tips
  • Tutorials
    • Android
      • Kotlin
    • Angular
    • Arduino
    • Flutter
    • Laravel
    • Linux
  • Services
  • Contact us
  • Donation
  • Twitter
  • YouTube
  • GooglePlus
  • LinkedIn
  • rss
  • Search
Flutter, Tutorials
by Azem ZejnilovicDecember 30, 20189:17 amDecember 30, 2018

Flutter: Login and registration with Firebase

In this tutorial I’ll show you probably the most elegant way of implementing the Login and Registration with Firebase and Flutter. It includes separation of two pages, state management and methods for returning the Widget objects. I strongly recommend you to study this code a bit, because it is not complicated and you will gain a lot from it.

NOTE: For this code to work, you must set up the firebase project and include all the dependencies for your project. It is too complicated for this type of tutorial, so I will just put a link for a tutorial that is pretty straightforward and easy to follow: How to Setup Firebase in your Flutter project ?

After you do all that is shown in the link above, you are ready to go. Simple, right?
Here is the code of our main Widget:

import 'dart:convert';
import 'dart:async';
import 'package:flutter/material.dart';
import 'package:http/http.dart' as http;
import 'dart:math';
import 'package:positioning_drill_real/screens/login_page.dart';
import 'auth.dart';
import 'root_page.dart';

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
   @override
   Widgetbuild(BuildContext context) {
      returnMaterialApp(
         home: RootPage(auth: new Auth()),
         debugShowCheckedModeBanner: false,
         theme: ThemeData(primarySwatch: Colors.blue),
      );
   }
}

We want to use inherited widget, because there are dependencies which are used across the application. More specifically, we want to have authentication dependency available everywhere.
For that matter, create file called ‘auth.dart’ and copy this into it:

import 'dart:async';
import 'package:firebase_auth/firebase_auth.dart';

abstract class BaseAuth {
   Future<String>signInWithEmailAndPassword(String email, String password);
   Future<String>createUserWithEmailAndPassword(String email, String password);
   Future<String>currentUser();
   Future<void>signOut();
}
class Auth implements BaseAuth {
   Future<String>signInWithEmailAndPassword(
      String email, String password) async {
      FirebaseUser user =awaitFirebaseAuth.instance
      .signInWithEmailAndPassword(email: email, password: password);
   return user.uid;
   }

   Future<String>createUserWithEmailAndPassword(
      String email, String password) async {
      FirebaseUser user =awaitFirebaseAuth.instance
      .createUserWithEmailAndPassword(email: email, password: password);
      return user.uid;
  }

   Future<String>currentUser() async {
      FirebaseUser user =awaitFirebaseAuth.instance.currentUser();
      return user.uid;
   }

   Future<void>signOut() async {
      returnFirebaseAuth.instance.signOut();
   }
}

Now we create root page which will host our authentication state. Create new file called root_page.dart and copy this code into it:

import 'package:flutter/material.dart';
import 'screens/login_page.dart';
import 'auth.dart';
import 'home_page.dart';

class RootPage extends StatefulWidget {

   finalBaseAuth auth;
   RootPage({this.auth});

   @override
   State<StatefulWidget>createState() =>RootPageState();
}

enum AuthStatus { notSignedIn, signedIn }

class RootPageState extends State<RootPage> {

   AuthStatus _authStatus =AuthStatus.notSignedIn;

   @override
   voidinitState() {
      super.initState();
      widget.auth.currentUser().then((userId) {
         setState(() {
            authStatus = userId == null ? AuthStatus.signedIn : AuthStatus.signedIn;
         });
      });
   }

   void_signedIn() {
      setState(() {
         authStatus = AuthStatus.signedIn;
      });
   }

   void_signedOut() {
      setState(() {
         authStatus = AuthStatus.notSignedIn;
      });
   }

   @override
   Widgetbuild(BuildContext context) {
      switch (_authStatus) {
         caseAuthStatus.notSignedIn:
            return newLoginPage(
               auth: widget.auth,
               onSignedIn: _signedIn,
            );
         caseAuthStatus.signedIn:
              return newHomePage(
              auth: widget.auth,
              onSignedOut: _signedOut,
            );
      }

      return newLoginPage(auth: widget.auth);

   }
}

Now we create a starting page which will be visible to user. Create file called home_page.dart and copy this into it:

import 'package:flutter/material.dart';
import 'auth.dart';

class HomePage extends StatelessWidget {

   HomePage({this.auth, this.onSignedOut});
   finalBaseAuth auth;
   finalVoidCallback onSignedOut;

   void_signOut() async {
      try {
          await auth.signOut();
          onSignedOut();
      } catch (e) {}
    }

   @override
      Widgetbuild(BuildContext context) {
         returnScaffold(
            appBar: AppBar(
               title: Text("Welcome"),
               actions: <Widget>[
                   newFlatButton(
                      child: Text("Log out",
                      style: TextStyle(
                      fontSize: 17.0,
                      color: Colors.white,
                   )),
                   onPressed: _signOut,
                  )
               ],
            ),
           body: Container(
           child: Text("Welcome"),
           ),
         ),
       );
   }
}

Now, in your lib folder, make a new folder called ‘screens’ and inside of it make a new file called login_page.dart.
Inside of login_page.dart, copy and paste this code:

import 'package:flutter/material.dart';
import 'package:firebase_auth/firebase_auth.dart';
import '../auth.dart';

class LoginPage extends StatefulWidget {

   LoginPage({this.auth, this.onSignedIn});
   finalBaseAuth auth;
   finalVoidCallback onSignedIn;

   @override
   State<StatefulWidget>createState() {
      // TODO: implement createState
      return new_LoginPageState();
   }
}

enum FormType { login, register }
   class _LoginPageState extends State<LoginPage> {

      final formKey =newGlobalKey<FormState>();
      String _email;
      String _password;
      FormType _formType =FormType.login;

      boolvalidateAndSave() {

         final form = formKey.currentState;

         if (form.validate()) {
            form.save();
            returntrue;
         }

         returnfalse;
     }

    voidvalidateAndSubmit() async {

       if (validateAndSave()) {
          try {
              if (_formType ==FormType.login) {
                 String userId = await widget.auth.signInWithEmailAndPassword(_email, _password);
                 print("signed in: $userId");
              } else {
                 String userId =await widget.auth.createUserWithEmailAndPassword(_email, _password);
                 print("Registered user: $userId");
              }
               widget.onSignedIn;
          } catch (e) {
               print("error: $e");
          }
        }
      }

      voidmoveToRegister() {
         formKey.currentState.reset();
         setState(() {
            formType = FormType.register;
         });
      }

      voidmoveToLogin() {
         formKey.currentState.reset();
         setState(() {
             _formType = FormType.login;
         });
       }

      @override
      Widgetbuild(BuildContext context) {
          returnScaffold(
              appBar: new AppBar(
              title: Text("Flutter login demo"),
              ),
              body: new Container(
                 padding: EdgeInsets.all(16.0),
                 child: new Form(
                 key: formKey,
                 child: Column(
                     crossAxisAlignment: CrossAxisAlignment.stretch,
                     children: _buildInputs() + _buildSubmitButtons(),
                 ),
              )),
           );
      }

      List<Widget>_buildInputs() {
         return [
             newTextFormField(
                 decoration: InputDecoration(labelText: "Email"),
                 validator: (value) =>
                 value.isEmpty || !value.contains("@") ? "Incorrect email" : null,
                 onSaved: (value) => _email = value,
                 ),
            newTextFormField(
                decoration: InputDecoration(labelText: "Password"),
                obscureText: true,
                validator: (value) => value.length < 5 ? "Password too short" : null,
                onSaved: (value) => _password = value,
            ),
         ];
      }

      List<Widget>_buildSubmitButtons() {
          if (_formType ==FormType.login) {
              return [
                 RaisedButton(
                     child: Text("Login", style: TextStyle(fontSize: 20.0)),
                     onPressed: validateAndSubmit,
                     ),
                 newFlatButton(
                     child: Text("Create an account", style:newTextStyle(fontSize:20.0)),
                     onPressed: moveToRegister,
                     )
                 ];
            } else {
                 return [
                     RaisedButton(
                         child: Text("Register", style: TextStyle(fontSize: 20.0)),
                         onPressed: validateAndSubmit,
                     ),
                     newFlatButton(
                         child: Text("Already registered? Login",
                         style: new TextStyle(fontSize: 20.0)),
                         onPressed: moveToLogin,
                     )
                 ];
             }
      }
}

I won’t explain this code in detail, but I will encourage you to study it on your own. It is not complicated and you will learn a lot about fundamentals of Flutter.
Also, you have a fully working Login and Registration with Firebase and Flutter.

Thank you and bye!
Azem

Share with your friends

Related Posts

  • Migrating to Flutter

    If you guys are like me and you always want to keep step with latest…

  • How to add collapsing toolbar in Flutter

    Hello. There was this thing in Android called collapsing toolbar. In flutter it is called…

  • BUILD ANDROID APPLICATION USING FLUTTER AND WORDPRESS API PART 4

    This is part 4 of my tutorial series Build Android Application using Flutter and WordPress…

Tagged with: Firebase flutter Login Registration

Azem Zejnilovic

All posts

Android developer, coder, hacker and linux enthusiast. Love coding and testing new things. Please check my github profile to see what I'm working on now. GitHub

3Comments

Add yours
  1. 1
    Ana on April 30, 2019 at April 30, 2019
    Reply

    Hi, thanks a lot four share this post, It´s very helpfully for me.
    I got some questions for you about the first declared class MyApp, you import some packages that are not used:
    import ‘dart:convert’;
    import ‘dart:async’;
    import ‘dart:math’;
    Why do you import these packages?

    • 2
      Azem Zejnilovic on July 21, 2020 at July 21, 2020
      Reply

      I often use same project for demonstration purposes, so sometimes I don’t bother leaving some packages that I used in previous tutorials.
      Cheers

  2. 3
    Omer on January 10, 2020 at January 10, 2020
    Reply

    Thank you helped me a lot

Leave a Reply Cancel reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.

GoodFirms Badge

Please support us and our work by donating.

 

Virtuooza donation

$
Select Payment Method
Personal Info

Billing Details

Donation Total: $5.00

Subscribe to Virtuooza via Email

Enter your email address to subscribe to virtuooza development blog and receive notifications of new posts by email.

Tags

android (19) angular (3) animation (3) api (5) app (3) application (7) compressor (3) css (6) design (9) designer (6) designers (7) development (2) editor (4) error (3) fix (3) flutter (9) fonts (3) framework (6) free (13) gimp (3) google (8) how to (4) html (3) html5 (4) icons (3) image (9) inkscape (3) javascript (6) kotlin (3) linux (6) open source (3) photo (2) png (3) quote (3) templates (3) theme (4) tool (7) tools (3) tutorial (6) vector (3) virtuooza (5) web (3) website (3) windows (3) wordpress (7)

Popular

  • GridLayout with CardView 20.9k views
  • Update and delete items from Room database 16.3k views
  • How to get JSON object via API call using Retrofit 11.3k views
  • How to set daily notification. Shows up even after phone is turned off 9.2k views
  • Add data to SQLite Room, fetch it and display it into RecyclerView 7.9k views
  • Build Android application using Flutter and WordPress API 7.4k views
  • Flutter: Login and registration with Firebase 6.3k views
  • How to fix JavaScript heap out of memory in Angular project 5.8k views
  • How to use Feather Icons in your Angular app ? 4.7k views
  • Api Client using Retrofit, RXJava and Kotlin 4.1k views

Recent Comments

  • Azem Zejnilovic on Migrating to Flutter
  • Azem Zejnilovic on Flutter: Login and registration with Firebase
  • Omer on Flutter: Login and registration with Firebase
  • Anes Prentic on How to fix JavaScript heap out of memory in Angular project
  • Anshul on Build Android application using Flutter and WordPress API
  • Kunal Das on BUILD ANDROID APPLICATION USING FLUTTER AND WORDPRESS API PART 4
  • Ana on Flutter: Login and registration with Firebase
  • Francisco on Build Android Application using Flutter and WordPress API Part 2
  • ala on Api Client using Retrofit, RXJava and Kotlin
  • Samir Kahvedzic on Build Android Application using Flutter and WordPress API Part 2
© 2018 Virtuooza Development Blog | Become our friend Contact us.

Begin typing your search above and press return to search. Press Esc to cancel.

Patch