How to Work With Progress Indicator In Flutter

How to Work With Progress Indicator In Flutter ?

CircularProgressIndicator Widget is a widget that displays the progress in a circular shape. So in this article How to Work With Progress Indicator In Flutter? In this blog, we delve into the world of progress indicators in Flutter and provide a step-by-step guide on how to effectively work with them in your Flutter applications. Whether you’re a beginner or an experienced Flutter developer, this tutorial covers everything you need to know to create sleek and interactive progress indicators that enhance the user experience of your apps. Discover various types of progress indicators, explore customization options, and learn how to handle different scenarios, such as loading data from APIs or displaying file uploads. Level up your Flutter skills with this in-depth exploration of progress indicators and take your app development to the next level.

Learn How to Work With Progress Indicator In Flutter?

There are a few ways to deal with Asynchronous actions.

A simple way to do this is by using a modal that will block the user input, thus preventing any unwanted actions. Consider a method like below:

void _onLoading() {
  showDialog(
    context: context,
    barrierDismissible: false,
    builder: (BuildContext context) {
      return Dialog(
        child: new Row(
          mainAxisSize: MainAxisSize.min,
          children: [
            new CircularProgressIndicator(),
            new Text("Loading"),
          ],
        ),
      );
    },
  );
  new Future.delayed(new Duration(seconds: 3), () {
    Navigator.pop(context); //pop dialog
    _login();
  });
}

The most ideal way to do it is using FutureBuilder and a stateful widget. Which is what you started. The trick is that, instead of having a boolean loading = false in your state, you can directly use a Future<MyUser>, user

And then pass it as an argument to FutureBuilder, which will give you some info such as “hasData” or the instance of MyUser when completed.

Consider the below code snippet.

@immutable
class MyUser {
  final String name;

  MyUser(this.name);
}

class MyApp extends StatelessWidget {
  // This widget is the root of your application.
  @override
  Widget build(BuildContext context) {
    return new MaterialApp(
      title: 'Flutter Demo',
      home: new MyHomePage(title: 'Flutter Demo Home Page'),
    );
  }
}

class MyHomePage extends StatefulWidget {
  MyHomePage({Key key, this.title}) : super(key: key);

  final String title;

  @override
  _MyHomePageState createState() => new _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  Future<MyUser> user;

  void _logIn() {
    setState(() {
      user = new Future.delayed(const Duration(seconds: 3), () {
        return new MyUser("Toto");
      });
    });
  }

  Widget _buildForm(AsyncSnapshot<MyUser> snapshot) {
    var floatBtn = new ElevatedButton(
     onPressed:
         snapshot.connectionState == ConnectionState.none ? _logIn : null,
     child: new Icon(Icons.save),
   );
    var action =
        snapshot.connectionState != ConnectionState.none && !snapshot.hasData
            ? new Stack(
                alignment: FractionalOffset.center,
                children: <Widget>[
                  floatBtn,
                  new CircularProgressIndicator(
                    backgroundColor: Colors.red,
                  ),
                ],
              )
            : floatBtn;

    return new ListView(
      padding: const EdgeInsets.all(15.0),
        children: <Widget>[
          new ListTile(
            title: new TextField(),
          ),
          new ListTile(
            title: new TextField(obscureText: true),
          ),
          new Center(child: action)
        ],
    );
  }

  @override
  Widget build(BuildContext context) {
    return new FutureBuilder(
      future: user,
      builder: (context, AsyncSnapshot<MyUser> snapshot) {
        if (snapshot.hasData) {
          return new Scaffold(
            appBar: new AppBar(
              title: new Text("Hello ${snapshot.data.name}"),
            ),
          );
        } else {
          return new Scaffold(
            appBar: new AppBar(
              title: new Text("Connection"),
            ),
            body: _buildForm(snapshot),
          );
        }
      },
    );
  }
}

Another way is to set CircularProgressIndicator in a SnackBar Widget.

