Overflow menusはメニューのアイテムをツールバー(アクションバー)へ表示することが出来ます。
その方法を紹介します。
showAsAction属性の指定
「Overflow menusの実装」で紹介したサンプルのような、メニューを表示するだけの実装の場合、メニューのアイテムはオーバーフローアイコンに隠されます。
オーバーフローアイコンに隠された状態ではなく、メニューのアイテムをツールバー(アクションバー)へ表示させることが出来ます。
アイテムをツールバーへ表示させるためにshowAsAction属性を指定します。


アイテムのタイトルを表示
showAsAction属性は3つのタイプがあり、それぞれの動作は次の通りです。
| showAsAction | アイテムの表示 | 表示例 | 
|---|---|---|
| ifRoom | 配置が許される範囲へ表示 配置が許される個数を表示 上記から溢れるアイテムは隠される |  ※すべてのアイテムがifRoom | 
| 【注意】 ・アプリ名とアイテムが重なる時、アイテムの表示を優先する | ||
| always | 常に表示する |  ※すべてのアイテムがalways | 
| 【注意】 ・アプリ名とアイテムが重なる時、アイテムの表示を優先する | ||
| never、なし (デフォルト) | 常に表示しない 全てのアイテムが隠される |  ※すべてのアイテムがnever | 
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:id="@+id/menu_file"
        android:title="File"
        app:showAsAction="ifRoom" />
    <item
        android:id="@+id/menu_edit"
        android:title="Edit"
        app:showAsAction="ifRoom" />
    <item
        android:id="@+id/menu_help"
        android:title="Help"
        app:showAsAction="ifRoom" />
</menu>
表示できなかった(配置が許される範囲・個数から溢れた)アイテムはオーバーフローアイコンに隠されます。
アイテムのアイコンを表示
icon属性へアイコン画像が指定されていると、タイトルよりもアイコンを優先して表示します。
| showAsAction | 説明 | 表示例 | 
|---|---|---|
| ifRoom | 配置が許される範囲へ表示 配置が許される個数を表示 上記から溢れるアイテムは隠される |  ※すべてのアイテムがifRoom | 
| 【注意】 ・アプリ名とアイテムが重なる時、アイテムの表示を優先する | ||
| always | 常に表示する |  ※すべてのアイテムがalways | 
| 【注意】 ・アプリ名とアイテムが重なる時、アイテムの表示を優先する | ||
| never、なし (デフォルト) | 常に表示しない 全てのアイテムが隠される |  ※すべてのアイテムがnever | 
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:id="@+id/menu_file"
        android:icon="@drawable/outline_folder_24"
        android:title="File"
        app:showAsAction="ifRoom" />
    <item
        android:id="@+id/menu_edit"
        android:icon="@drawable/outline_edit_24"
        android:title="Edit"
        app:showAsAction="ifRoom" />
    <item
        android:id="@+id/menu_help"
        android:icon="@drawable/outline_help_outline_24"
        android:title="Help"
        app:showAsAction="ifRoom" />
</menu>
表示できなかった(配置が許される範囲・個数から溢れた)アイテムはオーバーフローアイコンに隠されます。
アイテムのタイトル+アイコンを表示
アイテムのicon属性へアイコン画像が指定されていると、タイトルよりもアイコンを優先して表示します。
アイコンに加えてタイトルも表示したければ、アイテムのshowAsAction属性にwithTextを追加します。
| showAsAction | 説明 | 表示例 | 
|---|---|---|
| withText | アイコンと一緒にタイトルも表示する | ※単体の使用は不可 ※ifRoom、alwaysと併用 | 
| ifRoom|withText | 配置が許される範囲へ表示 配置が許される個数を表示 上記から溢れるアイテムは隠される | 【幅:320dpの時】  【幅:480dpの時】  ※すべてのアイテムがifRoom|withText | 
| 【注意】 ・画面の幅<480[dp]の時、アイテムのタイトルは表示されない ・アプリ名のタイトルとアイテムが重なる時、アイテムの表示を優先する | ||
| always|withText | 常に表示する | 【幅:320dpの時】  【幅:480dpの時】  ※すべてのアイテムがalways|withText | 
| 【注意】 ・画面の幅<480[dp]の時、アイテムのタイトルは表示されない ・アプリ名のタイトルとアイテムが重なる時、アイテムの表示を優先する | ||
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:id="@+id/menu_file"
        android:icon="@drawable/outline_folder_24"
        android:title="File"
        app:showAsAction="ifRoom|withText" />
    <item
        android:id="@+id/menu_edit"
        android:icon="@drawable/outline_edit_24"
        android:title="Edit"
        app:showAsAction="ifRoom|withText" />
    <item
        android:id="@+id/menu_view"
        android:icon="@drawable/outline_monitor_24"
        android:title="View"
        app:showAsAction="ifRoom|withText" />
    <item
        android:id="@+id/menu_search"
        android:icon="@drawable/outline_search_24"
        android:title="Search"
        app:showAsAction="ifRoom|withText" />
    <item
        android:id="@+id/menu_help"
        android:icon="@drawable/outline_help_outline_24"
        android:title="Help"
        app:showAsAction="ifRoom|withText" />
</menu>
表示できなかった(配置が許される範囲・個数から溢れた)アイテムはオーバーフローアイコンに隠されます。
「配置が許される範囲・個数」とは
ツールバー(アクションバー)の最も重要な役割はアプリ名を表示することがです。
メニューのアイテム(タイトル、アイコン)をツールバーに表示するとき、アプリ名の表示を妨げないように、アイテムの「配置が許される範囲・個数」が決められています。
この範囲・個数は、固定ではありません。画面の幅が広ければ大きくなるし、狭ければ小さくなります。これらの関係は次のように定義されています。
| 画面の大きさ[dp] | 許される個数 (アイコンを並べた幅[dp]) | 許される範囲 | 
|---|---|---|
| 000≧画面の幅>600 | 5(280) | 画面の幅/2 | 
| 600≧画面の幅≧500 | 4(224) | |
| 500>画面の幅≧360 | 3(168) | |
| 360>画面の幅 | 2(112) | |
| ※アイコンサイズ:56×56[dp] | ||
public class ActionBarPolicy {
    ...
    /**
     * Returns the maximum number of action buttons that should be permitted within an action
     * bar/action mode. This will be used to determine how many showAsAction="ifRoom" items can fit.
     * "always" items can override this.
     */
    public int getMaxActionButtons() {			// 許される個数
        final Configuration config = mContext.getResources().getConfiguration();
        final int width = config.screenWidthDp;
        final int height = config.screenHeightDp;
        final int smallest = config.smallestScreenWidthDp;
        if (smallest > 600 || (width > 960 && height > 720) || (width > 720 && height > 960)) {
            // For values-w600dp, values-sw600dp and values-xlarge.
            return 5;
        } else if (width >= 500 || (width > 640 && height > 480) || (width > 480 && height > 640)) {
            // For values-w500dp and values-large.
            return 4;
        } else if (width >= 360) {
            // For values-w360dp.
            return 3;
        } else {
            return 2;
        }
    }
	...
    public int getEmbeddedMenuWidthLimit() {	// 許される範囲
        return mContext.getResources().getDisplayMetrics().widthPixels / 2;
    }
	...
}
ちなみに、記事中のツールバーのスナップショットはスクリーンサイズ320×480[px](mdpi)の端末です。
※mdpiの端末は1[px]=1[dp]です。
関連記事:
