Android PopupMenu : Show floating menu anchored to a view

PopupMenu shows floating Menu in a popup window anchored to a view. PopupMenu was added with API level 11. PopupMenu itself decides its position on screen around anchor view based upon available space. If there is room below anchor view, it will show below it. Otherwise it will be shown above anchor view.

PopupMenu provides two interfaces to handler dismiss and item click.

1. PopupMenu.OnDismissListener
Callback interface used to notify the application that popup menu has been closed.

2. PopupMenu.OnMenuItemClickListener
Interface responsible for receiving menu item click events if the items themselves do not have individual item click listeners.

Sample PopupMenu Application

PopupMenu_Bottom PopupMenu_Top

Our main target is to achieve above output. Activity layout will have two buttons one each aligned to top and bottom of view. PopupMenu will be shown on clicking buttons. In screenshot, PopupMenu is shown above it for anchor view in bottom and it is shown below anchor view for top aligned button.

Second target is to acheive styling of PopupMenu. We will define style for text appearance and background of PopupMenu as by deafult it will have style inherited from android:Widget.Holo.Light.ListPopupWindow.

Let’s start making changes with /res/layout/activity_main.xml. Final xml will be similar to as below.

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:paddingBottom="@dimen/activity_vertical_margin"
    android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    tools:context="com.andoidsrc.popupmenu.MainActivity" >

    <Button
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentTop="true"
        android:layout_centerHorizontal="true"
        android:onClick="onClick"
        android:text="Click to show PopupMenu" />

    <Button
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentBottom="true"
        android:layout_centerHorizontal="true"
        android:onClick="onClick"
        android:text="Click to show PopupMenu" />

</RelativeLayout>

We need to create a menu layout to be inflated in PopupMenu. Create /res/menu/popup_menu.xml as below.

<menu xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    tools:context="com.andoidsrc.popupmenu.MainActivity" >

    <item
        android:id="@+id/lang_java"
        android:showAsAction="ifRoom|withText"
        android:title="Java"
        android:visible="true"/>
    <item
        android:id="@+id/lang_android"
        android:showAsAction="ifRoom|withText"
        android:title="Android"
        android:visible="true"/>
    <item
        android:id="@+id/lang_ruby"
        android:showAsAction="ifRoom|withText"
        android:title="Ruby"
        android:visible="true"/>
    <item
        android:id="@+id/lang_python"
        android:showAsAction="ifRoom|withText"
        android:title="Python"
        android:visible="true"/>
</menu>

For styling PopupMenu,add below lines to /res/values/styles.xml. It is assumed that Application theme is set to android:theme="@style/AppTheme" in manifest file.

    <!-- Application theme. -->
    <style name="AppTheme" parent="AppBaseTheme">
        <!-- All customizations that are NOT specific to a particular API-level can go here. -->
        <item name="android:popupMenuStyle">@style/AndroidSRC.PopupMenu</item>
        <item name="android:itemTextAppearance">@style/AndroidSRC.TextAppearance</item>
    </style>

    <style name="AndroidSRC.PopupMenu" parent="android:Widget.Holo.Light.ListPopupWindow">
        <item name="android:popupBackground">#21B6A8</item>
    </style>

    <style name="AndroidSRC.TextAppearance" parent="@android:style/Widget.Holo.Light.TextView">
        <item name="android:textColor">@android:color/white</item>
        <item name="android:textStyle">bold</item>
    </style>

Finally, Let add code for PopupMenu in MainActivity.java. Activity will implement View.OnClickListener for listening to onClick events for buttons. In onClick(), We will create a PopupMenu object. View will be set with inflate(int resourceId). Attach OnDismissListener and OnMenuItemClickListener in order to listen for menu dismiss and handling for menu click events.

package com.andoidsrc.popupmenu;

import android.app.Activity;
import android.os.Bundle;
import android.view.MenuItem;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.PopupMenu;
import android.widget.Toast;

public class MainActivity extends Activity implements OnClickListener {

    private PopupMenu popupMenu;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    }

    @Override
    public void onClick(View anchor) {
        // TODO Auto-generated method stub
        popupMenu = new PopupMenu(MainActivity.this, anchor);
        popupMenu.setOnDismissListener(new OnDismissListener());
        popupMenu.setOnMenuItemClickListener(new OnMenuItemClickListener());
        popupMenu.inflate(R.menu.popup_menu);
        popupMenu.show();
    }

    private class OnDismissListener implements PopupMenu.OnDismissListener {

        @Override
        public void onDismiss(PopupMenu menu) {
            // TODO Auto-generated method stub
            Toast.makeText(getApplicationContext(), "Popup Menu is dismissed",
                    Toast.LENGTH_SHORT).show();
        }

    }

    private class OnMenuItemClickListener implements
            PopupMenu.OnMenuItemClickListener {

        @Override
        public boolean onMenuItemClick(MenuItem item) {
            // TODO Auto-generated method stub
            switch (item.getItemId()) {
                case R.id.lang_java:
                    Toast.makeText(getApplicationContext(), "Java got clicked",
                            Toast.LENGTH_SHORT).show();
                    return true;
                case R.id.lang_android:
                    Toast.makeText(getApplicationContext(), "Android got clicked",
                            Toast.LENGTH_SHORT).show();
                    return true;
                case R.id.lang_python:
                    Toast.makeText(getApplicationContext(), "Python got clicked",
                            Toast.LENGTH_SHORT).show();
                    return true;
                case R.id.lang_ruby:
                    Toast.makeText(getApplicationContext(), "Ruby got clicked",
                            Toast.LENGTH_SHORT).show();
                    return true;

            }
            return false;
        }
    }
}

You may also like...

5 Responses

  1. Popup Menu in android studio
    if you are beginner and do not know how to create a popup menu in android this lecture can help you a lot
    http://themasterworld.com/popup-menu-in-android-studio/

  2. Michael Lee says:

    Can I set the content of the popup menu without the popup_menu.xml but in the codes? How should I do? Thx!

  3. prem suman says:

    Hey there, Ive tried this tutorial, and the popup menu is appearing with the rows, but the text is not showing there.

Leave a Reply

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