Floating action button aka FAB is a staple of apps using material design. What if you need the user to choose from multiple different actions? Well, you have to use a floating action menu which is basically a FAB which upon click displays multiple smaller FABs.
There are two ways in which we can add a floating action menu. Using a 3rd party library is one option, but that is not always ideal because libraries can get outdated. Much more viable option is to code it ourselves and use the latest and greatest things from the design support library made by Google which guarantees we will always be able to use bleeding edge features.
This post contains all the code that’s been written in this YouTube video.
You can also check out this GitHub repository: https://github.com/ResoCoder/FabMenuXamarinAndroid
MainActivity.cs
using Android.App;
using Android.Widget;
using Android.OS;
using Android.Support.V7.App;
using Android.Support.Design.Widget;
using Android.Views;
using System;
using Android.Animation;
namespace FabMenuTut
{
[Activity(Label = "FabMenuTut", MainLauncher = true)]
public class MainActivity : AppCompatActivity
{
private static bool isFabOpen;
private FloatingActionButton fabAirballoon;
private FloatingActionButton fabCake;
private FloatingActionButton fabMain;
private View bgFabMenu;
protected override void OnCreate(Bundle savedInstanceState)
{
base.OnCreate(savedInstanceState);
// Set our view from the "main" layout resource
SetContentView(Resource.Layout.Main);
fabAirballoon = FindViewById<FloatingActionButton>(Resource.Id.fab_airballoon);
fabCake = FindViewById<FloatingActionButton>(Resource.Id.fab_cake);
fabMain = FindViewById<FloatingActionButton>(Resource.Id.fab_main);
bgFabMenu = FindViewById<View>(Resource.Id.bg_fab_menu);
fabMain.Click += (o, e) =>
{
if (!isFabOpen)
ShowFabMenu();
else
CloseFabMenu();
};
fabCake.Click += (o, e) =>
{
CloseFabMenu();
Toast.MakeText(this, "Cake!", ToastLength.Short).Show();
};
fabAirballoon.Click += (o, e) =>
{
CloseFabMenu();
Toast.MakeText(this, "Airballoon!", ToastLength.Short).Show();
};
bgFabMenu.Click += (o, e) => CloseFabMenu();
}
private void ShowFabMenu()
{
isFabOpen = true;
fabAirballoon.Visibility = ViewStates.Visible;
fabCake.Visibility = ViewStates.Visible;
bgFabMenu.Visibility = ViewStates.Visible;
fabMain.Animate().Rotation(135f);
bgFabMenu.Animate().Alpha(1f);
fabAirballoon.Animate()
.TranslationY(-Resources.GetDimension(Resource.Dimension.standard_100))
.Rotation(0f);
fabCake.Animate()
.TranslationY(-Resources.GetDimension(Resource.Dimension.standard_55))
.Rotation(0f);
}
private void CloseFabMenu()
{
isFabOpen = false;
fabMain.Animate().Rotation(0f);
bgFabMenu.Animate().Alpha(0f);
fabAirballoon.Animate()
.TranslationY(0f)
.Rotation(90f);
fabCake.Animate()
.TranslationY(0f)
.Rotation(90f).SetListener(new FabAnimatorListener(bgFabMenu, fabCake, fabAirballoon));
}
private class FabAnimatorListener : Java.Lang.Object, Animator.IAnimatorListener
{
View[] viewsToHide;
public FabAnimatorListener(params View[] viewsToHide)
{
this.viewsToHide = viewsToHide;
}
public void OnAnimationCancel(Animator animation)
{
}
public void OnAnimationEnd(Animator animation)
{
if (!isFabOpen)
foreach (var view in viewsToHide)
view.Visibility = ViewStates.Gone;
}
public void OnAnimationRepeat(Animator animation)
{
}
public void OnAnimationStart(Animator animation)
{
}
}
}
}
Main.axml
<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Hello FAB menu!"
android:textSize="24sp"/>
<View
android:id="@+id/bg_fab_menu"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#48000000"
android:alpha="0"
android:visibility="gone"/>
<android.support.design.widget.FloatingActionButton
android:id="@+id/fab_airballoon"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="bottom|end"
android:layout_margin="@dimen/standard_23"
android:visibility="gone"
android:rotation="90"
app:fabSize="mini"
app:srcCompat="@drawable/ic_airballoon"/>
<android.support.design.widget.FloatingActionButton
android:id="@+id/fab_cake"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="bottom|end"
android:layout_margin="@dimen/standard_23"
android:visibility="gone"
android:rotation="90"
app:fabSize="mini"
app:srcCompat="@drawable/ic_cake"/>
<android.support.design.widget.FloatingActionButton
android:id="@+id/fab_main"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="bottom|end"
android:layout_margin="@dimen/fab_margin"
app:fabSize="normal"
app:srcCompat="@drawable/ic_plus"/>
</android.support.design.widget.CoordinatorLayout>
dimens.xml
<resources> <dimen name="fab_margin">16dp</dimen> <dimen name="standard_12">12dp</dimen> <dimen name="standard_23">23dp</dimen> <dimen name="standard_55">55dp</dimen> <dimen name="standard_100">100dp</dimen> <dimen name="standard_145">145dp</dimen> </resources>
AndroidManifest.xml
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="FabMenuTut.FabMenuTut"
android:versionCode="1"
android:versionName="1.0">
<uses-sdk android:minSdkVersion="21" />
<application android:allowBackup="true"
android:label="@string/app_name"
android:theme="@style/Theme.AppCompat.Light.DarkActionBar">
</application>
</manifest>


thanks 🙂
Your point of view caught my eye and was very interesting. Thanks. I have a question for you.
Can you be more specific about the content of your article? After reading it, I still have some doubts. Hope you can help me.
I don’t think the title of your article matches the content lol. Just kidding, mainly because I had some doubts after reading the article.
Thanks for sharing. I read many of your blog posts, cool, your blog is very good.
Thank you for your sharing. I am worried that I lack creative ideas. It is your article that makes me full of hope. Thank you. But, I have a question, can you help me?
Thank you for your sharing. I am worried that I lack creative ideas. It is your article that makes me full of hope. Thank you. But, I have a question, can you help me? https://www.binance.com/register?ref=GGYHGRE