Assume I have a JSON-file that looks like this one:
{
"data": [
{
"question": "What's 1 1",
"answers": [
{
"text": "3",
"correct": false
},
{
"text": "2",
"correct": true
}
]
}
]
}
In my code I am iterating over these answers and rendering a button for each. Each button also receives a click-handler like beneath. What I'd like to happen when you click a button, is that if it's the correct one, I should assign it a (correct) class. But if it's the wrong one, I will assign it another (wrong) class, but still show which was the correct one.
const handleClick = answer => {
// How would I implement this logic?
}
const App = ({ data }) => {
return (
<div>
{data.answers.map(answer => (
<button onClick={() => handleClick(answer)}>{answer.text}</button>
))}
</div>
)
}
I tried to create a state variable to the button that was clicked. Then compare it against the parameter that was passed through the onclick handler.
CodePudding user response:
For Dynamic classname try this,
const App = ({ data }) => {
return (
<div>
{data.answers.map(answer => (
<button classname={answer.correct ? 'correct-class' : 'wrong-class'`} onClick={() => handleClick(answer)}>{answer.text}</button>
))}
</div>
)}
CodePudding user response:
You can maintain a selectedAnswer
state that you set once you select an answer. You can then decide to show the correct
class when mapping if the current answer's .correct
property is true
and the incorrect
class if it is false
, this class is stord in classType
below. Since you only want to show these classes once you've selected an answer, you can conditionally add the class if:
- You have selected an answer (ie
selectedAnnswer
has a value)
AND
- Add the class if the currently mapped answer is correct OR the current answer is your selected answer
See example below:
const {useState} = React;
const App = ({ data }) => {
const [selectedAnswer, setSelectedAnswer] = useState();
const handleClick = answer => {
setSelectedAnswer(answer);
}
return (
<div>
{data.answers.map(answer => {
const classType = answer.correct ? "correct" : "incorrect";
const showClass = selectedAnswer && (answer.correct || selectedAnswer === answer);
return <button
key={answer.text}
className={showClass && classType}
onClick={() => handleClick(answer)}>{answer.text}</button>
})}
</div>
);
}
const obj = { "data": [ { "question": "What's 1 1", "answers": [ { "text": "3", "correct": false }, { "text": "2", "correct": true }, { "text": "1", "correct": false } ] } ] }
ReactDOM.createRoot(document.body).render(<App data={obj.data[0]} />);
.correct {background: lime;}
.incorrect {background: red;}
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/18.2.0/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/18.2.0/umd/react-dom.production.min.js"></script>
CodePudding user response:
const App = ({ data }) => {
return (
<div>
{data.answers.map(answer => (
<button
className={`${answer.correct ? "correct" : "wrong"} other
classes `}
onClick={() => handleClick(answer)}>{answer.text}
</button>
))}
</div>
)
}