今天,我开始为一些Android 2.x应用程序添加android:showAsAction菜单属性,以在ActionBar上显示最常用的菜单项。
ActionBar不会立即反映启用/禁用和可见性。我需要点击右侧的菜单下拉列表才能看到这种变化发生。
好的,我知道菜单会触发onPrepareOptionsMenu事件。但是我需要做什么来刷新ActionBar呢?我认为这个更改需要从onOptionsItemSelected中应用,但我不知道我应该调用什么方法。
以下是菜单:
<item
android:icon="@drawable/ic_menu_mapmode"
android:id="@+id/men_mapview"
android:showAsAction="ifRoom|withText"
android:title="@string/txt_mapview" />
<item
android:icon="@drawable/ic_menu_mapmode"
android:id="@+id/men_satelliteview"
android:showAsAction="ifRoom|withText"
android:title="@string/txt_satelliteview" />
这里是 onPrepareOptionsMenu 方法:
@Override
public boolean onPrepareOptionsMenu(final Menu menu) {
MenuItem menuItemMapView = menu.findItem(R.id.men_mapview);
MenuItem menuItemSatelliteView = menu.findItem(R.id.men_satelliteview);
if (mapView.isSatellite()) {
menuItemMapView.setEnabled(true).setVisible(true);
menuItemmenuItemSatelliteView.setEnabled(false).setVisible(false);
} else {
menuItemMapView.setEnabled(false).setVisible(false);
menuItemmenuItemSatelliteView.setEnabled(true).setVisible(true);
}
return super.onPrepareOptionsMenu(menu);
}
这里是onOptionsItemSelected函数
@Override
public boolean onOptionsItemSelected(final MenuItem menuItem) {
switch (menuItem.getItemId()) {
case R.id.men_mapview:
mapView.setSatellite(false);
mapView.setStreetView(true);
mapView.invalidate();
invalidateOptionsMenu(); // This works on Android 3.x devices only
return true;
case R.id.men_satelliteview:
mapView.setSatellite(true);
mapView.setStreetView(false);
mapView.invalidate();
invalidateOptionsMenu(); // This works on Android 3.x devices only
return true;
}
return super.onOptionsItemSelected(menuItem);
}
编辑:如果我添加invalidateOptionsMenu,这将在Android 3.x应用程序上运行,但由于缺少方法,在Android 2.x设备上会崩溃。有什么推荐的正确方法吗?
invalidateOptionsMenu()
仅存在于 API 11(蜂巢)及以上版本。因此,如果您的应用程序运行在低于 API 11 的任何版本上,它将崩溃。为了避免这种情况,您需要将相关方法包装在另一个 静态 方法中(例如refreshActionBarMenu()
),并且仅在API> 11上运行时才调用此静态方法(因此在调用静态方法之前进行版本检查)。这可行的原因是VersionHelper
类不会在您实际使用它之前加载。 - Tony Chanelse
情况,你应该什么也不做。这是因为旧的方法(API11之前)更新菜单的方法是onPrepareOptionsMenu
,它会在用户打开菜单时自动调用。因此,为了处理旧操作系统和新的API>11,您将菜单更改的代码放在onPrepareOptionsMenu
中(这是为了处理旧操作系统),然后为了处理新操作系统,在事件触发菜单更改时调用invalidateOptionsMenu
。 - Tony ChanVersionHelper
并将这些if
放在其中,您可以使代码更加清晰。 - Ricardo