pkachu
pkachu

Reputation: 35

Issue in checkbox

Reactv18.2.0: Whenever the value is True the checkbox is checked but it cannot be unchecked(state changes as expected). However if the value is not true then checkbox can be checked/unchecked. I have used conditional rendering for displaying checked and unchecked input field. When looking from the inspect elements > components > i can see that the state is changing as expected. Below is agent.jsx code snippet with checkbox issue. The toggleShift function is passed from parent (agentlist.jsx) to child component in agent.jsx

agent.jsx //For single item in list

import axios from 'axios'
import React from 'react'
import { useState } from 'react'

const Agent = (props) => {
    const { agentemail, agentid,agentname,agentshift,toggleShift} = props
    const [isOnShift,setIsOnShift] = useState(agentshift)

    const handleCheckbox= async ()=>{
        try {
            const res = await axios.patch(`http://127.0.0.1:8000/api/setShift/${agentid}`, {"shift":agentshift})
            console.log(res)
            toggleShift(agentid)
        } catch (err) {
            console.log(err)
        }
           
    }
    
  return (
    <>
      <tr key={agentemail}>
      <td>{agentname}</td>
      <td>{agentemail}</td>
      <td>
       
           {  isOnShift === "OD" ?  <input type="checkbox"  onChange={handleCheckbox} checked  /> :  <input type="checkbox"   onChange={handleCheckbox} /> }

      </td>
      <td>{agentid}</td>
      <td>
            <select style={{fontSize: "medium"}}>
                <option value="0">0</option>
                <option value="1">1</option>
                <option>{agentbias}</option>
            </select>
       </td>
</tr>

    </>
  )
}

export default Agent

Agentlist.jsx

import {useEffect, useState } from 'react'
import CountT from './CountT'
import React from 'react'
import axios from 'axios'
import Agent from './Agent'

function Agentlist() {
  const [agents,setAgents] = useState([])
  useEffect(()=>{
    fetchAgents()
  },[])

  function toggleShift(id){

    const newAgentList=[...agents].map((a)=>{
       if (a.Aid===id) {
          if(a.Shift === "OD"){ 
              a.Shift="Off"
          } else if (a.Shift==="Off") {
              a.Shift="OD"
          } else {
          a.Shift="Off"
          }
       }
       return a   //modified agent and rest of agent obj is returned to newAgentlist
    })
    setAgents(newAgentList)
    console.log("newAgentList",newAgentList)
  }
  
  const fetchAgents = async ()=> {
    axios.get(`http://127.0.0.1:8000/api/list`).then((response)=>{setAgents(response.data)}).catch(error=>{console.log("Make sure the local fetcher service is up & running:",error)})
  }

  return (
    <>
    {  agents.length<1 && <article>Agent not running!</article>}
     <div className='grid'>
     <table style={{fontSize: "medium"}}>
     <thead>
     <tr>
      <th scope="col">Name</th>
      <th scope="col">Email</th>
      <th scope="col">Shift</th>
      <th scope="col">AgentID</th>
    </tr>
  </thead>
  <tbody >
    {agents.map((agnt)=>(
      <Agent key={agnt.Email} agentemail={agnt.Email} agentname={agnt.Name} agentid={agnt.Aid} agentshift={agnt.Shift} toggleShift={toggleShift} />
    ))}
  </tbody>
  </table>
     </div>
    <div className='grid' ><CountT/></div>
    </>
  )
}

export default Agentlist

Upvotes: 0

Views: 21

Answers (1)

ray
ray

Reputation: 27285

Don't conditionally render a different checkbox for the checked/unchecked states. Render one checkbox and set its checked attribute according to your condition:

<input
  type="checkbox"
  onChange={handleCheckbox}
  checked={isOnShift === "OD"}
/>

Upvotes: 1

Related Questions