简体   繁体   中英

How to manipulate the DOM inside of map function using onChange event on one of the checkboxes with react hooks

So first I import really simple "database" object from a different file which has a students array property in it. After that I map through the students array to display all of the students on the window object. All went well until I tried to dynamically change class name on one of the div tags inside of map function every time when state for status is changing to true I want to display information otherwise that div should stay invisible. After implementing the code below and trying to tick the box I am getting error "Cannot create property '0' on boolean 'true'". Please tell me what I am doing wrong. Thank You for Your interest in that case.

 import React,{ useState,useEffect } from 'react' import db from './db' import './App.css' const App = () => { const [status,setStatus] = useState(database.map((student) => { return student.isChecked })) return db.students.map(({name,id,email,isChecked}, index) => { return ( <form key={id} className='form'> <h2> {name} </h2> <select name='student_attendance' className='form__dropdown' defaultValue='present'> <option value='present'> present </option> <option value='absent'>absent</option> </select> <div> <label htmlFor={id}>Left early</label> <input type='checkbox' name='leftEarly' id={id} /> </div> <div> <label htmlFor={email}>Arrival late</label> <input type='checkbox' name='arrivalLate' id={email} onChange= {(event) => { setStatus(status => status[index] = event.currentTarget.checked ) }}/> </div> <div className={status[index] ? 'visible' : 'invisible'> <p>time: </p> </div> </form> ) }) } export default App 
 <script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.6.3/umd/react.production.min.js"></script> <script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.6.3/umd/react-dom.production.min.js"></script> 

The argument to setStatus should be either:

  • The new value for status

or

  • A function that takes a previous version of status and returns the new version

You are passing it a function that modifies the received value of status, and then returns a boolean value. So it appears that status is changing to that boolean value, and then the status[index] in your className expression is essentially evaluating true[0] , which results in the error.

To fix this, fix your use of the setStatus() function:

setStatus(status => [
    ...status.slice(0, index),     
    event.currentTarget.checked,
    ...status.slice(index + 1)
])

You may also want to try this, which doesn't rely on the event properties:

setStatus(status => [
    ...status.slice(0, index),     
    !status[index],
    ...status.slice(index + 1)
])

Or even this:

setStatus(status => 
    status.map((x, i) => (i === index) ? !x : x)
)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM