Business
Jobs
  • About Us
  • Solutions
    • Job Postings
      Post your job and receive qualified candidates in 48h.
    • Candidate Assessments
      500+ technical and psychological tests, plus anti-fraud.
    • Headhunting
      Tailor-made executive search from start to finish.
    • Payroll + EOR
      Payroll dispersal and EOR across 15+ LATAM countries.
  • Pricing
  • Jobs

0

365
Views
REACT : getting error while re-rendering components using setState hook

I'm trying to change an inline style property of several items that have position info stored in a useState hook as well on the style property of each item rendered. I wanted to change the CSS value of all the items except the one I clicked on. I devised a function to do so, however when I try to update the CSS value using setState, the items don't re-render and I get an error saying "discs.map is not a function". Am I using the set state hook correctly? Should i be using the setState hook for a task like this i.e animating position of items?

// Main Component

function App() {
   const [discs, setDiscs] = useState([
      { id: 1, top: 100 },
      { id: 2, top: 200 },
      { id: 3, top: 300 },
      { id: 4, top: 400 },
      { id: 5, top: 500 },
      { id: 6, top: 600 },
      { id: 7, top: 700 },
      { id: 8, top: 800 },
      { id: 9, top: 900 },
      { id: 10, top: 1000 },
      { id: 11, top: 1100 },
      { id: 12, top: 1300 }
   ])

function enlargeDisc(e, num) {
      let t = e.target
      if (t.classList.contains('active')) {
         t.classList.remove('active')
         adjustDiscPos(num, true)
      } else {
         t.classList.add('active')
         adjustDiscPos(num, false)
      }
   }

   function adjustDiscPos(n, backToOriginal) {
      console.log(discs)
      discs.forEach((disc) => {
         if (disc.id < n) {
            setDiscs(prevState =>  backToOriginal ? prevState + 300 : prevState - 300)
         }
         if (disc.id > n) {
            setDiscs(prevState =>  backToOriginal ? prevState - 300 : prevState + 300)
         }
      })
   }

  return (
    <div className="App">
      <div className="container">
         <div className="wrapper" style={{bottom: scroll}}>
            {discs.map((item) => (
               <div className ='disc' key={item.id} data-index={item.id} style={{top: item.top + 'px'}} onClick={(e)=> enlargeDisc(e, item.id)} ></div>
            ))}
        </div>
      </div>
    </div>
  );
}

export default App;

CSS

.disc {
   position: absolute;
   transform:
      translate(-50%, -50%) rotateX(90deg) scale(1);
   width: 10em;
   height: 10em;
   transform-style: preserve-3d;
   cursor: pointer;
   background-image:
   radial-gradient(rgba(0, 0, 0, 0), rgb(22, 22, 22) 95%), 
   url('./img/cd3.png');
   background-size: 100% 100%;
   transition: all 0.5s ease-in-out; 
}

.disc.active {
   transform:
   translate(-50%, -50%) rotateX(0deg) scale(1.5);
}
about 4 years ago · Juan Pablo Isaza
3 answers
Answer question

0

I am assuming here that it is the value of top you wish to manipulate. I am also assuming that you wish to leave the disc with id equal to n as it is. Correct me if I'm wrong.

What you need to do is to create a temporary array and add the new values to that array. Then, when that is done, you call setDiscs with the temporary array as an argument.

let tmp_discs = [];

discs.forEach((disc) => {
  if (disc.id < n) {
    tmp_discs[disc.id] = backToOriginal ? disc.top + 300 : disc.top - 300;
  } else if (disc.id > n) {
    tmp_discs[disc.id] = backToOriginal ? disc.top - 300 : disc.top + 300;
  } else {
    tmp_discs[disc.id] = disc.top;
  }
})

setDiscs(tmp_discs);
about 4 years ago · Juan Pablo Isaza Report

0

In adjustDiscPos you are calling setDiscs with the value of a subtraction of an array and 300 prevState - 300.

This will push NaN to discs and hence your error.

You should compute a new array in your forEach and then call setDiscs only once.

about 4 years ago · Juan Pablo Isaza Report

0

Building up on what Radu Dita said

In adjustDiscPos you are calling setDiscs with the value of a subtraction of an array and 300 prevState - 300. This will push NaN to discs and hence your error. You should compute a new array in your forEach and then call setDiscs only once.

What this means is that instead of using a forEach and do setDiscs for each item in the array, you're supposed to use setDiscs once (prevState is the reference to the current discs value), and do your arrayu operation on it through map or something.

function adjustDiscPos(n, backToOriginal) {
      console.log(discs)
      setDiscs(prevState => prevState.map(disc => {
         const offset = backToOriginal ? 300 : -300;
         return { id: disc.id, top: disc.id < n ? disc.top + offset : disc.top - offset };
      })

Just make sure to remember not to mutate prevState directly either since it is a reference to current state variable, but rather to use some array function which returns a new value.

about 4 years ago · Juan Pablo Isaza Report
Answer question
Find remote jobs

Discover the new way to find a job!

Top jobs
Top job categories
Business
Post vacancy Pricing Sales
Legal
Terms and conditions Privacy policy
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Show me some job opportunities
There's an error!