Jase Whatson
Jase Whatson

Reputation: 4207

Changing the actionbar menu state depending on fragment

I am trying to show/hide items in my action bar depending on which fragment is visible.

In my MainActivity I have the following

/* Called whenever invalidateOptionsMenu() is called */
@Override
public boolean onPrepareOptionsMenu(Menu menu) {

    if(this.myFragment.isVisible()){
        menu.findItem(R.id.action_read).setVisible(true);
    }else{
        menu.findItem(R.id.action_read).setVisible(false);
    }

    return super.onPrepareOptionsMenu(menu);
} 

This works great however, when the device is rotated there is a issue. After the rotation is complete onPrepareOptionsMenu is called again however this time this.myFragment.isVisible() returns false...and hence the menu item is hidden when clearly the fragment is visible (as far as whats shown on the screen).

Upvotes: 7

Views: 5509

Answers (3)

Raman Lalia
Raman Lalia

Reputation: 245

Edit: This is a quick and dirty fix, see es0329's answer below for a better solution.

Try adding this attribute to your activity tag in your android manifest:

android:configChanges="orientation|screenSize"

Upvotes: -3

NemesisDoom
NemesisDoom

Reputation: 596

Try using Fragment's setRetainInstance(true); when your fragment is attached to the Activity. That way your fragment will retain it's current values and call the lifecycle when device rotated.

Upvotes: 0

es0329
es0329

Reputation: 1432

Based on the Fragments API Guide, we can add items to the action bar on a per-Fragment basis with the following steps: Create a res/menu/fooFragmentMenu.xml that contains menu items as you normally would for the standard menu.

<menu xmlns:android="http://schemas.android.com/apk/res/android" >
    <item
        android:id="@+id/newAction"
        android:orderInCategory="1"
        android:showAsAction="always"
        android:title="@string/newActionTitle"
        android:icon="@drawable/newActionIcon"/>
</menu>

Toward the top of FooFragment's onCreate method, indicate that it has its own menu items to add.

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setHasOptionsMenu(true);
    ...
}

Override onCreateOptionsMenu, where you'll inflate the fragment's menu and attach it to your standard menu.

@Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
    inflater.inflate(R.menu.fooFragmentMenu, menu);
    super.onCreateOptionsMenu(menu, inflater);
}

Override onOptionItemSelected in your fragment, which only gets called when this same method of the host Activity/FragmentActivity sees that it doesn't have a case for the selection.

@Override
public boolean onOptionsItemSelected(MenuItem item) {

    switch (item.getItemId()) {
        case R.id.newAction:
            ...
            break;
    }
    return super.onOptionsItemSelected(item);
}

Upvotes: 25

Related Questions