【问题标题】:React native Unable to render the page with force update or set stateReact native 无法通过强制更新或设置状态来呈现页面
【发布时间】:2018-08-12 04:40:22
【问题描述】:
class Wait extends Component{

constructor(props) {
  super(props);
  this.state = { fetchingData: true, data: [], check: ''}
  this.forceUpdateHandler.bind(this);
  }

getData = async() => {
  try {
    data = await AsyncStorage.getItem('restaurants');
    if (data != null) {
      this.setState({fetchingData: false , data: JSON.parse(data)})
    }
  } catch(error){
     console.log(error)
  }
}

forceUpdateHandler(){
    this.forceUpdate();
};

componentDidMount(){
  this.getData();
}

renderRestaurant(){
  return this.state.data.map((item) => {
    return (
    <View style ={{marginTop: 20, backgroundColor: 'red', marginTop: 20 }}>
      <Text> {item.name} </Text>
      <Text> {item.time} </Text>
      <Text> {item.wait} </Text>
      <Text> {item.people} </Text>
      <Button title = 'cancel' onPress = { async () => {
        let data = await AsyncStorage.getItem('restaurants');
        let temp = JSON.parse(data)
        let i = -1
        temp.map((value, index) => {
          if (value.name == item.name){
            i = index;
          }
        })
        if (i > -1){
          temp.splice(i, 1)
          await AsyncStorage.setItem('restaurants', JSON.stringify(temp))
        }
        this.forceUpdateHandler()         // First way
        this.forceUpdate()                // Second way
        this.setState({check: 'checked'})   // Third way
      }
      }
      />
    </View>
  )
})
}

render(){
  const { navigate } = this.props.navigation;
  const { navigation } = this.props;

  return (
    <View style={{width:200, height:200, justifyContent:'center', alignItems:'center', }}>
          {this.state.fetchingData ? null : this.renderRestaurant()}
    </View>
  )
}
}

每次单击按钮后,我都会尝试重新呈现页面。单击按钮后,它会访问 AsyncStorage 并删除数组中的相应元素,然后使用新数组更新 AsyncStorage 并重新渲染页面。

我尝试了以下方法:

1) call forUpdate directly after the update of the AsyncStorage
2) define the forceUpdateHandler function and bind it with this
3) call this.setState after the update of the AsyncStorage

但以上选项都不会重新呈现页面。有人可以帮忙解决吗?一个例子会很棒!提前致谢。

【问题讨论】:

    标签: react-native asyncstorage rerender


    【解决方案1】:

    答案很简单。它不会重新渲染,因为它没有可重新渲染的内容。它调用渲染器,检查渲染器中的每个组件是否用于渲染它的数据已更改,并在需要时渲染它们。如果您查看您的代码,您会看到按下按钮时,您将新数据保存在异步存储中。但是,您的渲染使用this.state.data 来渲染项目。问题是您永远不会使用新数据更新组件的状态。

    当然,您可以使用this.setState({check: 'checked'}),但渲染中没有任何东西在使用它。所以更新 UI 是没有意义的。

    解决此问题的一种简单方法是在按钮 onPress 的末尾调用 this.getData()。这样,您将更新数据状态,从而更新您的 UI。

    【讨论】:

      【解决方案2】:
      1. 获取更新的餐厅列表 {删除所选餐厅}
      2. 已将更新的列表存储到 Asyncstorage。
      3. 从 asyncStorage 获取更新的列表并设置状态。

       storeData = async (restaurants) => {
          try {
           await AsyncStorage.setItem('restaurants', JSON.stringify(restaurants))
          } catch (error) {
            console.log("Error", error);
          }
        }
      
      
      renderRestaurant(){
            return this.state.data.map((item, index, restaurants) => {
              return (
                <View key={index}>
                  <Text> {item.name} </Text>
                  <Text> {item.time} </Text>
                  <Button 
                    title = 'cancel' 
                    onPress = {() => {
                      let restaurantListWithoutCurrentRestaurant = restaurants.filter((restaurant)=> restaurant.name !== item.name);
                      this.storeData(restaurantListWithoutCurrentRestaurant);
                      this.getData();       
                  }}/>
                </View>
              )
            })
          }

      我想这会解决你的问题。

      【讨论】:

        猜你喜欢
        • 2016-11-09
        • 2022-01-22
        • 1970-01-01
        • 2021-06-03
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2019-12-04
        • 2021-05-17
        相关资源
        最近更新 更多