小编典典

更改为反应状态不会更新功能组件中的显示

reactjs

我创建了一个简单的2组件应用程序,其中动物的名字显示了动物的图标,以概括我在更复杂的应用程序中遇到的问题。

一旦选择了一个随机动物并将其合并到中state,该Display组件应该重新渲染,并且该组件也animalIcon应该更新,因为state正在向下传递props(或者我认为)。

取而代之的是,我们被卡在任何第一个动物(随机选择)的图标上。

我真的很想知道为什么图标不会更新,因为我认为state更改时间后,它将重新呈现使用该信息的Display组件(在本例中为组件),并在此console.log(animalIcon)正确显示给我。每次重新渲染Display组件时,animalIcon即已正确分配了正确的元素/图标。

不改变的唯一的事情就是输出{animalIcon}return该声明Display的组成部分。

class App extends React.Component {

  constructor(props) {

    super(props);

    this.state = {

      currentAnimal: ''

    }

    this.getAnimal = this.getAnimal.bind(this);

  }



  getAnimal() {



    function getRandomAnimal(arr) {

      function getRandomIndex(min, max) {

        min = Math.ceil(min);

        max = Math.floor(max);

        return Math.floor(Math.random() * (max - min + 1)) + min;

      }



      return arr[getRandomIndex(0, arr.length - 1)];

    }



      const allAnimals = ['cat', 'dog', 'mouse'];

      const chosenAnimal = getRandomAnimal(allAnimals);

      this.setState({currentAnimal: chosenAnimal});

  }



  render() {

    return(

      <Display getAnimal={this.getAnimal} animal={this.state.currentAnimal}/>

    )

  }

}



function Display (props) {

  const icons = {

    cat: <i class="fas fa-cat"></i>,

    dog: <i class="fas fa-dog"></i>,

    mouse: <i class="fas fa-mouse-pointer"></i>,

  }



  let animalIcon = icons[props.animal.toLowerCase()];

  console.log(animalIcon);



  return (

    <div>

      <h1>{props.animal} looks like {animalIcon}</h1>

      <button onClick={props.getAnimal}>Get New Animal</button>

    </div>

  )

}



ReactDOM.render(<App />, document.querySelector('.root'));


<script src="https://use.fontawesome.com/releases/v5.5.0/js/all.js"></script>

<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 class="root"></div>

阅读 229

收藏
2020-07-22

共1个答案

小编典典

您可以包装animalIconwith属性key,在传递道具时,它似乎无法正确更新。如果动物名称发生更改,这将告诉用户更新图标的反应。

<span key={props.animal}>{
      animalIcon
    }</span>



class App extends React.Component {

  constructor(props) {

    super(props);

    this.state = {

      currentAnimal: ''

    }

    this.getAnimal = this.getAnimal.bind(this);

  }



  getAnimal() {



    function getRandomAnimal(arr) {

      function getRandomIndex(min, max) {

        min = Math.ceil(min);

        max = Math.floor(max);

        return Math.floor(Math.random() * (max - min + 1)) + min;

      }



      return arr[getRandomIndex(0, arr.length - 1)];

    }



    const allAnimals = ['cat', 'dog', 'mouse'];

    const chosenAnimal = getRandomAnimal(allAnimals);

    this.setState({

      currentAnimal: chosenAnimal

    });

  }



  render() {

    return ( <

      Display getAnimal = {

        this.getAnimal

      }

      animal = {

        this.state.currentAnimal

      }

      />

    )

  }

}



function Display(props) {

  const icons = {

    cat: < i class = "fas fa-cat" > < /i>,

    dog: < i class = "fas fa-dog" > < /i>,

    mouse: < i class = "fas fa-mouse-pointer" > < /i>,

  }



  let animalIcon = icons[props.animal.toLowerCase()];

  console.log(props.animal);



  return ( <div ><h1> {

      props.animal

    }

    looks like <span key={props.animal}>{

      animalIcon

    }</span> < /h1> <

    button onClick = {

      props.getAnimal

    } > Get New Animal < /button> <

    /div>

  )

}



ReactDOM.render( < App / > , document.querySelector('.root'));


<script src="https://use.fontawesome.com/releases/v5.5.0/js/all.js"></script>

<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 class="root"></div>
2020-07-22