Как установить State в дочернем компоненте, когда дочерняя функция вызывается из родительского компонента в ReactJS

Я хочу вызвать дочернюю функцию из родительского компонента, поэтому я нашел здесь вопрос

Вызовите дочерний метод от родителя

Поэтому я использовал этот способ, чтобы назвать его (из 1-го ответа и 2-го подхода).

Теперь вопрос, как установить состояние у ребенка getAlert функция

class Parent extends Component {
  render() {
    return (
      <div>
        <Child ref={instance => { this.child = instance; }} />
        <button onClick={() => { this.child.getAlert(); }}>Click</button>
      </div>
    );
  }
}

class Child extends Component {
  constructor(){
     super();
     this.state = {message:""};
  }

  getAlert() {
    alert('clicked');
    //HERE I NEED TO SETSTATE 
  }

  render() {
    return (
      {this.state.message!=""?(
         <h1>{this.state.message}</h1>

      ):(

      <h1>Hello</h1>

      )}
    );
  }
}

В функции getAlert child мне нужно установить setState, но я не смог этого сделать. Пожалуйста, предоставьте любое решение

2 ответа

Решение

Кажется, проблема в том, что при звонке setState внутри функции getAlert ребенка, this.setState придет неопределенным. Это происходит потому, что this внутри вашей функции getAlert не ссылается на контекст компонента React, и для компонента определено setState. Вы можете решить эту проблему, связав getAlert функция.

Вы можете сделать это двумя способами.

Первое: использование .bind(this) в конструкторе

class Child extends Component {

  constructor() {
     super();
     this.getAlert = this.getAlert.bind(this);
  }
  getAlert() {
    alert('clicked');
    //HERE I NEED TO SETSTATE 
  }

  render() {
    return (
      <h1>Hello</h1>
    );
  }
}

Второе: использовать функцию стрелки

getAlert = ()  => {
    alert('clicked');
    //HERE I NEED TO SETSTATE 
  }

Проверьте этот ответ на Почему мы должны связывать функции React

Проверьте рабочий фрагмент

class Parent extends React.Component {
  render() {
    return (
      <div>
        <Child ref={instance => { this.child = instance; }} />
        <button onClick={() => { this.child.getAlert(); }}>Click</button>
      </div>
    );
  }
}

class Child extends React.Component {
  constructor(){
     super();
     this.state = {message:""};
  }

  getAlert = () => {
    alert('clicked');
    this.setState({message: "somemessage"});
  }

  render() {
    return (
      <div>{this.state.message!=""?(
         <h1>{this.state.message}</h1>

      ):(

      <h1>Hello</h1>

      )}</div>
    );
  }
}

ReactDOM.render(<Parent/>, 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"/>

class Parent extends React.Component {
  render() {
    return (
      <div>
        <Child ref={instance => { this.child = instance; }} />
        <button onClick={() => { this.child.getAlert(); }}>Click</button>
      </div>
    );
  }
}

class Child extends React.Component {
  constructor(){
  super()
  this.state = {
    message: 'google'
  }
  this.getAlert = this.getAlert.bind(this)
  }
    
  getAlert() {
    alert('clicked');
    this.setState ({
      message: 'yahoo'
    }, () => {
      console.log(this.state.message) //the state value will be printed
    }); 
  }

  render() {
  console.log(this.state.message)
    return (
      <h1>Hello {this.state.message}</h1>
    );
  }
}

ReactDOM.render(
  <Parent />,
  document.getElementById('container')
);
<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="container"></div>

вы привязали метод getAlert() к области видимости класса ie). 'этот'. Я добавил пример кода.. пожалуйста, проверьте

Другие вопросы по тегам