运行期间更改选项菜单 - invalidateOptionsMenu()

时间:2022-12-09 15:31:29

I am creating a menu where one of the items is used the lock an object. When this item is clicked, the menu should be recreated with a button to unlock the item. I created two menus for this. This is working fine. I read that in Android version >= 11 the onPrepareOptionsMenu is no longer called when displaying the menu and I have to call invalidateOptionsMenu(). So I changed the build target (both in the Manifest and in properties) to 11 and ran the app on an AVD of 4.0.3. The program is still working fine, but I thought it shouldn't anymore, and I should check

我正在创建一个菜单,其中一个项目用于锁定一个对象。单击此项目时,应使用按钮重新创建菜单以解锁项目。我为此创建了两个菜单。这工作正常。我读到在Android版本> = 11时,在显示菜单时不再调用onPrepareOptionsMenu,我必须调用invalidateOptionsMenu()。所以我将构建目标(在Manifest和属性中)更改为11并在AVD 4.0.3上运行应用程序。该程序仍然工作正常,但我认为它应该不再,我应该检查

if (Build.VERSION.SDK_INT >= 11)
{
  invalidateOptionsMenu();
}

This is my code:

这是我的代码:

public class MainActivity3 extends Activity{

    boolean locked;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);

        locked = false;
    }

      @Override
      public boolean onCreateOptionsMenu(Menu menu){
            MenuInflater inflater = getMenuInflater();
            inflater.inflate(R.menu.changing_menu1, menu);

            return true;
        }

        @Override
        public boolean onPrepareOptionsMenu(Menu menu) {

            menu.clear();
            MenuInflater inflater = getMenuInflater();

            if (locked) {
                inflater.inflate(R.menu.changing_menu2, menu);
            }
            else {
                inflater.inflate(R.menu.changing_menu1, menu);
            }

        return super.onPrepareOptionsMenu(menu);
        }

        public boolean onOptionsItemSelected(MenuItem item) {
            switch (item.getItemId()) {

          case R.id.Menu1:
          break;

          case R.id.Menu2 :
          break;

          case R.id.Menu3 :
          locked = !locked;
          break;

           }
        return true;
        }
}

So the Menu is still refreshed/recreated in 4.0. Did I misunderstand something about the usage of invalidateOptionsMenu();?

因此,菜单仍然在4.0中刷新/重新创建。我是否误解了invalidateOptionsMenu()的用法;?

1 个解决方案

#1


30  

invalidateOptionsMenu() was added to give us the ability to force onCreateOptionsMenu() to be called again. onPrepareOptionsMenu() is still called every time you call the menu.

添加了invalidateOptionsMenu(),使我们能够强制再次调用onCreateOptionsMenu()。每次调用菜单时仍会调用onPrepareOptionsMenu()。

What you are trying to achieve above is a good example of when to use invalidateOptionsMenu() but because of backwards compatibility you will need to do both:

您在上面尝试实现的是一个很好的示例,说明何时使用invalidateOptionsMenu()但由于向后兼容性,您需要同时执行以下操作:

if (Build.VERSION.SDK_INT >= 11) {
  invalidateOptionsMenu();
}


@Override
public boolean onCreateOptionsMenu(Menu menu){
    if (Build.VERSION.SDK_INT >= 11) {
        selectMenu(menu);
    }
    return true;
}

@Override
public boolean onPrepareOptionsMenu(Menu menu) {
    if (Build.VERSION.SDK_INT < 11) {
        selectMenu(menu);
    }
    return true;
}

private void selectMenu(Menu menu) {
    menu.clear();
    MenuInflater inflater = getMenuInflater();

    if (locked) {
        inflater.inflate(R.menu.changing_menu2, menu);
    }
    else {
        inflater.inflate(R.menu.changing_menu1, menu);
    }
}

#1


30  

invalidateOptionsMenu() was added to give us the ability to force onCreateOptionsMenu() to be called again. onPrepareOptionsMenu() is still called every time you call the menu.

添加了invalidateOptionsMenu(),使我们能够强制再次调用onCreateOptionsMenu()。每次调用菜单时仍会调用onPrepareOptionsMenu()。

What you are trying to achieve above is a good example of when to use invalidateOptionsMenu() but because of backwards compatibility you will need to do both:

您在上面尝试实现的是一个很好的示例,说明何时使用invalidateOptionsMenu()但由于向后兼容性,您需要同时执行以下操作:

if (Build.VERSION.SDK_INT >= 11) {
  invalidateOptionsMenu();
}


@Override
public boolean onCreateOptionsMenu(Menu menu){
    if (Build.VERSION.SDK_INT >= 11) {
        selectMenu(menu);
    }
    return true;
}

@Override
public boolean onPrepareOptionsMenu(Menu menu) {
    if (Build.VERSION.SDK_INT < 11) {
        selectMenu(menu);
    }
    return true;
}

private void selectMenu(Menu menu) {
    menu.clear();
    MenuInflater inflater = getMenuInflater();

    if (locked) {
        inflater.inflate(R.menu.changing_menu2, menu);
    }
    else {
        inflater.inflate(R.menu.changing_menu1, menu);
    }
}