首页 > 解决方案 > 按 T​​ab 键关闭从子菜单打开的 Material UI 对话框

问题描述

我需要创建一个包含许多具有子菜单的菜单的菜单栏。当我从顶级菜单项打开对话框时,一切都按预期/预期工作。但是当我从子菜单打开一个对话框时,按 tab 键会关闭对话框。

我尝试了几种不同的方法来实现嵌套菜单并确定了这里讨论的方法:https ://github.com/mui-org/material-ui/issues/11723

我在这里创建了示例代码来演示该问题: https ://codesandbox.io/s/loving-heisenberg-rvwwb 你会看到这是从我在 GitHub 上找到的子菜单示例中分叉出来的。我改变了一些东西,因为我不确定如何从该示例中添加对话框的打开,所以我不确定我这样做的方式是否正确。

标签: reactjsmaterial-ui

解决方案


问题是Tab触发关闭父菜单,然后导致对话框被卸载。您可以使用状态来防止父菜单在对话框打开时关闭,但这会留下不同的问题。无论父菜单是否关闭,当 aTab发生时,它都会调用event.preventDefault(),然后阻止Tab更改焦点位置(默认浏览器行为)。

您可以通过停止键事件的Dialog传播来解决此问题。Tab这会阻止Menu接收它,因此Menu不会尝试关闭自身,也不会调用event.preventDefault(). 我不能保证这不会引入一些新问题,但这解决了所描述的问题。

const stopPropagationForTab = (event) => {
  if (event.key === "Tab") {
    event.stopPropagation();
  }
};

      <Dialog
        onKeyDown={stopPropagationForTab}

使用对话框编辑级联菜单

在我的沙箱分支中,我将 Material-UI 版本从 1.2 升级到 4.0,只是因为我想确保问题与已更改的方面无关。这抛弃了一些样式,但要解决的主要行为似乎在两个版本中都一样。


处理此问题的另一种方法是重新编写代码,使对话框不再是菜单的子项。然后单击打开对话框的菜单项将在顶层设置状态以关闭所有菜单并打开对话框。这可能是处理这个问题的更好方法,但它是对代码结构的更大改变。


推荐阅读