Saturday, January 30, 2016

android - Add, update and remove Menu item programmatically

activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:id="@+id/rl"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:padding="0dp"
    tools:context=".MainActivity"
    android:background="#cfc883"
    >
    <android.support.v7.widget.Toolbar
        android:id="@+id/toolbar"
        android:layout_width="match_parent"
        android:layout_height="?attr/actionBarSize"
        android:background="?attr/colorPrimary"
        android:elevation="4dp"
        android:theme="@style/ThemeOverlay.AppCompat.ActionBar"
        app:popupTheme="@style/ThemeOverlay.AppCompat.Light"
        />
    <TextView
        android:id="@+id/tv"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerInParent="true"
        android:text="Change This Text Color\nUsing Toolbar Menu"
        android:textSize="50dp"
        android:gravity="center"
        android:textStyle="bold"
        android:fontFamily="sans-serif-condensed"
        />
</RelativeLayout>
res/menu/toolbar_options_menu.xml

<?xml version="1.0" encoding="utf-8"?>
<menu
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    >
    <item
        android:id="@+id/red"
        android:title="Red"
        android:icon="@drawable/ic_palette_red_36dp"
        app:showAsAction="always|withText"
        android:orderInCategory="1"
        />
    <item
        android:id="@+id/green"
        android:title="Green"
        android:icon="@drawable/ic_palette_green_36dp"
        app:showAsAction="always|withText"
        android:orderInCategory="2"
        />
    <item
        android:id="@+id/blue"
        android:title="Blue"
        android:icon="@drawable/ic_palette_blue_36dp"
        app:showAsAction="ifRoom|withText"
        android:orderInCategory="3"
        />
</menu>
MainActivity.java

package com.cfsuman.me.androidcodesnippets;

import android.app.Activity;
import android.content.Context;
import android.graphics.Color;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.widget.RelativeLayout;
import android.widget.TextView;
import android.support.v7.widget.Toolbar;
import android.widget.Toast;


public class MainActivity extends AppCompatActivity {
    private Context mContext;
    private Activity mActivity;

    private RelativeLayout mRelativeLayout;
    private TextView mTextView;
    private Toolbar mToolbar;


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

        // Get the application context
        mContext = getApplicationContext();

        // Get the activity
        mActivity = MainActivity.this;

        // Get the widgets reference from XML layout
        mRelativeLayout = (RelativeLayout) findViewById(R.id.rl);
        mTextView = (TextView) findViewById(R.id.tv);
        mToolbar = (Toolbar) findViewById(R.id.toolbar);

        // Set a title for toolbar
        mToolbar.setTitle("Add, Edit and Remove Menu Item");
        mToolbar.setTitleTextColor(Color.WHITE);

        // Set support actionbar with toolbar
        setSupportActionBar(mToolbar);

