This is the second part of my tutorial about BottomAppBar and FAB (part one is here). Today we will see how to reveal options when the FAB if pressed.

We will see how to add overlays in Flutter, and why this is a valuable technique that you can add to your toolbox.

Revealing buttons when FAB is pressed

In this tutorial we will add the code to enable the following animation:

The animation itself was originally taken from this example on StackOverflow.

I have bundled the example code into FabWithIcons , a new custom widget that we can assign directly to our Scaffold.floatingActionButton :

How does this work?

Line 4: We define FabWithIcons as a StatefulWidget as it needs an AnimationController to manage the animation state.

We define as a as it needs an to manage the animation state. Lines 5 to 7 : We pass a list of icons and a callback for when an icon is tapped. This is of type ValueChanged<int> so that we can specify the index of the icon that was tapped.

: We pass a list of icons and a callback for when an icon is tapped. This is of type so that we can specify the index of the icon that was tapped. Lines 12 to 22 : We add a TickerProviderStateMixin to our state class, and initialise an AnimationController , passing this to the vsync parameter. For a good overview of the animation APIs see this article about Flutter animations by Sergi & Replace.

: We add a to our state class, and initialise an , passing to the parameter. For a good overview of the animation APIs see this article about Flutter animations by Sergi & Replace. Lines 25 to 35 : In our build method, we generate a list of icons, and append a FloatingActionButton as the last element.

: In our method, we generate a list of icons, and append a as the last element. Lines 37 to 61 : We define a small ( mini: true ) FloatingActionButton for the item at a given index, and link a ScaleTransition widget to our animation controller. This is what makes the FABs animate in and out.

: We define a small ( ) for the item at a given index, and link a widget to our animation controller. This is what makes the FABs animate in and out. Lines 63 to 76 : We create the main FAB, and use the onPressed handler to update our animation controller as needed.

: We create the main FAB, and use the handler to update our animation controller as needed. Lines 78 to 81: When an option is selected, we hide all the icons (via _controller.reverse() ), and notify the parent that an item has been selected.

Let’s try to use this.

In our main page, we add this method to create a FAB with three icons:

Then, we can call it like so inside our Scaffold :

floatingActionButton: _buildFab(context)

If we run the app, we see that this does not look right. However, if we comment out the floatingActionButtonLocation line in our Scaffold , the FAB moves to the default location and no longer interferes with our BottomAppBar .

Left: custom FAB with centerDocked position. Right: default “floating” position with icons.

What is going on here?

Well, our FABWithIcons is taller than a normal FAB because it has additional icons. Trying to fit this as a docked item in a BottomAppBar does not work well. I suspect the Flutter SDK tries to compensate for the extra height by pushing the FAB all the way to the bottom, but this results in a visual artifact.

What to do?

Enter Overlays

What if we could use a standard FAB as a single widget in our BottomAppBar , but switch to a completely separate layer when we need to show the extra icons?

Flutter offers a widget called Overlay which is great for this scenario. From the documentation of the Overlay class:

A Stack of entries that can be managed independently. Overlays let independent child widgets “float” visual elements on top of other widgets by inserting them into the overlay’s Stack. The overlay lets each of these widgets manage their participation in the overlay using OverlayEntry objects.

This sounds like what we need. But how do we use it?

The SDK documentation reveals that we need to create an OverlayEntry object so that we can hold our custom FABWithIcons . We can do this by defining this method:

However, this is some imperative code, while our application UI is defined declaratively. How do we reconcile the two?

It turns out that getting overlays to work requires quite a bit of work, and implementing them correctly is not straightforward.

Luckily, Matt Carroll has already explored this issue in his Fluttery video about Feature Discovery, and created some useful layout helper widgets.

For the purposes of our tutorial, we are going to borrow and use some of his code. Here is the entire Overlay layout code:

Matt explains this code in great detail on his video.

Here, I just show how to use it for our purposes.

Bottom line: we can update our _buildFab method as follows:

This code uses AnchoredOverlay to build a separate overlay for our FabWithIcons widget. CenterAbout is used to position our overlay relative to the location of the FAB. To position our FabWithIcons correctly, we offset it by the number of icons, times the size of each icon (35 pt).

Note: On line 4, we pass showOverlay: true . This is so that the FAB in the overlay is always visible and stacked exactly above the main FAB in the BottomAppBar . This is ok because the original FAB and the one inside FABWithIcons look identical when the icons are hidden.

If you use AnchoredOverlay to build your own UIs, you could hold a state variable for the showOverlay parameter, and toggle this as needed.

That’s it

We have seen how to show our custom UI with animations as an overlay, so that we can dock our custom FAB inside a BottomAppBar without problems.

With the layout helpers provided, adding overlays to your app becomes very easy:

Move all your overlay UI code into a custom widget class. Wrap your desired widget inside an AnchoredOverlay . Use CenterAbout to position your overlay relative to the original widget.

I open sourced my full example here on GitHub. 🙏

Feel free to reuse it in your projects. 😎

Happy coding!

UPDATE: My Flutter & Firebase Udemy course is now available for Early Access. Use this link to enroll (discount code included):

For more articles and video tutorials, check out Code With Andrea.

I’m @biz84 on Twitter. You can also see my GitHub page. Did you like this article? Then smash that clap 👏 button! It makes me feel awesome so I can write more about Flutter. 😎