Material-UI 的 Dialog 如何允许在对话框后面进行交互?

Posted

技术标签:

【中文标题】Material-UI 的 Dialog 如何允许在对话框后面进行交互?【英文标题】:How can Material-UI's Dialog allow interaction behind the dialog? 【发布时间】:2020-08-03 17:31:42 【问题描述】:

我在我的 React 应用程序中使用Material-UI,并且我有一个Dialog,在我单击按钮后会出现在多个表单元素上。

我还设置了该对话框以允许使用react-draggable 拖动它。

当对话框显示时,它后面的表单元素都不能被访问。我意识到阻止与对话框背后元素的交互在直觉上是有意义的。

但是,我正试图弄清楚如何显示对话框,但仍然能够编辑它后面的表单元素。

代码示例here:

有谁知道是否可以显示 MaterialUI 对话框并仍然能够与对话框后面的表单元素进行交互(即,当对话框被拖走时)?

【问题讨论】:

不要和控制权斗,尽量找一个效果更好的;也许用户可以在填写页面本身的表单字段时管理页脚中的祝酒词?需要更多地了解对话框中的内容?您可以使用 css 删除对话框下的覆盖,但我建议不要这样做。 【参考方案1】:

该对话框旨在阻止所有其他交互,以便用户可以专注于其内容。无论如何,我找到了一种解决方案,可能不是更好但在这里工作,代码是这样的:

<Dialog
  hideBackdrop // Disable the backdrop color/image
  disableEnforceFocus // Let the user focus on elements outside the dialog
  style= position: 'initial'  // This was the key point, reset the position of the dialog, so the user can interact with other elements
  disableBackdropClick // Remove the backdrop click (just to be sure)
  ...
>
  ...
</Dialog>

Here a working example

【讨论】:

这是完美的。我没有意识到 Material-UI Modal 道具也适用于 Dialog,但回想起来,这是有道理的。而你的风格技巧——正如你所提到的——是key!谢谢!已接受答案。 很高兴能帮到你! 位置初始会抛出弹出的样式以显示在内容的末尾而不是预期的叠加层 如果您还想滚动对话框后面的内容,请传递 disableScrollLock=true @FernandoGomes 当我应用此代码时它可以工作。但对话框出现在网站的顶部中心。你知道怎么解决吗?【参考方案2】:

这是可能的,而且没有太多麻烦!当对话框打开时,它的根容器是一个类为MuiDialog-root 的div,直接在你的&lt;body&gt; 中生成。我们没有将 react-draggable 组件放在对话框的 PaperComponent 周围,而是将其放在整个对话框周围:

<Draggable 
  handle='[class*="MuiDialog-root"]' 
  cancel='[class*="MuiDialogContent-root"]'>
    <Dialog 
      // Styling goes here
     > 
     ... // Dialog contents
    </Dialog>
</Draggable>

然后,有必要对 Dialog 进行一些样式设置。我们需要确保禁用背景,然后缩小容器大小,这样当我们在它后面点击时,我们实际上是在选择其他组件:

<Dialog
    open=open
    onClose=handleClose
    disableEnforceFocus // Allows other things to take focus
    hideBackdrop  // Hides the shaded backdrop
    disableBackdropClick  // Prevents backdrop clicks
    PaperComponent=PaperComponent
    style=
        top: '30%', // Position however you like
        left: '30%',
        height: 'fit-content',  // Ensures that the dialog is 
        width: 'fit-content',   // exactly the same size as its contents
    
    >
...
</Dialog>

注意PaperComponent 属性。根据可拖动对话框上的material-ui docs,这是指包含对话框内容的表面。但是,我们需要创建此组件以进行样式设置,而不是将纸张包装在 &lt;Draggable&gt; 中。如果我们不这样做,PaperComponent 将有很大的、令人讨厌的边距,并且不能正确地适应它的父级。

function PaperComponent(props: PaperProps)  
// PaperProps is an import from '@material-ui/core'
    return (
        <Paper ...props style= margin: 0, maxHeight: '100%'  />
    );

请务必将此函数放置在渲染组件之外。否则,每次状态更改时,您的对话框内容都会重新加载。这对我来说很糟糕,因为我在对话框中使用了自动完成字段,并且每次我选择一个选项并使用 onChange() 执行某些操作时,文本输入都会消失。更改函数范围解决了这个问题。

【讨论】:

这太棒了!谢谢! 我试过了,但这不会使组件可拖动@April【参考方案3】:

禁用强制焦点也会干扰原点和位置 使用禁用自动对焦

<Dialog
    hideBackdrop=true
    disableBackdropClick
    disableAutoFocus
    ...
>
    ....
</Dialog>
    
    

【讨论】:

以上是关于Material-UI 的 Dialog 如何允许在对话框后面进行交互?的主要内容,如果未能解决你的问题,请参考以下文章

如何使 Material-UI Dialog 在 React 中工作

如何将 Material-table 与 Material-UI Dialog 结合起来? (反应JS)

Material-UI Dialog 如何在对话框的右上角放置关闭按钮

如何在 Material-UI 中为对话框设置高度?

React、Jest 和 Material-UI:如何测试以模态或弹出框呈现的内容

React Material-Ui(0.20.0) 对话框未显示预期结果?