        // Change the toolbar background color
        mToolbar.setBackgroundColor(Color.parseColor("#FF68BFD1"));
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu){
        MenuInflater inflater = getMenuInflater();
        inflater.inflate(R.menu.toolbar_options_menu, menu);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item){
        switch(item.getItemId()){
            case R.id.red:
                // Set the text color to red
                mTextView.setTextColor(Color.RED);
                return true;
            case R.id.green:
                // Set the text color to green
                mTextView.setTextColor(Color.GREEN);
                return true;
            case R.id.blue:
                // Set the text color to blue
                mTextView.setTextColor(Color.BLUE);
                return true;
            default:
                return super.onOptionsItemSelected(item);
        }
    }

    /*
        public boolean onPrepareOptionsMenu (Menu menu)
            Prepare the Screen's standard options menu to be displayed. This is called right before
            the menu is shown, every time it is shown. You can use this method to efficiently
            enable/disable items or otherwise dynamically modify the contents.

            The default implementation updates the system menu items based on the activity's state.
            Deriving classes should always call through to the base class implementation.

        Parameters
            menu : The options menu as last shown or first initialized by onCreateOptionsMenu().
        Returns
            You must return true for the menu to be displayed; if you return false it will not be shown.
    */
    @Override
    public boolean onPrepareOptionsMenu(Menu menu){
        //------------------- Add new Menu Item ---------------------------------
        // Specify an id for the new menu item
        int purpleId = 101;

        // Check the menu item already added or not
        if(menu.findItem(purpleId) == null){
            /*
                public abstract MenuItem add (int groupId, int itemId, int order, CharSequence title)
                    Add a new item to the menu. This item displays the given title for its label.

                Parameters
                    groupId : The group identifier that this item should be part of. This can be
                              used to define groups of items for batch state changes. Normally
                              use NONE if an item should not be in a group.
                    itemId : Unique item ID. Use NONE if you do not need a unique ID.
                    order : The order for the item. Use NONE if you do not care about the order.
                    title : The text to display for the item.
                Returns
                    The newly added menu item.
            */
            /*
                public static final int NONE
                    Value to use for group and item identifier integers when you
                    don't care about them.

                Constant Value: 0 (0x00000000)
            */
            // If it not exists then add the menu item to menu
            MenuItem purple = menu.add(
                    Menu.NONE, // groupId
                    purpleId, // itemId
                    2, // order
                    "Purple" // title
            );

            /*
                public abstract MenuItem setIcon (int iconRes)
                    Change the icon associated with this item. This icon will not always be shown,
                    so the title should be sufficient in describing this item.

                    This method will set the resource ID of the icon which will be used to lazily
                    get the Drawable when this item is being shown.

                Parameters
                    iconRes : The new icon (as a resource ID) to be displayed.
                Returns
                    This Item so additional setters can be called.
            */
            // Set an icon for the new menu item
            purple.setIcon(R.drawable.ic_palette_purple_36dp);

            /*
                public abstract MenuItem setShowAsActionFlags (int actionEnum)
                    Sets how this item should display in the presence of an Action Bar. The
                    parameter actionEnum is a flag set. One of SHOW_AS_ACTION_ALWAYS,
                    SHOW_AS_ACTION_IF_ROOM, or SHOW_AS_ACTION_NEVER should be used, and you may
                    optionally OR the value with SHOW_AS_ACTION_WITH_TEXT. SHOW_AS_ACTION_WITH_TEXT
                    requests that when the item is shown as an action, it should be shown
                    with a text label.

                    Note: This method differs from setShowAsAction(int) only in that it returns
                    the current MenuItem instance for call chaining.

                Parameters
                    actionEnum : How the item should display. One of SHOW_AS_ACTION_ALWAYS,
                                 SHOW_AS_ACTION_IF_ROOM, or SHOW_AS_ACTION_NEVER.
                                 SHOW_AS_ACTION_NEVER is the default.
                Returns
                    This MenuItem instance for call chaining.
            */
            // Set the show as action flags for new menu item
            purple.setShowAsActionFlags(
                    MenuItem.SHOW_AS_ACTION_WITH_TEXT |
                            MenuItem.SHOW_AS_ACTION_ALWAYS
            );

            /*
                public abstract MenuItem setOnMenuItemClickListener (
                                        MenuItem.OnMenuItemClickListener menuItemClickListener)
                    Set a custom listener for invocation of this menu item. In most situations,
                    it is more efficient and easier to use onOptionsItemSelected(MenuItem)
                    or onContextItemSelected(MenuItem).

                Parameters
                    menuItemClickListener : The object to receive invokations.
                Returns
                    This Item so additional setters can be called.
            */
            // Set a click listener for the new menu item
            purple.setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() {
                @Override
                public boolean onMenuItemClick(MenuItem menuItem) {
                    Toast.makeText(mContext,menuItem.getTitle()+" Clicked",Toast.LENGTH_SHORT).show();
                    mTextView.setTextColor(Color.parseColor("#800080"));
                    return true;
                }
            });

            Toast.makeText(mContext,"Purple MenuItem Added",Toast.LENGTH_SHORT).show();
        }

        //------------------- Remove a Menu Item ---------------------------------
        /*
            public abstract MenuItem findItem (int id)
                Return the menu item with a particular identifier.

            Parameters
                id : The identifier to find.
            Returns
                The menu item object, or null if there is no item with this identifier.
        */
        // Remove a menu item from menu
        if(menu.findItem(R.id.blue)!=null){
            /*
                public abstract void removeItem (int id)
                    Remove the item with the given identifier.

                Parameters
                    id : The item to be removed. If there is no item with this identifier,
                         nothing happens.

            */
            // If blue menu item is not deleted then delete/remove it from the menu
            menu.removeItem(R.id.blue);
            Toast.makeText(mContext,"Blue MenuItem Deleted",Toast.LENGTH_SHORT).show();
        }

        //------------------- Update a Menu Item ---------------------------------
        // Update/modify/change a menu item
        MenuItem green = menu.findItem(R.id.green);
        if(green.getTitle() != "Green Text"){
            // If green menu item title not updated then update/change it
            green.setTitle("Green Text");
            Toast.makeText(mContext,"Green MenuItem Edited",Toast.LENGTH_SHORT).show();
        }

        super.onPrepareOptionsMenu(menu);
        return true;
    }
}