Here is how to set up the SnackBar.

  • Define a global key for your Scaffold
    final GlobalKey<ScaffoldState> _scaffoldKey = new GlobalKey<ScaffoldState>();

    Add it to your Scaffold key attribute

    return new Scaffold(
          key: _scaffoldKey,
    .......

    On a Button Press CallBack

    onPressed: () {
                      _scaffoldKey.currentState.showSnackBar(
                          new SnackBar(duration: new Duration(seconds: 4), content:
                          new Row(
                            children: <Widget>[
                              new CircularProgressIndicator(),
                              new Text("  Signing-In...")
                            ],
                          ),
                          ));
                      _handleSignIn()
                          .whenComplete(() =>
                          Navigator.of(context).pushNamed("/Home")
                      );
                    }
    CircularProgressIndicator
    CircularProgressIndicator

    Without Plugin

        class IndiSampleState extends State<ProgHudPage> {
      @override
      Widget build(BuildContext context) {
        return new Scaffold(
            appBar: new AppBar(
              title: new Text('Demo'),
            ),
            body: Center(
             child: ElevatedButton(
               color: Colors.blueAccent,
               child: Text('Login'),
               onPressed: () async {
                 showDialog(
                     context: context,
                     builder: (BuildContext context) {
                       return Center(child: CircularProgressIndicator(),);
                     });
                 await loginAction();
                 Navigator.pop(context);
               },
             ),
           ));
      }
    
      Future<bool> loginAction() async {
        //replace the below line of code with your login request
        await new Future.delayed(const Duration(seconds: 2));
        return true;
      }
    }

    With Plugin

  • Check this plugin progress_hud 
  • Add the dependency in the pubspec.yaml file
    dev_dependencies:
      progress_hud:

    Import the package

    import 'package:progress_hud/progress_hud.dart';

    Code Snippet will look like below:

    class ProgHudPage extends StatefulWidget {
      @override
      _ProgHudPageState createState() => _ProgHudPageState();
    }
    
    class _ProgHudPageState extends State<ProgHudPage> {
      ProgressHUD _progressHUD;
      @override
      void initState() {
        _progressHUD = new ProgressHUD(
          backgroundColor: Colors.black12,
          color: Colors.white,
          containerColor: Colors.blue,
          borderRadius: 5.0,
          loading: false,
          text: 'Loading...',
        );
        super.initState();
      }
    
      @override
      Widget build(BuildContext context) {
        return new Scaffold(
            appBar: new AppBar(
              title: new Text('ProgressHUD Demo'),
            ),
            body: new Stack(
             children: [
               _progressHUD,
               new Positioned(
                   child: ElevatedButton(
                     color: Colors.blueAccent,
                     child: Text('Login'),
                     onPressed: () async{
                       _progressHUD.state.show();
                       await loginAction();
                       _progressHUD.state.dismiss();
                     },
                   ),
                   bottom: 30.0,
                   right: 10.0)
             ],
           ));
      }
    
      Future<bool> loginAction()async{
        //replace the below line of code with your login request
        await new Future.delayed(const Duration(seconds: 2));
        return true;
      }
    }

    You can also try with the below methods.

  • Step 1: Create Dialog
    showAlertDialog(BuildContext context){
       AlertDialog alert=AlertDialog(
         content: new Row(
             children: [
                CircularProgressIndicator(),
                Container(margin: EdgeInsets.only(left: 5),child:Text("Loading" )),
             ],),
       );
       showDialog(barrierDismissible: false,
         context:context,
         builder:(BuildContext context){
           return alert;
         },
       );
     }
  • Step 2:Call it
    showAlertDialog(context);
    await firebaseAuth.signInWithEmailAndPassword(email: email, password: password);
    Navigator.pop(context);

    The example will look like below:

    import 'package:flutter/cupertino.dart';
    import 'package:flutter/material.dart';
    import 'package:firebase_auth/firebase_auth.dart';
    class DynamicLayout extends StatefulWidget{
      @override
      State<StatefulWidget> createState() {
        // TODO: implement createState
        return new MyWidget();
        }
      }
    showAlertDialog(BuildContext context){
      AlertDialog alert=AlertDialog(
        content: new Row(
            children: [
               CircularProgressIndicator(),
               Container(margin: EdgeInsets.only(left: 5),child:Text("Loading" )),
            ],),
      );
      showDialog(barrierDismissible: false,
        context:context,
        builder:(BuildContext context){
          return alert;
        },
      );
    }
    
      class MyWidget extends State<DynamicLayout>{
      Color color = Colors.indigoAccent;
      String title='app';
      GlobalKey<FormState> globalKey=GlobalKey<FormState>();
      String email,password;
      login() async{
       var currentState= globalKey.currentState;
       if(currentState.validate()){
            currentState.save();
            FirebaseAuth firebaseAuth=FirebaseAuth.instance;
            try {
              showAlertDialog(context);
              AuthResult authResult=await firebaseAuth.signInWithEmailAndPassword(
                  email: email, password: password);
              FirebaseUser user=authResult.user;
              Navigator.pop(context);
            }catch(e){
              print(e);
            }
       }else{
    
       }
      }
      @override
      Widget build(BuildContext context) {
        return new Scaffold(
            appBar:AppBar(
            title: Text("$title"),
            ) ,
              body: Container(child: Form(
                key: globalKey,
                child: Container(
                  padding: EdgeInsets.all(10),
                  child: Column(children: <Widget>[
                  TextFormField(decoration: InputDecoration(icon: Icon(Icons.email),labelText: 'Email'),
                  // ignore: missing_return
                  validator:(val){
                    if(val.isEmpty)
                      return 'Please Enter Your Email';
                  },
                  onSaved:(val){
                    email=val;
                  },
                  ),
                    TextFormField(decoration: InputDecoration(icon: Icon(Icons.lock),labelText: 'Password'),
                 obscureText: true,
                      // ignore: missing_return
                      validator:(val){
                        if(val.isEmpty)
                          return 'Please Enter Your Password';
                      },
                      onSaved:(val){
                        password=val;
                      },
                  ),
                    RaisedButton(color: Colors.lightBlue,textColor: Colors.white,child: Text('Login'),
                      onPressed:login),
                ],)
                  ,),)
             ),
        );
      }
    }
    

    We will get output like below:

    CircularProgressIndicator in a Modal
    CircularProgressIndicator in a Modal

Conclusion:

In this article, We have learned about How to Work With Progress Indicator In Flutter?

Thanks for being with us on a Flutter Journey.

Thanks for Reading!!!

Do let us know if you need any assistance with Flutter Development?

FlutterAgency.com is our portal Platform dedicated to Flutter Technology and Flutter Developers. The portal is full of cool resources from Flutter like Flutter Widget GuideFlutter ProjectsCode libs and etc.

FlutterAgency.com is one of the most popular online portal dedicated to Flutter Technology and daily thousands of unique visitors come to this portal to enhance their knowledge on Flutter.

Nirali Patel

Written by Nirali Patel

Nirali Patel is a dedicated Flutter developer with over two years of experience, specializing in creating seamless mobile applications using Dart. With a passion for crafting user-centric solutions, Nirali combines technical proficiency with innovative thinking to push the boundaries of mobile app development.

Leave a comment

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

Discuss Your Project

Connect with Flutter Agency's proficient skilled team for your app development projects across different technologies. We'd love to hear from you! Fill out the form below to discuss your project.

Build Your Agile Team

Hire Skilled Developer From Us

"*" indicates required fields

✓ Valid number ✕ Invalid number

ready to get started?

Fill out the form below and we will be in touch soon!

"*" indicates required fields

✓ Valid number ✕ Invalid number