'Android 4.3 menu item showAsAction="always" ignored

I'm using the new v7 appcompat library available starting from Android 4.3 (API level 18).

Regardless of what is specified in showAsAction for a menu item, it's not shown - it always creates the overflow menu icon, and puts even a single menu item under the menu.

Trying to add menu to an activity like this:

@Override
public boolean onCreateOptionsMenu(Menu menu) {
    getMenuInflater().inflate(R.menu.menu_sizes, menu);
    return true;
}

And here's my menu xml:

<menu xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:id="@+id/menu_add_size"
        android:title="@string/menu_add_item"
        android:orderInCategory="10"
        android:showAsAction="always"
        android:icon="@android:drawable/ic_menu_add" />
</menu>

Is it a bug of the new support library v7, or just something wrong with the code? I've been using the similar code with ActionBarSherlock many times before.



Solution 1:[1]

Figured out myself. With the support library v7 the showAsAction should go under a custom namespace like this:

<menu xmlns:android="http://schemas.android.com/apk/res/android"
      xmlns:balloonberry="http://schemas.android.com/apk/res-auto">
    <item android:id="@+id/menu_add_size"
        android:title="@string/menu_add_item"
        android:orderInCategory="10"
        balloonberry:showAsAction="always"
        android:icon="@android:drawable/ic_menu_add" />
</menu>

Solution 2:[2]

Also make sure that you use correct inflater in ActionBarActivity.onCreateOptionsMenu() method.

Correct solution:

MenuInflater menuInflater = getMenuInflater();
menuInflater.inflate(R.menu.menu_example, menu);

Incorrect solution:

MenuInflater menuInflater = new MenuInflater(this);
menuInflater.inflate(R.menu.menu_example, menu);

Solution 3:[3]

For Fragments

Menus with custom namespace will prevent showAsAction from showing.

Using "android:" prefix for showAsAction will work, even though Android Studio will remark you should use a custom name space.

<menu xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:id="@+id/action_add_checkin"
          android:title="Add Checkin"
          android:orderInCategory="10"
          android:showAsAction="always"
        android:icon="@android:drawable/ic_menu_add"/>
</menu>

This is using Android SDK 22 and Support v4 fragments, in case that makes any difference.

Solution 4:[4]

Got the same problem, but on Android 5. I have 3 items but OS ignored my attribute "always" and showed only 2 items. Here my solution:

  @Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
    Log.d(TAG, "onCreateOptionsMenu()");
    inflater.inflate(R.menu.your_menu, menu);
    for (int j = 0; j < menu.size(); j++) {
        MenuItem item = menu.getItem(j);
        Log.d(TAG, "set flag for " + item.getTitle());
        item.setShowAsActionFlags(MenuItem.SHOW_AS_ACTION_ALWAYS);
    }
}

Solution 5:[5]

Also make sure that you have the correct path for the namespace. It will not give you an error message if it's wrong.

I had

<menu xmlns:android="http://schemas.android.com/apk/res/android"
      xmlns:myapp="http://schemas.android.com/res-auto">

instead of

<menu xmlns:android="http://schemas.android.com/apk/res/android"
      xmlns:myapp="http://schemas.android.com/apk/res-auto">

All I knew was that it wasn't working. Not sure how I managed to forget the /apk part of the path, but it happened. No error message, just an elusive bug to track down.

Solution 6:[6]

In my case, I had to remove from my app's build.gradle compile 'com.android.support:appcompat-v7:21.0.3'.

Notice: My min sdk = 14, and created project by android studio inserted my unnesessary dependancy.

After this replace you can write android:showAsAction="always"

Solution 7:[7]

This might not be your case but I was using

new MenuInflater(this).inflate(R.menu.my_menu, menu);

changing it to

getMenuInflater().inflate(R.menu.my_menu, menu);

fixed the problem!

Solution 8:[8]

<?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/back"
        android:icon="@drawable/back"
        app:showAsAction="always"
        android:title="@string/back"/>
    <item
        android:id="@id/save"
        android:icon="@drawable/le_top_btn_icon_add"
        app:showAsAction="ifRoom"
        android:title="@string/save"/>
</menu>

don't work, with supportLibraryVersion = '25.1.0' compileSdkVersion = 25

see the "Warning"

Should use app:showAsAction with the appcompat library with xmlns:app="http://schemas.android.com/apk/res-auto" less... (Ctrl+F1)

When using the appcompat library,menu resources should refer to the showAsAction in the app: namespace, not the android: namespace.

Similarly,when not using the appcompat library, you should be using the android:showAsAction attribute.

I think the warn can be ignore.

Solution 9:[9]

add custom namespace like this to showAsAction and actionViewClass:

<menu xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto">
<item android:id="@+id/search"
    android:title="@string/search"
    android:icon="@drawable/ic_search"
    app:showAsAction="collapseActionView|ifRoom"
    app:actionViewClass="android.widget.SearchView" />

Solution 10:[10]

I have solved it by replacing

android:showAsAction="ifRoom"

with

app:showAsAction="ifRoom"

That is menuitme xml look like,

<item android:id="@+id/action_refresh"
      android:title="Refresh"
      android:icon="@drawable/refresh2"
      app:showAsAction="ifRoom" />

Solution 11:[11]

The simplest way is Modify your code by adding

xmlns:app="http://schemas.android.com/apk/res-auto"

and change this code

android:showAsAction="always"

to

app:showAsAction="always"

and finally

<menu xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto">
    <item android:id="@+id/menu_add_size"
        android:title="@string/menu_add_item"
        android:orderInCategory="10"
        app:showAsAction="always"
        android:icon="@android:drawable/ic_menu_add" />
</menu>

Solution 12:[12]

In Addition to @petrnohejl 's answer, in Kotlin you can just use this one line without initializing it first.

override fun onCreateOptionsMenu(menu: Menu?): Boolean {
        menuInflater.inflate(R.menu.options_menu, menu)
        return true
    }

In my case, the menu item just ignored my app:showAsAction="always" or "ifRoom" and it really annoys me for hours. Then, after I searched in StackOverflow, I realized that I'm not using the correct MenuInflater.