我有一个屏幕,应该显示搜索结果。所以,我在render()中创建了我的fetch。正如在this stackoverflow response中描述的那样,我将我的响应推送到一个数组中。在控制台面板中,结果数组在几秒钟后加载,但在我的屏幕中,结果数组仍为空。
这是我的渲染功能
render() {
let result = [];
let endPoint = this.props.navigation.getParam('endPoint', '');
fetch(endPoint, {
method: "GET",
headers: null,
}).then(response => response.json())
.then(response => {
let list = response;
for (let i = 0; i < list.length; i++) {
result.push(
<View key={i} style={styles.item}>
<View>
<View style={styles.imageContainer}>
<Image style={styles.imageItem} resizeMode="cover"
source={{uri: list[i].img}}/>
</View>
</View>
<View style={styles.inlineDetails}>
<Text style={styles.innerTitle}>
{list[i].lieugeo}
</Text>
<Text style={styles.innerDescription}>
{list[i].desc.substring(0, 80)}
</Text>
</View>
</View>
)
}
}).catch((error) => {
console.error(error);
});
return (
<ImageBackground source={require('./images/internal_bg.png')} style={{width: '100%', height: '100%'}}>
<ScrollView>
<View style={styles.container}>
{result}
</View>
</ScrollView>
</ImageBackground>
);
}
预期结果:显示项目列表实际结果:屏幕仍为空
你的问题是fetch
是异步的。因此渲染不会在渲染组件之前等待它完成。您应该在componentDidMount
中进行数据检索,并使用结果修改组件状态。然后在渲染方法中使用此状态来填充项目(一旦更改状态,组件将重新渲染)。您还应该在组件constructor
方法中设置初始状态。
如下所示:
constructor(props) {
super(props)
this.state = { list: [] }
}
componentDidMount() {
let endPoint = this.props.navigation.getParam('endPoint', '');
fetch(endPoint, {
method: "GET",
headers: null,
})
.then(response => response.json())
.then(response => {
this.setState({ list: response })
})
.catch((error) => {
console.error(error);
});
}
render() {
let result = [];
const { list } = this.state;
for (let i = 0; i < list.length; i++) {
result.push(
<View key={i} style={styles.item}>
<View>
<View style={styles.imageContainer}>
<Image style={styles.imageItem} resizeMode="cover"
source={{uri: list[i].img}}/>
</View>
</View>
<View style={styles.inlineDetails}>
<Text style={styles.innerTitle}>
{list[i].lieugeo}
</Text>
<Text style={styles.innerDescription}>
{list[i].desc.substring(0, 80)}
</Text>
</View>
</View>
)
}
return (
<ImageBackground source={require('./images/internal_bg.png')} style={{width: '100%', height: '100%'}}>
<ScrollView>
<View style={styles.container}>
{result}
</View>
</ScrollView>
</ImageBackground>
);
}
始终在componentDidMount(){}中执行side-efects,然后更新组件状态或redux存储。您还可以使用响应数组并创建单独的子组件以显示该数组的结果。
这样你的代码就更具有可重用性了
render(){
<View>
{this.state.data && this.state.data.map(item => <DisplayProduct data={item}/>)}
<View/>
}
这里显示产品一次接受一个项目作为道具,当状态更新时,子组件也会更新,并且此组件可以在应用程序内的任何位置重复使用。