当锚点元素被外部化到另一个组件时,弹出菜单的位置不正确

时间:2019-12-09 04:14:48

标签: material-ui

我是React和Material-UI的新手。尽管examples可以正常工作并且很有意义,但是它们都将内联元素用于触发按钮和菜单本身。我想要一些条件。为此,我宁愿有一个单独的呈现此功能的组件/功能。但是,只要将触发按钮移到一个函数中,我就会得到

Material-UI: the `anchorEl` prop provided to the component is invalid.
The anchor element should be part of the document layout.
Make sure the element is present in the document or that it's not display none.

我在这里浏览了类似的问题,但是没有一个看起来相关...或者我没有得到它们:(

这是修改示例的代码,在此示例中,我想将按钮渲染外部化为一个函数(以后再添加条件代码,而不添加条件代码)

export default function SimpleMenu() {
  const [anchorEl, setAnchorEl] = React.useState(null);

  const handleClick = event => {
    setAnchorEl(event.currentTarget);
  };

  const Qqq = () => {
    return (
      <Button
        aria-controls="simple-menu"
        aria-haspopup="true"
        onClick={handleClick}
      >
        Broken Menu
      </Button>
    )
  }

  const handleClose = () => {
    setAnchorEl(null);
  };

  return (
    <div>
      <p> hello</p>
      <Button
        aria-controls="simple-menu"
        aria-haspopup="true"
        onClick={handleClick}
      >
        Open Menu
      </Button>
      <Qqq />
      <Menu
        id="simple-menu"
        anchorEl={anchorEl}
        keepMounted
        open={Boolean(anchorEl)}
        onClose={handleClose}
      >
        <MenuItem onClick={handleClose}>Profile</MenuItem>
        <MenuItem onClick={handleClose}>My account</MenuItem>
        <MenuItem onClick={handleClose}>Logout</MenuItem>
      </Menu>
    </div>
  );
}

这是小提琴 https://codesandbox.io/s/material-demo-7bnki?fontsize=14&hidenavigation=1&theme=dark。我确实尝试使用SO代码段,但是我在https://stacksnippets.net/js上遇到了一些错误:(

要使事情正常进行,我缺少什么?

1 个答案:

答案 0 :(得分:1)

Qqq内放置SimpleManu代码会导致Qqq在每个SimpleMenu渲染器上重新安装。
因为Qqq已重新安装,所以anchorEl引用不再有效。
要解决此问题,请将Qqq移到SimpleMenu之外。

const Qqq = (props) => {
    return (
      <Button
        aria-controls="simple-menu"
        aria-haspopup="true"
        onClick={props.handleClick}
      >
        Broken Menu
      </Button>
    )
  }

export default function SimpleMenu() {
  const [anchorEl, setAnchorEl] = React.useState(null);

  const handleClick = event => {
    setAnchorEl(event.currentTarget);
  };

  const handleClose = () => {
    setAnchorEl(null);
  };

  return (
    <div>
      <p> hello</p>
      <Button
        aria-controls="simple-menu"
        aria-haspopup="true"
        onClick={handleClick}
      >
        Open Menu
      </Button>
      <Qqq handleClick={handleClick}/>
      <Menu
        id="simple-menu"
        anchorEl={anchorEl}
        keepMounted
        open={Boolean(anchorEl)}
        onClose={handleClose}
      >
        <MenuItem onClick={handleClose}>Profile</MenuItem>
        <MenuItem onClick={handleClose}>My account</MenuItem>
        <MenuItem onClick={handleClose}>Logout</MenuItem>
      </Menu>
    </div>
  );
}

Code Sandbox


要看到Qqq确实可以在每个SimpleMenu渲染器上重新安装,请转到“代码沙箱”,像以前一样将Qqq移到SimpleMenu内。
useEffect将在每次安装时打印到控制台,您可以看到发生了什么。