基于 Material UI 中 IconButton 组件的 onClick 属性 在 React 中进行条件渲染
Conditional rendering in React based on the onClick property of the IconButton component in Material UI
import "./styles.css";
import React, { useState } from "react";
import { IconButton } from "@material-ui/core";
import ExpandMoreIcon from "@material-ui/icons/ExpandMore";
export default function App() {
const [expand, setExpand] = useState({
arrowA: false,
arrowB: false,
arrowC: false,
arrowD: false
});
const handleChange = (e) => {
setExpand({
...expand,
[e.currentTarget.name]: !expand.arrowA,
[e.currentTarget.name]: !expand.arrowB,
[e.currentTarget.name]: !expand.arrowC,
[e.currentTarget.name]: !expand.arrowD
});
};
return (
<div className="App">
<h1>React conditional rendering</h1>
<h2>
The component below should render if the user clicks on the arrow, and
be removed if the user clicks the arrow again.
</h2>
<h5>
This arrow should show the first part of the text.{" "}
<IconButton
variant="contained"
size="small"
color="primary"
aria-label="expand"
name="arrowA"
onClick={handleChange}
>
{<ExpandMoreIcon />}
</IconButton>
</h5>
<h5>
This arrow show the second part of the text if clicked, and be possible
to remove.
<IconButton
variant="contained"
size="small"
color="primary"
aria-label="expand"
name="arrowB"
onClick={handleChange}
>
{<ExpandMoreIcon />}
</IconButton>
</h5>
<h5>
This arrow should show the third part of the text below.{" "}
<IconButton
variant="contained"
size="small"
color="primary"
aria-label="expand"
name="arrowC"
onClick={handleChange}
>
{<ExpandMoreIcon />}
</IconButton>
</h5>
<h5>
This was really the last part.{" "}
<IconButton
variant="contained"
size="small"
color="primary"
aria-label="expand"
name="arrowD"
onClick={handleChange}
>
{<ExpandMoreIcon />}
</IconButton>
</h5>
{expand.arrowA ? (
<h2>
This is the first start of the story, let's see if we can add the
rest.
</h2>
) : null}
{expand.arrowB ? (
<h2>This is the middle part, it starts to break soon.</h2>
) : null}
{expand.arrowC ? (
<h2>
We are nearing the end. But as you see, this state management is not
optimal.
</h2>
) : null}
{expand.arrowD ? (
<h2>
This is was all I wanted to show. But why is removing this so hard?
How to make this better?
</h2>
) : null}
</div>
);
}
首先,感谢您的光临!我是 React 的初学者,有一个关于如何使我的状态管理更优化和更好地工作的问题。
我正在尝试在一个 React 挂钩中呈现多个组件,以避免必须创建许多不同的挂钩。但是我的解决方案无法正常工作并且不是很理想。我缺乏如何让状态更有活力的知识,但我觉得我很接近。以下是示例:Code Sandbox
如果您打开代码沙箱,在第二次尝试文件中,我尝试设置 [e.currentTarget.value]: [e.currentTarget.status]
以尝试从 IconButton 获取状态,我将其存储为 status={!expand.checkedA}
。但这显然不是 React 状态管理的工作方式。
有人可以告诉我这里的最佳做法是什么吗?如果您有条件渲染多个组件的替代方法的建议,我也很好奇。
干杯。
我认为你做的很好我只是改变一些东西让它工作:
首先让 handleChange 执行此操作而不是当前代码:
const handleChange = (e) => {
setExpand({
...expand,
[e.currentTarget.name]: !expand[e.currentTarget.name]
});
};
这样你只会改变你点击的那一个,其余的将保持不变。
其次,您的 jsx 中不需要三元运算符,您可以使用 && 运算符:
{expand.arrowA && (
<h2>
This is the first start of the story, let's see if we can add the
rest.
</h2>
)}
如果您有问题,请检查分叉沙箱:
https://codesandbox.io/s/cool-fog-h7vct?file=/src/App.js:2073-2226
import "./styles.css";
import React, { useState } from "react";
import { IconButton } from "@material-ui/core";
import ExpandMoreIcon from "@material-ui/icons/ExpandMore";
export default function App() {
const [expand, setExpand] = useState({
arrowA: false,
arrowB: false,
arrowC: false,
arrowD: false
});
const handleChange = (e) => {
setExpand({
...expand,
[e.currentTarget.name]: !expand.arrowA,
[e.currentTarget.name]: !expand.arrowB,
[e.currentTarget.name]: !expand.arrowC,
[e.currentTarget.name]: !expand.arrowD
});
};
return (
<div className="App">
<h1>React conditional rendering</h1>
<h2>
The component below should render if the user clicks on the arrow, and
be removed if the user clicks the arrow again.
</h2>
<h5>
This arrow should show the first part of the text.{" "}
<IconButton
variant="contained"
size="small"
color="primary"
aria-label="expand"
name="arrowA"
onClick={handleChange}
>
{<ExpandMoreIcon />}
</IconButton>
</h5>
<h5>
This arrow show the second part of the text if clicked, and be possible
to remove.
<IconButton
variant="contained"
size="small"
color="primary"
aria-label="expand"
name="arrowB"
onClick={handleChange}
>
{<ExpandMoreIcon />}
</IconButton>
</h5>
<h5>
This arrow should show the third part of the text below.{" "}
<IconButton
variant="contained"
size="small"
color="primary"
aria-label="expand"
name="arrowC"
onClick={handleChange}
>
{<ExpandMoreIcon />}
</IconButton>
</h5>
<h5>
This was really the last part.{" "}
<IconButton
variant="contained"
size="small"
color="primary"
aria-label="expand"
name="arrowD"
onClick={handleChange}
>
{<ExpandMoreIcon />}
</IconButton>
</h5>
{expand.arrowA ? (
<h2>
This is the first start of the story, let's see if we can add the
rest.
</h2>
) : null}
{expand.arrowB ? (
<h2>This is the middle part, it starts to break soon.</h2>
) : null}
{expand.arrowC ? (
<h2>
We are nearing the end. But as you see, this state management is not
optimal.
</h2>
) : null}
{expand.arrowD ? (
<h2>
This is was all I wanted to show. But why is removing this so hard?
How to make this better?
</h2>
) : null}
</div>
);
}
首先,感谢您的光临!我是 React 的初学者,有一个关于如何使我的状态管理更优化和更好地工作的问题。
我正在尝试在一个 React 挂钩中呈现多个组件,以避免必须创建许多不同的挂钩。但是我的解决方案无法正常工作并且不是很理想。我缺乏如何让状态更有活力的知识,但我觉得我很接近。以下是示例:Code Sandbox
如果您打开代码沙箱,在第二次尝试文件中,我尝试设置 [e.currentTarget.value]: [e.currentTarget.status]
以尝试从 IconButton 获取状态,我将其存储为 status={!expand.checkedA}
。但这显然不是 React 状态管理的工作方式。
有人可以告诉我这里的最佳做法是什么吗?如果您有条件渲染多个组件的替代方法的建议,我也很好奇。
干杯。
我认为你做的很好我只是改变一些东西让它工作:
首先让 handleChange 执行此操作而不是当前代码:
const handleChange = (e) => {
setExpand({
...expand,
[e.currentTarget.name]: !expand[e.currentTarget.name]
});
};
这样你只会改变你点击的那一个,其余的将保持不变。
其次,您的 jsx 中不需要三元运算符,您可以使用 && 运算符:
{expand.arrowA && (
<h2>
This is the first start of the story, let's see if we can add the
rest.
</h2>
)}
如果您有问题,请检查分叉沙箱: https://codesandbox.io/s/cool-fog-h7vct?file=/src/App.js:2073-2226