Create a loading button using Flutter

In this article, I am going to show two ways to create a progress button in Flutter. The first one is to change the button shape to loading animation and the second one is to change the button content to loading animation.

Alon Barad
2 min readApr 17, 2020

In both examples, I used the flutter_spinkit Dart package for the loading animation.

First way

Change the button shape to loading animation.

Fully animated button

To create a button that changes its own shape you can use Dart package called flutter_progress_button. All the information you need is in the docs.

And here is a simple code snippet:

import 'package:flutter/material.dart';
import 'package:flutter_progress_button/flutter_progress_button.dart';
import 'package:flutter_spinkit/flutter_spinkit.dart';
void main() => runApp(MyApp());class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
home: Container(
color: Colors.white,
padding: EdgeInsets.all(100.0),
child: Center(
child: ProgressButton(
borderRadius: 5.0,
color: Colors.blue,
height: 50.0,
onPressed: () async {
await Future.delayed(Duration(milliseconds: 1000));
},
progressWidget: SpinKitFadingCircle(
color: Colors.white,
size: 30,
),
defaultWidget: Text(
'Click here',
style: TextStyle(
color: Colors.white,
fontSize: 20.0,
),
),
),
),
),
);
}
}

Second way

Change the button content to loading animation.

Inner animated button

All we need to do is create a StatefulWidget and an _isLoading bool variable. Now, when our button is clicked, we change the _isLoading variable to true, execute our long function and then change it back to false.

In our widget tree, we create a condition that returns different button content according to our _isLoading variable.

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

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

class MyApp extends StatefulWidget {
@override
_MyAppState createState() => _MyAppState();
}

class _MyAppState extends State<MyApp> {
bool _isLoading = false;
@override
Widget build(BuildContext context) {
return MaterialApp(
home: Container(
color: Colors.white,
child: Center(
child: ButtonTheme(
height: 50.0,
minWidth: 200.0,
child: RaisedButton(
child: _isLoading
? Container(
height: 50.0,
width: 150,
child: SpinKitWave(
color: Colors.white,
size: 20.0,
),
)
: Text(
'Click here',
style: TextStyle(
color: Colors.white,
fontSize: 20.0,
),
),
onPressed: () async {
setState(() => _isLoading = true);
await Future.delayed(Duration(milliseconds: 1000));
setState(() => _isLoading = false);
},
),
),
),
),
);
}
}

This was my first Medium article :)

Hope I could help.

--

--