[英]How to implement a check all button for radio buttons, using React Hooks?
不要與檢查頁面上的每個單選按鈕混淆。 我想實現一個check all button
,將嵌套 object state 的值設置為某個值。 我將每個問題存儲在嵌套的 state 中。 前任。
formQuestions({
kitchen: [question,question2,question3],
living: [question,question2,question3]
})
每個問題都制作了四個單選按鈕。 現在一次只能選擇一個單選按鈕。 每個單選按鈕都有自己的值。 前任。 `“好”、“一般”、“差”、“不適用”。
選擇單按鈕時,state是為該部分和問題動態生成的。 前任。
formAnswers({
kitchen: {
question: "Good"
question2: "Poor"
}
})
這里的目標是我要創建的按鈕,它只檢查每個問題 Ex 的一個值。 點擊按鈕question: "Good", question2: "Good"
等。
對我來說,將 state 設置為動態值,我需要“Section name”讓我們稱之為Name
和“Question”我們稱之為question
。 這將使我能夠像這樣訪問值formAnswers[Name][question]: value
我正在嘗試從名為 SectionHeader 的組件中設置SectionHeader
。 這些包含按鈕。
SectionHeader.js
import { FormAnswersContext, FormQuestionsContext } from "../../Store";
function SectionHeader({ title, name }) {
const [formAnswers, setFormAnswers] = useContext(FormAnswersContext);
const [formQuestions, setFormQuestions] = useContext(FormQuestionsContext);
return (
<div>
<h1 className={styles["Header"]}>{title}</h1>
<div className={styles["MarkAllWrapper"]}>
<button className={styles["MarkAll"]}>
Mark all items as "Good" in this section
</button>
<br />
<button className={styles["MarkAll"]}>
Mark all items as "N/A" in this section
</button>
</div>
</div>
);
}
Section Header
的父級和表單代碼的 rest不包括我已經解釋的子單選按鈕,位於另一個組件LivingRoom.js
客廳.js
import { FormQuestionsContext, FormAnswersContext } from "../../Store";
function LivingRoomForm({ Name }) {
const [expanded, setExpanded] = useState(false);
const [formQuestions, setFormQuestions] = useContext(FormQuestionsContext);
const [formAnswers, setFormAnswers] = useContext(FormAnswersContext);
const array = formQuestions.living;
const onChange = (e, name) => {
const { value } = e.target;
setFormAnswers((state) => ({
...state,
[Name]: { ...state[Name], [name]: value },
}));
};
const handleOpen = () => {
setExpanded(!expanded);
};
return (
<div>
<Button
className={styles["CollapseBtn"]}
onClick={handleOpen}
style={{ marginBottom: "1rem", width: "100%" }}
>
<p>LIVING ROOM INSPECTION</p>
<FontAwesome
className="super-crazy-colors"
name="angle-up"
rotate={expanded ? null : 180}
size="lg"
style={{
marginTop: "5px",
textShadow: "0 1px 0 rgba(0, 0, 0, 0.1)",
}}
/>
</Button>
<Collapse className={styles["Collapse"]} isOpen={expanded}>
<Card>
<CardBody>
{array ? (
<div>
<SectionHeader title="Living Room Inspection" name={Name} />
<div
className={styles["LivingRoomFormWrapper"]}
id="living-room-form"
>
{array.map((question, index) => {
const selected =
formAnswers[Name] && formAnswers[Name][question]
? formAnswers[Name][question]
: "";
return (
<div className={styles["CheckboxWrapper"]} key={index}>
<h5>{question}</h5>
<Ratings
section={Name}
question={question}
onChange={onChange}
selected={selected}
/>
</div>
);
})}
</div>
<br />
<ImageUploader name="living" title={"Living Room"} />
</div>
) : (
<div></div>
)}
</CardBody>
</Card>
</Collapse>
</div>
);
}
如果有什么我想念的,請告訴我,我很樂意分享。 干杯
編輯:適用於需要單選按鈕組件的任何人。
Ratings.js
import React from "react";
import { FormGroup, CustomInput } from "reactstrap";
function Ratings({ selected, section, question, onChange }) {
return (
<div>
<FormGroup>
<div>
<CustomInput
checked={selected === "Good"}
onChange={(e) => onChange(e, question)}
type="radio"
id={`${section}_${question}_Good`}
value="Good"
label="Good"
/>
<CustomInput
checked={selected === "Fair"}
onChange={(e) => onChange(e, question)}
type="radio"
id={`${section}_${question}_Fair`}
value="Fair"
label="Fair"
/>
<CustomInput
checked={selected === "Poor"}
onChange={(e) => onChange(e, question)}
type="radio"
id={`${section}_${question}_Poor`}
value="Poor"
label="Poor"
/>
<CustomInput
checked={selected === "N/A"}
onChange={(e) => onChange(e, question)}
type="radio"
id={`${section}_${question}_NA`}
value="N/A"
label="N/A"
/>
</div>
</FormGroup>
</div>
);
}
我不完全理解你的問題,很抱歉,但我認為這會對你有所幫助。 這是使用反應的單選按鈕的實現 -
class App extends React.Component {
constructor(props) {
super(props);
this.state = {};
}
handleChange = e => {
const { name, value } = e.target;
this.setState({
[name]: value
});
};
render() {
return (
<div className="radio-buttons">
Windows
<input
id="windows"
value="windows"
name="platform"
type="radio"
onChange={this.handleChange}
/>
Mac
<input
id="mac"
value="mac"
name="platform"
type="radio"
onChange={this.handleChange}
/>
Linux
<input
id="linux"
value="linux"
name="platform"
type="radio"
onChange={this.handleChange}
/>
</div>
);
}
}
經過幾次嘗試,我能夠找出解決此問題的方法。
這里的關鍵是想辦法收集每個問題,以便在設置 state 時將其用作關鍵。 由於我的問題存儲在 ContextAPI 中,因此我能夠像這樣將它們拉出來......
這可能不是最好的解決方案,但它對我有用。
const setStateGood = () => {
formQuestions[name].map((question) => {
setFormAnswers((state) => ({
...state,
[name]: { ...state[name], [question]: "Good" },
}));
});
};
const setStateNA = () => {
formQuestions[name].map((question) => {
setFormAnswers((state) => ({
...state,
[name]: { ...state[name], [question]: "N/A" },
}));
});
};
我能夠通過每個問題 map ,因為name
正在通過道具是實際 object 中的一個鍵, formQuestions[name]
。 因為我正在映射每個問題,所以我可以將該問題設置為一個鍵,並將每個問題的新 state 返回到我想要的任何問題。
但是,如果我要創建一個onClick={setState('Good')}
,React 不喜歡這樣,它會創建一個無限循環。 如果我找到一個,我會尋找更多的解決方案並更新這篇文章。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.