React this.state is null



我尝试在 react中做天气应用程序,但是当我在我的 const API 中添加${this.state.latitude}时,我替换了 null。但是当我尝试在render()中显示this.state.latitude时,我有一个值。怎么了?

export class TodayWeather extends React.Component {
    constructor(props) {
        super(props);
        this.state = {
            latitude: "",
            longitude: "",
        };
    }
    getMyLocation =() => {
        const location = navigator.geolocation;
        if (location) {
            location.getCurrentPosition((position) => {
                this.setState({
                    latitude: position.coords.latitude,
                    longitude: position.coords.longitude,
                })
            },)}
    };
    getWeather = () => {
        this.getMyLocation();
        const API = `http://api.openweathermap.org/data/2.5/forecast?lat=${this.state.latitude}&lon=139&appid=${apiKey}`;
        fetch(API)
            .then(response => {
                if (response.ok) {
                    return response
                }
                throw Error("")
            })
            .then(response => response.json())
            .then(data => {
                const time = new Date().toLocaleString();
                this.setState({
                })
            })})
    };
    componentDidMount() {
        this.getWeather();
    }
    render(){
            return (
            <div className="App">
                <Result className="result" weather={this.state}/>
                <p> {this.state.latitude} </p>
            </div>
        );
    }
}

预期的执行顺序为:

  1. this.getMyLocation()latitudelongitude设置为状态。
  2. this.getWeather() 它使用状态变量发出 xhr 请求(再次异步(。

this.setState也是异步的。因此,当设置状态变量时,this.getWeather()已经开始执行,因此它返回 null 并且获取请求失败。因此,当设置状态变量时,它会触发重新渲染,这就是为什么它确实出现在render中。

对此的解决方案是在setState中使用回调。我做了一些小的修改。

我在componentDidMount上打电话给this.getMyLocation()

  componentDidMount() {
    this.getMyLocation();
  }

其中我使用回调并调用修改后的this.getWeather

this.setState(
          {
            latitude: position.coords.latitude,
            longitude: position.coords.longitude
          },
          this.getWeather
);

它不再在开始时调用this.getMyLocation()

除此之外,一个明显的缺陷是,在获取完成后,您没有向setState传递任何内容,大概是您获得的 json 数据。

      .then((data) => {
        const time = new Date().toLocaleString();
        this.setState({
          // Something needs to come here, possibly:
          data
        });
      });

完整代码:

export default class TodayWeather extends Component {
  constructor(props) {
    super(props);
    this.state = {
      latitude: '',
      longitude: ''
    };
  }
  getMyLocation = () => {
    const location = navigator.geolocation;
    if (location) {
      location.getCurrentPosition((position) => {
        this.setState(
          {
            latitude: position.coords.latitude,
            longitude: position.coords.longitude
          },
          this.getWeather
        );
      });
    }
  };
  getWeather = () => {
    const API = `http://api.openweathermap.org/data/2.5/forecast?lat=${
      this.state.latitude
    }&lon=139&appid=${apiKey}`;
    fetch(API)
      .then((response) => {
        if (response.ok) {
          return response;
        }
        throw Error('');
      })
      .then((response) => response.json())
      .then((data) => {
        const time = new Date().toLocaleString();
        this.setState({
          // Something needs to come here
          data
        });
      });
  };
  componentDidMount() {
    this.getMyLocation();
  }
  render() {
    return (
      <div className="App">
        <Result className="result" weather={this.state} />
        <p> {this.state.latitude} </p>
      </div>
    );
  }
}

试试这个..但是代码看起来很混乱

export default class TodayWeather extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      latitude: '',
      longitude: ''
    };
  }
  getMyLocation = (getData) => {
    const location = navigator.geolocation;
    if (location) {
      location.getCurrentPosition((position) => {
        getData(position);
      });
    }
  };
  getWeather = () => {
    const getData = (position) => {
      this.setState({
        latitude: position.coords.latitude,
        longitude: position.coords.longitude
      });
      const API = `http://api.openweathermap.org/data/2.5/forecast?lat=${
        position.coords.latitude
      }&lon=139&appid=${apiKey}`;
      fetch(API)
        .then((response) => {
          if (response.ok) {
            return response;
          }
          throw Error('');
        })
        .then((response) => response.json())
        .then((data) => {
          const time = new Date().toLocaleString();
          this.setState({ time });
        });
    };
    this.getMyLocation(getData);
  };
  componentDidMount() {
    this.getWeather();
  }
  render() {
    return (
      <div className="App">
        <Result className="result" weather={this.state} />
        <p> {this.state.latitude} </p>
      </div>
    );
  }
}

相关内容

最新更新