I have the below code to dynamically render a component with data from an API. However I keep getting this error:
Error: Objects are not valid as a React child (found: object with keys {_U, _V, _W, _X}). If you meant to render a collection of children, use an array instead.
In the code I tried to create an array with the data but still continue to get the error. There is just one object that I extract from the API data to render.
import React, { useState } from 'react';
import { Button, View, Text, Image, TextInput, StyleSheet, ScrollView, SafeAreaView, TouchableOpacity } from 'react-native';
import { Video } from 'expo-av';
import { AsyncStorage } from 'react-native';
import { Ionicons } from '@expo/vector-icons';
export default async function Profile({navigation}) {
const [company, setCompany] = useState([])
const getData = async () => {
try {
const value = await AsyncStorage.getItem('company')
console.log(value)
fetchData(value)
if(value !== null) {
}
} catch(e) {
}
}
const fetchData = (name) => {
fetch("https://stonernautz.com/companies.json")
.then(response => {
return response.json()
})
.then(data => {
for(var i in data){
if(data[i].name == name)
console.log(data[i])
setCompany("[" JSON.stringify(data[i]) "]")
console.log(company)
}
})
}
useEffect(() => {
getData()
});
return (
<View style={{ flex: 1, alignItems: 'center', justifyContent: 'center', backgroundColor:"black",color:"white"}}>
<View style={styles.catView}>
<Ionicons name="arrow-back" color={'white'} size={26} style={{marginLeft:0, marginTop:10}} onPress={() => navigation.goBack()}/>
<Text style={{color:"white"}}>Back</Text>
</View>
<View style={{height:"60%",position:'absolute', top:110}}>
<ScrollView>
{company.map(user => (
<View style={{marginBottom:100}} key={user.name}>
<Video
source={{ uri: `${user.video}` }}
rate={1.0}
volume={1.0}
isMuted={false}
resizeMode="contain"
useNativeControls
style={{ width: 400, height: 250, maxWidth:"100%" }}
/>
<Image
style ={styles.image}
source={{ uri : `${user.logo}`}}
/>
<Text style={styles.name}>{user.name}</Text>
<TouchableOpacity
style={styles.button}
>
<Text>Connect</Text>
</TouchableOpacity>
</View>
))}
</ScrollView>
</View>
</View>
);
}
const styles = StyleSheet.create({
input: {
height: 40,
margin: 12,
borderWidth: 5,
borderBottomColor: '#000000',
borderTopColor: '#000000',
borderRightColor: '#000000',
borderLeftColor: '#000000',
padding: 10,
borderColor: "#000000"
},
image: {
width: 50,
height: 50,
borderRadius: 100,
overflow: "hidden",
marginTop: 20,
marginLeft:20
},
button: {
alignItems: "center",
backgroundColor: "white",
padding: 10,
width:200,
position:'absolute',
top:300,
left:'25%',
height:40,
justifyContent: 'center'
},
container: {
flex: 1,
paddingTop:10,
},
scrollView: {
position:'absolute',
top:80,
left:0,
marginHorizontal: 20,
maxHeight:400,
width:"90%",
maxWidth:"100%",
},
text: {
fontSize: 100,
marginLeft:10,
},
catText: {
color: "white",
fontSize:24,
marginLeft:40,
lineHeight:50
},
catView: {
paddingRight: 20,
position:"absolute",
top:50,
left:20
},
name: {
color:'white',
fontSize:20,
position:'absolute',
top:260,
left:110,
justifyContent: 'center',
alignItems: 'center'
},
});
CodePudding user response:
getData is async so you should try to await the Promise with something like this:
useEffect(() => {
(async () => {
await getData()
})();
}, []);
CodePudding user response:
I figured it out after A While, Here is what I did:
import React, { useState, Component } from 'react';
import { Button, View, Text, Image, TextInput, StyleSheet, ScrollView, SafeAreaView, TouchableOpacity } from 'react-native';
import { Video } from 'expo-av';
import { AsyncStorage } from 'react-native';
import { Ionicons } from '@expo/vector-icons';
const styles = StyleSheet.create({
input: {
height: 40,
margin: 12,
borderWidth: 5,
borderBottomColor: '#000000',
borderTopColor: '#000000',
borderRightColor: '#000000',
borderLeftColor: '#000000',
padding: 10,
borderColor: "#000000"
},
image: {
width: 50,
height: 50,
borderRadius: 100,
overflow: "hidden",
marginTop: 20,
marginLeft:20
},
button: {
alignItems: "center",
backgroundColor: "white",
padding: 10,
width:200,
position:'absolute',
top:300,
left:'25%',
height:40,
justifyContent: 'center'
},
container: {
flex: 1,
paddingTop:10,
},
scrollView: {
position:'absolute',
top:80,
left:0,
marginHorizontal: 20,
maxHeight:400,
width:"90%",
maxWidth:"100%",
},
text: {
fontSize: 100,
marginLeft:10,
},
catText: {
color: "white",
fontSize:24,
marginLeft:40,
lineHeight:50
},
catView: {
paddingRight: 20,
position:"absolute",
top:50,
left:20
},
name: {
color:'white',
fontSize:20,
position:'absolute',
top:260,
left:110,
justifyContent: 'center',
alignItems: 'center'
},
});
class ProductList extends Component {
constructor(props) {
super(props)
this.state = {
company: []
}
}
fetchData = (company) => {
//console.log("hi" company)
fetch("https://stonernautz.com/companies.json")
.then(response => {
return response.json()
})
.then(data => {
for(var i in data){
if(data[i].name == company){
this.setState({ company: data[i] })
//console.log(this.state)
}
}
})
}
componentDidMount = async () => {
const value = await AsyncStorage.getItem('company')
//console.log(value)
await this.fetchData(value)
}
render() {
return (
<View style={{backgroundColor:"black", height:"100%", alignItems:"center", justifyContent:"center"}}>
<Text style={{color:"white", alignItems:"center", justifyContent:"center"}}>{this.state.company.name}</Text>
</View>
)
}
}
export default ProductList;