a7dc
a7dc

Reputation: 3416

How to iterate over an array that's inside an object in React JS

Imagine I have an array of objects like so:

const chefs = [
  {
    key: 1,
    images: ['http://lorempixel.com/400/400/sports/', 'http://lorempixel.com/400/400/abstract/', 'http://lorempixel.com/400/400/animals/', 'http://lorempixel.com/400/400/city/', 'http://lorempixel.com/400/400/people/']
  }
]

And I'm wanting to assign each of the images inside of the images array to a React component called CarrouselItem using props:

class CarrouselItem extends React.Component {
  render() {

    return (
      <div>
        <img src={this.props.imageUrl} />
      </div>
    )
  }
}

Which is then placed into a parent component called Carrousel, where I loop over the object and return the images inside, to be placed inside of the CarrouselItem component:

class Carrousel extends React.Component {
  render() {
    return (
      <div>
        <h4>Slide image</h4>
        {chefs.map((chef, index) => {
          return <CarrouselItem imageUrl={chef.images[index]} />
        })}
      </div>
    )
  }
}

What I expect to happen

The map function should iterate over all of the objects (in this case, just one of them) which then creates X number of CarrouselItem components, each with an <img> that's taken from the images array.

What actually happens

Unfortunately I'm only getting the first item in the array (in this case, 'http://lorempixel.com/400/400/sports/').

Could someone be so kind to explain where I'm going wrong here?

Link to CodePen.

Upvotes: 2

Views: 5473

Answers (3)

John Ruddell
John Ruddell

Reputation: 25842

The reason why its only giving you one item, is because you are mapping over a chef and not his images.. so you only iterate once. Instead you just want to map over the images like so chefs.images.map

const chefs = [
  {
    key: 1,
    images: ['http://lorempixel.com/400/400/sports/', 'http://lorempixel.com/400/400/abstract/', 'http://lorempixel.com/400/400/animals/', 'http://lorempixel.com/400/400/city/', 'http://lorempixel.com/400/400/people/']
  }
]

class Carrousel extends React.Component {
  render() {
    const elems = [];
    chefs.forEach( (chef) => {
        chef && chef.images.forEach( (image, j) => {
            elems.push(<CarrouselItem imageUrl={image} key={i} />)
        })
    })
    return (
      <div>
        <h4>Slide image</h4>
        {elems}
      </div>
    )
  }
}

I would recommend you make a chef component that renders things like the chefs information, name, age, location, restaurant... etc.. and renders a carousel for each chef with their images.

Upvotes: 2

Anurag Awasthi
Anurag Awasthi

Reputation: 6233

First you need to iterate over chefs array, and then individual images.

const chefs = [
  {
    key: 1,
    images: ['http://lorempixel.com/400/400/sports/', 'http://lorempixel.com/400/400/abstract/', 'http://lorempixel.com/400/400/animals/', 'http://lorempixel.com/400/400/city/', 'http://lorempixel.com/400/400/people/']
  }
]

class Carrousel extends React.Component {
  render() {
    return (
      <div>
        <h4>Slide image</h4>
        {chefs.map((chef, i)=>(
          <div key={i}>
            {chef.images.map((image,index)=>(
              <CarrouselItem imageUrl={image} key={index} />
            ))}
          </div>  
        ))}
        ))
      </div>
    )
  }
}

class CarrouselItem extends React.Component {
  render() {

    return (
      <div>
        <img src={this.props.imageUrl} />
      </div>
    )
  }
}

ReactDOM.render(<Carrousel />,document.getElementById("app"))
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script>
<div id="app"></div>

Upvotes: 6

owais
owais

Reputation: 4922

actually its picking chef object index which is one so you getting first instead use chefs.images.map

{chefs[0].images.map((image, index) => {
          return <CarrouselItem imageUrl={image} />
        })}

Upvotes: 1

Related Questions