我通过此代码添加了自定义上下文菜单。
ns_text_menu.xml只包含两个项目。
this.textViewTest.setCustomSelectionActionModeCallback(new ActionMode.Callback() {
@Override
public boolean onCreateActionMode(ActionMode mode, Menu menu) {
menu.clear();
mode.setTitle("Menu");
mode.getMenuInflater().inflate(R.menu.ns_text_menu, menu);
return true;
}
@Override
public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
return false;
}
@Override
public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
if (item.getTitle().equals("View Vocab")) {
ErrorController.showToast(mContext, "View Vocab : " + textViewTest.getText().toString().substring(textViewTest.getSelectionStart(), textViewTest.getSelectionEnd()));
}else{//cpy
ErrorController.showToast(mContext, "Copy : " + textViewTest.getSelectionStart() + ", " + textViewTest.getSelectionEnd());
}
return true;
}
@Override
public void onDestroyActionMode(ActionMode mode) {
}
});
如本回答(Remove default CAB items in TextView selection ActionMode)所述,我使用了代码
menu.clear();
在onCreateActionMode上清除默认的CAB菜单。它清除了一些默认的上下文菜单,但仍然是这两个菜单:
'全部选择'和'字典'。
测试机是galaxy s9 +(android 8.0)和nexus模拟器(6.0)。
他们都显示意外的菜单。
如何解决此问题?
答案 0 :(得分:1)
似乎在onPrepareActionMode上添加了意外的菜单。
要解决此问题,
(1)将我的自定义菜单的ID存储在全局列表中。 (2)在onPrepareActionMode中,删除与上面列表中存储的id不匹配的每个菜单。
代码看起来像这样。
this.textViewTest.setCustomSelectionActionModeCallback(new ActionMode.Callback() {
private List<Integer> validResIdList = new ArrayList<>();
@Override
public boolean onCreateActionMode(ActionMode mode, Menu menu) {
menu.clear();
validResIdList.clear();
mode.getMenuInflater().inflate(R.menu.ns_text_menu, menu);
for (int i = 0; i < menu.size(); i++) {
validResIdList.add(menu.getItem(i).getItemId());
}
return true;
}
@Override
public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
List<Integer> toRemoveResId = new ArrayList<>();
for (int i = 0; i < menu.size(); i++) {
if (menu.getItem(i).getItemId() != (validResIdList.get(0)) && menu.getItem(i).getItemId() != (validResIdList.get(1))) {
toRemoveResId.add(menu.getItem(i).getItemId());
}
}
for (Integer resId : toRemoveResId) {
menu.removeItem(resId);
}
return true;
}
@Override
public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
if(validResIdList != null && validResIdList.size() > 0){
if (item.getItemId() == validResIdList.get(0)) {
ErrorController.showToast(mContext, "View Vocab : " + textViewTest.getText().toString().substring(textViewTest.getSelectionStart(), textViewTest.getSelectionEnd()));
mode.finish();
} else {//cpy
ErrorController.showToast(mContext, "Copy : " + textViewTest.getSelectionStart() + ", " + textViewTest.getSelectionEnd());
mode.finish();
}
}
return true;
}
@Override
public void onDestroyActionMode(ActionMode mode) {
}
});
我在R.id.xxx上使用validResIdList的原因是因为我在库项目上实现了这个。
如果您在应用程序项目中,可以使用R.id.xxx找出您正在处理的菜单。