在React中为对象数组设置状态

时间:2018-12-10 17:37:16

标签: arrays reactjs

我是React的新手,无法设置对象数组的状态。我希望每个对象都能够分别反映和“单击”状态。下面是我的代码。

const pictures = [
     {
            photo: 'https://cdn.images.dailystar.co.uk/dynamic/1/photos/755000/620x/cristiano-ronaldo-net-worth-how-much-madrid-player-worth-695569.jpg?r=5c053f491050f',
            id: 0,
            clicked: false
        }, {
            photo: 'https://www.tsn.ca/polopoly_fs/1.912227!/fileimage/httpImage/image.jpg_gen/derivatives/landscape_620/antoine-griezmann.jpg',
            id: 1,
            clicked: false
        }, {
            photo: 'https://e00-marca.uecdn.es/assets/multimedia/imagenes/2018/02/03/15176565269601.jpg',
            id: 2,
            clicked: false
        }, {
            photo: 'https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcTqa94bKUtifeRx2kxVEZFgTNx3JjEgD1ymNqRP8k8Au9zmLZiz',
            id: 3,
            clicked: false
        },
]

export default class picRender extends Component {

    state = {
        clicked: false
    }

    handleClick = (event) => {
        if (this.state.clicked === false) {
            this.setState({clicked: true});
            console.log(event.target.getAttribute('data-key') + " state changed to clicked");
            console.log(this.state.clicked);
        } else if (this.state.clicked === true) {
            console.log('THIS HAS BEEN CLICKED!');
        }
    }

    render() {
        return pictures.map(pic => <img
            className="photo"
            data-key={pic.photo}
            key={pic.id}
            src={pic.photo}
            onClick={this
            .handleClick.bind(this)}></img>);
    }
}

每次单击其中一张图片时,整个阵列的状态都会更改为“ true”。我不确定如何反映每个对象的状态变化。

2 个答案:

答案 0 :(得分:1)

之所以只得到truefalse,是因为当前您仅在状态中存储一个变量clicked。 如果要单独处理每张图片的状态,则应该有一个处于状态的数组来管理每张图片的单击状态。为此,最简单的方法就是将初始状态设置为等于图片数组

state = {
        pictures: [
     {
        photo: 'https://cdn.images.dailystar.co.uk/dynamic/1/photos/755000/620x/cristiano-ronaldo-net-worth-how-much-madrid-player-worth-695569.jpg?r=5c053f491050f',
        id: 0,
        clicked: false
    }, {
        photo: 'https://www.tsn.ca/polopoly_fs/1.912227!/fileimage/httpImage/image.jpg_gen/derivatives/landscape_620/antoine-griezmann.jpg',
        id: 1,
        clicked: false
    }, {
        photo: 'https://e00-marca.uecdn.es/assets/multimedia/imagenes/2018/02/03/15176565269601.jpg',
        id: 2,
        clicked: false
    }, {
        photo: 'https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcTqa94bKUtifeRx2kxVEZFgTNx3JjEgD1ymNqRP8k8Au9zmLZiz',
        id: 3,
        clicked: false
    },

   ],
 }

现在在您的点击事件中,您需要确定点击了哪张图片,然后更改该特定图片的点击状态。

执行此操作的一种方法是将图像ID照这样传递给handleClick

render() {
        return pictures.map(pic => <img
            className="photo"
            data-key={pic.photo}
            key={pic.id}
            src={pic.photo}
            onClick={this
            .handleClick.bind(this, pic.id)}></img>);
    }

,然后在您的handleClick中,修改ID传入的图片的点击状态

handleClick = (event, id) => {
        //find the picture using the id and change its clicked state
    }

答案 1 :(得分:0)

首先,组件名称必须以大写字母开头吗? PicRender

在JSX中,小写标签名称被认为是HTML标签

一种简单的解决方案,使数组具有所有单击的ID

const pictures = [
  {
    photo: 'https://cdn.images.dailystar.co.uk/dynamic/1/photos/755000/620x/cristiano-ronaldo-net-worth-how-much-madrid-player-worth-695569.jpg?r=5c053f491050f',
    id: 0,
    clicked: false
  }, {
    photo: 'https://www.tsn.ca/polopoly_fs/1.912227!/fileimage/httpImage/image.jpg_gen/derivatives/landscape_620/antoine-griezmann.jpg',
    id: 1,
    clicked: false
  }, {
    photo: 'https://e00-marca.uecdn.es/assets/multimedia/imagenes/2018/02/03/15176565269601.jpg',
    id: 2,
    clicked: false
  }, {
    photo: 'https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcTqa94bKUtifeRx2kxVEZFgTNx3JjEgD1ymNqRP8k8Au9zmLZiz',
    id: 3,
    clicked: false
  },
]

 class PicRender extends React.Component {

  state = {
    clicked: []
  }

  handleClick = (pic) => {
    if(this.state.clicked.indexOf(pic.id) === -1){
      this.setState((prevState) => ({ clicked: [...prevState.clicked, pic.id] })) // added the id to clicked array
    }else{ // remove the id from clicked array
      this.setState((prevState) => ({ clicked: prevState.clicked.filter(row => row !== pic.id) })) 
    }
  }

  render() {
    return pictures.map(pic => <img
      className="photo"
      data-key={pic.photo}
      style={this.state.clicked.indexOf(pic.id) !== -1 ? {border: '5px solid green'} : {}}
      key={pic.id}
      src={pic.photo}
      onClick={this.handleClick.bind(this, pic)}></img>);
  }
}

ReactDOM.render(<PicRender />, document.getElementById("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>
<div id='app'></div>