2

I'm having an issue when trying to increment through the index of an array in React. There are three items in the array, which is called 'projects', and I'm using a separate variable to set state of the index.

const [projects, setProjects] = useState([
  {
    title: 'hello'
  },
  {
    title: 'hi'
  },
  {
    title: 'bye'
  },

])

const [index, setIndex] = useState({
  i: 0

})

I have a JSX button element, which has an onClick event handler function. The purpose of this function is to increment through the index of the array and display its data on screen.

function handleClick(e) {
  if (index.i > 2){
    index.i = 2
  } else {
    setIndex({i: index.i + 1 })
  }
  e.preventDefault() 
}

This function works fine, but only until index.i reaches 2. If it goes above 2 the page breaks because there are only 3 items in the array. Is there any reason why my if statement in the function isn't working? I've tried variations of it, using index.i === 0 instead of >2, but this still doesn't work.

JSX -

<div>{projects[index.i].title}</div>
<button onClick={handleClick}></button>

Please can someone help?! Thanks

1
  • Don't mutate state directly; use the hook setters in order to do it. Commented Jan 31, 2020 at 15:55

3 Answers 3

3

Use the length of the projects

First off index should be an int not an object.

const [index, setIndex] = useState(0);

No need for bad syntax like index.i thats a code smell.

Instead of a static number try project length - 1 since index is counting from 0 and length counts each item.

if (index < projects.length - 1){setIndex(index + 1 )}
Sign up to request clarification or add additional context in comments.

1 Comment

This is good advice. Using the array length is more flexible than hard coded values.
1

I believe it's because the index is already greater than 2 when your if statement is true. Your array index is [0, 1, 2] so an index of 3 breaks it.

Try this code instead:

function handleClick(e) {
  e.preventDefault()
  if (index.i === (projects.length - 1)) return null

  setIndex({i: index.i + 1 })
}

Comments

1

Is there a reason why your index is an object ? It's harder to use, and I don't see the point here.
If not, your state should look like this :

const [projects, setProjects] = useState([
  {title: 'hello'},
  {title: 'hi'},
  {title: 'bye'},
])

const [index, setIndex] = useState(0)

And you will be able to work with it like this :

function handleClick(e) {
  e.preventDefault()
  setIndex((prevIndex) => {
    if (prevIndex >= 2)
        return 2
    else
        return prevIndex + 1
  })
}

2 Comments

No reason apart from the fact that I'm fairly new to this :). Thanks
This implementation is used on the standard react components (no hooks). You set the states in an object, and declare them as an array : this.state = {i: 0 blabla: false} & this.setState({i: 2, blabla: true}). With hooks, you juste have the useState and functions like above :)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.