gpt4 book ai didi

reactjs - Material UI-Next 关闭 child 单击的抽屉

转载 作者:行者123 更新时间:2023-12-02 16:37:32 25 4
gpt4 key购买 nike

我正在运行 MaterialUI-Next 并且我已经尝试了抽屉的所有变体,但是当单击抽屉中的项目时我无法关闭它。我知道临时变体允许我这样做,但是当单击任何内容时它就会关闭。我只需要在单击 ListItem 时关闭它。

就我而言,抽屉里有一个 ExpansionPanel,里面有 Lists 和 ListItems。单击 ExpansionPanel 不应关闭抽屉,抽屉应保持打开状态,因为我还没有准备好离开。但是,当我单击抽屉中的 ListItem(它们包含 component="a" 项)时,抽屉应该关闭,并且 component="a"导航到其 href。

我的代码非常基础和普通,几乎与 MaterialUI-Next Drawers 中的演示完全相同。 。他们还有一个测试代码的 Playground 。但无论如何,这是我的一些相关代码

我的抽屉:

<Drawer
variant="persistent" //I tried "temporary", and "permanent" as well
elevation={16}
anchor="right"
open={this.state.open}
// onClick={(open) => this.setState({ open: false })}
// onKeyDown={(open) => this.setState({ open: false })}>
<SystemMenu />
</Drawer>

系统菜单中存储的我的内容:

import React from 'react';
import { withStyles } from 'material-ui-next/styles';
import List, { ListItem, ListItemText } from 'material-ui-next/List';
import ExpansionPanel, { ExpansionPanelDetails, ExpansionPanelSummary } from 'material-ui-next/ExpansionPanel';
import ListSubheader from 'material-ui-next/List/ListSubheader';
import {ChevronDown} from 'mdi-material-ui';
import Grid from 'material-ui-next/Grid';
const OTHERPAGES = require('data/pages.js');
const systemMenuData = OTHERPAGES['systemMenuPagesItems'];

class SystemMenu extends React.Component {
constructor(props) {
super(props);
this.state = {
expanded: null,
};
}

handleChange = panel => (event, expanded) => {
this.setState({
open: false,
expanded: expanded ? panel : false,
});
};

render() {
const { expanded, open } = this.state;
return (
<div>
<Grid
container>
<Grid item xs={12} style={{padding: 0}}>
<ListSubheader component="div">MENU ITEMS</ListSubheader>
</Grid>
</Grid>
<Grid
container>
<Grid item xs={12}>
<ExpansionPanel
expanded={expanded === 'panel1'}
onChange={this.handleChange('panel1')}>
<ExpansionPanelSummary
expandIcon={<ChevronDown />}>
Players
</ExpansionPanelSummary>
<ExpansionPanelDetails>
<List>
<ListItem
button
component="a"
href="/app/page1">
<ListItemText primary="Page 1" />
</ListItem>
<ListItem
button
component="a"
href="/app/page2">
<ListItemText primary="Page 2" />
</ListItem>
<ListItem
button
component="a"
href="/app/page3">
<ListItemText primary="Page 3" />
</ListItem>
</List>
</ExpansionPanelDetails>
</ExpansionPanel>
</Grid>
</Grid>
</div>
);
}
}

export default withStyles(styles)(SystemMenu);

我在其他帖子中读到,您可以使用 props 将 onKeyDown={(open) => this.setState({ open: false })} 传递给其子级。但我是 React 新手,对这个概念有一些问题。

基本上,我需要使 onKeyDown 适用于 ListItems,而不是实际的抽屉。我可能需要也可能不需要将抽屉变体更改回临时状态才能使 onKeyDown 属性正常工作。不太确定。

(记住上面的链接提供了一个测试代码的平台。比我尝试为 React 构建 jFiddle 好多了)

编辑

我采用了不同的方法,但不是我最喜欢的。

通过将 SystemMenu 中的内容移动到 Menu.js 文件(我的 Drawer 导入、函数和状态都在其中),我能够创建一个带有超时的 handleClose 函数,以便它关闭。这是函数:

handleClose = () => {
if (!this.state.open) {
return;
}
this.timeout = setTimeout(() => {
this.setState({ open: false });
this.setState({ expanded: null });
});
};

这需要持久变量和 handleOpen() 函数来保持抽屉打开,直到我单击具有 handleClose() 函数的列表。所以,我的抽屉现在看起来像这样

<Drawer
variant="persistent"
elevation={16}
anchor="right"
open={this.state.open}
onClick={() => { this.handleOpen(); }}>
...
My System Menu code in here, not too happy about this part. :(
...
</Drawer>

接下来,在包含扩展面板和列表的系统菜单代码中,我将 handleClose() 函数添加到列表中,它可以导航并关闭抽屉和扩展面板。像这样:

<List 
className="quickpanel-navigation"
onClick={() => { this.handleClose(); }}>
.... ListItems code here ....
</List>

这是一个好的方法,但我更希望将 SystemMenu 代码放在另一个文件中并导入到该文件中,并使用 props 来操作 SystemMenu.js 文件中 Menu.js 文件中的关闭函数。如果其他人愿意继续帮助我,我将不胜感激。

最佳答案

demo ,他们将所有 ListItems 包装在一个负责关闭抽屉的 div 中:

<div
tabIndex={0}
role="button"
onClick={this.toggleDrawer('left', false)}
onKeyDown={this.toggleDrawer('left', false)}
>
{sideList}
</div>

在此代码中,toggleDrawer 是一个设置用于 Drawer 的 open 属性的状态的函数。因此,当按下某个键或在 List 的子级之一中发生单击时,事件将冒泡到这些处理程序(只要未使用 event.stopPropagation()),并且状态会发生更改。

在您的代码中,您不希望通过单击扩展器来关闭抽屉,因此您必须以不同的方式处理这些事件。

您可以将 onClick 处理程序添加到列表中:

<ExpansionPanelDetails>
<List onClick={ () => { /* close the drawer here */ } }>
<ListItem
button
component="a"
href="/app/page1">
<ListItemText primary="Page 1" />
</ListItem>
<ListItem
button
component="a"
href="/app/page2">
<ListItemText primary="Page 2" />
</ListItem>
<ListItem
button
component="a"
href="/app/page3">
<ListItemText primary="Page 3" />
</ListItem>
</List>
</ExpansionPanelDetails>

然后,当单击 ListItems 时,事件将冒泡到 List 的处理程序,该处理程序设置状态,关闭抽屉。

根据代码结构,您可能需要修改 Drawer 的实现,以将函数传递给 SystemMenu 组件,以便其 List 上的单击处理程序可以设置其父级的状态因为 this.setState 影响 this 的状态,它是该组件的当前实例。它不会设置抽屉的状态。

更新:

根据您的评论,我添加了这一点。

在您的 SystemMenu 组件中: - 接受一个名为 closeDrawer 的 prop。 - 使用 props 中的此函数作为 List 上的 onClick 处理程序

  • 在您的菜单组件中:
  • 添加一个函数来关闭抽屉,我们暂时将其称为closeDrawer
  • 渲染 SystemMenu 时,将 this.closeDrawer 传递为 `closeDrawer
     <SystemMenu closeDrawer={this.closeDrawer} ...>

这是从子组件 SystemMenu 中更改父组件 Menu 的本地状态的一种方法。

关于reactjs - Material UI-Next 关闭 child 单击的抽屉,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49071231/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com