dynamically displaying scrolling list of characters via FlatList - reactjs

I have an array in a file called arrays.js like this:
export var Characters = [
{
id: 1,
Name: "Dirk Longsword"
Avatar: require('./images/profile1.png')
},
{
id: 2,
Name: "Msal Reaper"
Avatar: require('./images/profile2.png')
},
{
id: 3,
Name: "Stone Rockthrow"
Avatar: require('./images/profile3.png')
}
]
On my main screen, I'm trying to write it all out dynamically via a scrollable like this:
import {Characters} from './arrays';
render() {
return (
<FlatList
data={Characters}
keyExtractor={
character => character.Name
}
renderItem={
({character}) => (
<View style={[styles.flexRow]}>
<Text>
{character.Name}
</Text>
<Image style={[ styles.charImage ]}
source={character.Avatar}
/>
</View>
)
}
/>
}
But I keep getting this error:
'undefined' is not an object(character.Name)
I'm not sure what I'm doing wrong and could use a helping hand.
Thanks!

First, I'll be ignoring the many syntax errors in the code you posted.
Second, you are misunderstanding how { } destructuring works in Javascript. You are attempting to destructure character from the data passed to Flatlist's renderItem. There is no such key value for the object passed to renderItem. If you look at the docs, you'll see there there are only the following keys:
item <- This contains the "character" object that you are trying to access.
index
separators
You can fix your code in two ways. One of which is to not destructure at all:
renderItem={
(character) => (
<View style={[styles.flexRow]}>
<Text>
{character.item.Name}
</Text>
<Image style={[ styles.charImage ]}
source={character.item.Avatar}
/>
</View>
)
}
The other is to destructure item and use that in the manner you're trying to do with character:
renderItem={
({item}) => (
<View style={[styles.flexRow]}>
<Text>
{item.Name}
</Text>
<Image style={[ styles.charImage ]}
source={item.Avatar}
/>
</View>
)
}

Related

How to Limit render element Flat List and add more content in React Native

I want like that flatlist render only 5 checkbox items and then when I click to +5 more button it will show 5 more checkbox list.In this all checkbox list appearing but i want only five
Please help me how to achieve that
Thanks in advance
const renderResourceList = renderData => {
return (
<FlatList
data={renderData}
initialNumToRender={5}
maxToRenderPerBatch={5}
pagingEnabled={true}
nestedScrollEnabled={true}
renderItem={({item}) => (
<View style={styles.card}>
<TouchableOpacity
onPress={() => {
if(resourceTypeArray.includes(item)){
setResourceTypeArray(currentList => {
return currentList.filter(items => items !== item);
});
}
else{
setResourceTypeArray(currentList => [
...currentList,
item
]);
}
onSetResourceType(item);
}}
style={styles.modalBtn}>
<Icon
name={
resourceTypeArray.includes(item) ? 'checkbox-marked' : 'checkbox-blank-outline'
}
size={18}
color="#353C3C"
style={{bottom: -1}}
/>
<View style={styles.textWrapper}>
<Text style={styles.modalText}>{item.charAt(0)}
{item.toLowerCase().slice(1).replace(/_/g, ' ')}</Text>
</View>
</TouchableOpacity>
</View>
)}
/>
);
};
I tried but this not working
I used a package called flatlist-react to handle this for me. A decent tutorial for this can be found here.
With this package, you can directly specify and limit the items rendered with the limit prop. Here is an example:
<FlatList
limit="2,-2"
list={people}
renderItem={Person}
/>
If you keep track of the limit prop variables using state, you can dynamically change these values when you click 5+ more in order to render whatever part of your data you would like.

How to put value from an object inside an array into a flatlist React Native

so I have this array:
let Reviews = [
{
name: "Tibo Mertens",
review: "Very nice model",
},
{
name: "Quintt Adam",
review: "I like the car",
},
];
And a Flatlist:
<View>
<FlatList
data={Reviews}
renderItem={({ item }) => {
<View>
<Text>{item.name}</Text>
</View>;
}}
></FlatList>
</View>
Where you see {item.name} I want to display the names of the objects in the flatlist. But nothing is showing, the value is undefined. How do I get the right values?
There are a few things wrong with your code.
You are not returning the View in renderItem.
You having a semi-colon on the end of the View in renderItem - You should remove that.
FlatList should be self-closing.
<View>
<FlatList
data={Reviews}
renderItem={({ item }) =>
<View><Text>{item.name}</Text></View>
}
/>
</View>
To note, the above is an implicit return and is an alternative to the following:
renderItem={({ item }) => {
return <View><Text>{item.name}</Text></View>
}}

Will memoization prevent my React component from rerendering?

I'm struggling to understand what causes my component to rerender as there is no state present here. Code to focus on is Flatlist as this is React Native but this is about React and not specifically RN. As you can see inside Flatlist I render renderPost. I know that renderPost, aka reusable component PostListItem rerenders because this console.log you can see inside flatlist gives me repeated keys, and even console logging postsSortedByDate shows me that they render few times. Because of this, I even have a warning child list keys must be unique while I definitely gave flatlist unique IDs from my array, that warning is because of these rerendering. I guess I need to use Memo somewhere?:
const FeedScreen: React.FC<FeedScreenProps> = ({ navigation }) => {
const { postsSortedByDate } = checkPostsContext();
const navigateToCreatePostScreen = async () => {
navigation.navigate("CreatePostScreen");
};
const renderPost: ListRenderItem<IPost> = ({ item }) => (
<PostListItem post={item} key={item.uniquePostID} />
);
return (
<ScreenContainer>
<SafeAreaView>
<Header
containerStyle={styles.containerStyleHeader}
headerTitle="Factory X Feed"
rightIcon="add-photo-alternate"
onPressRightIcon={navigateToCreatePostScreen}
/>
</SafeAreaView>
{postsSortedByDate.length === 0 ? (
<View style={styles.noPostsContainer}>
<Text>
No posts exist at the moment, please create one by tapping on the
image icon in the header. In the meantime, as indicated by the
spinner below, we will continue to try to fetch posts in case some
do exist but are just loading slowly.
</Text>
<ActivityIndicator size="large" color="#0000ff" />
</View>
) : (
<FlatList
data={postsSortedByDate}
renderItem={renderPost}
keyExtractor={(item, index) => {
console.log("IDS:", item.uniquePostID.toString());
//HERE IS THE ISSUE as here I see same keys rendering //multiple times, and I checked and I did not save posts in a wrong way //for few of them to have the same key somehow. Its now about that. //Even logging posts themselves(here) shows me they re render.
return item.uniquePostID.toString();
}}
/>
)}
</ScreenContainer>
);
};
My PostListItem component:
const PostListItem: React.FC<PostItemProps> = ({ post }) => {
return (
<View style={styles.container}>
{post.postImage ? (
<Lightbox
renderContent={() => {
return (
<Image
source={{ uri: post.postImage }}
resizeMode="cover"
style={[
styles.imageInLightbox,
{
width: width,
height: height,
},
]}
/>
);
}}
>
<Image
source={{ uri: post.postImage }}
resizeMode="contain"
style={styles.image}
/>
</Lightbox>
) : null}
<React.Fragment>
{post.postDescription ? (
<Text style={styles.textStyle}>
{hashtagFormatter(post.postDescription)}
</Text>
) : (
<Text style={styles.textStyle}>{defaultPostDescription}</Text>
)}
</React.Fragment>
</View>
);
So why is PostListItem, I mean renderPost rerendering and how to fix it?

How can i do two subtitle using react native FlatList, ListItem?

I do list in my react native app.
I have this:
<FlatList
data={this.state.items}
renderItem={({ item }) => (
<ListItem
title={`${item.object.street_number}${item.object.apt_number?'/'+item.object.apt_number:''} ${item.object.street_name} ${item.object.city}`}
subtitle={`Payment: ${item.data[0].is_paid ? 'Paid' : 'No Paid'}`}
/>
)}
/>
Can i do the second subtitle or do line break?
It is totally up to you to define your own renderItem() function
renderItem({item}) {
const time = `${item.time}`;
const place = `${item.place}`;
const temp = css.addDegreesToEnd(item.currentTemp);
const {iconName, iconFont, iconColor} = item.icon;
let actualRowComponent =
<View style={css.home_screen_list.row}>
<View style={...}>
<Text style={...}>{time}</Text> //First text
<Text style={...}>{place}</Text> //Second
</View>
<Icon color={iconColor} size={...} name={iconName} //Others
type={iconFont}/>
<Text style={...}>{temp}</Text>
</View>;
...
}
Even complex layouts are also possible, not to mention two text rows, for instance:

React Native ternary/conditional operator error - "Raw Text cannot be used outside <Text> tag"

Having an issue implementing a ternary operator in my React Native code.
render() {
const contents = collection.map((item, index) => {
return (
<Card key={index}>
<Image
style={[styles.image_card]}
source={{uri: item.url}} />
<View>
{item.is_rtp_resto ?
null : <Text>hi</Text>
}
</View>
</Card>
collections is an array with fields like this:
{
"is_rtp_resto": false,
"item_name": "Chicken tikka masala",
"url": "https://res.cloudinary.com/grubhub/image/upload/v1511880272/yotwhnbr9hsnnkmfydm3.jpg"
},
However, the error I'm getting is Raw text cannot be used outside of a <text> tag. Not rendering string: ''. I'm having trouble figuring out where that could be, because i don't have empty '' anywhere...
What am I doing wrong in the item.is_rtp_resto ? call? If i take that out I have no issues (item.url among other fields are coming in fine and everything).
Thanks!
MORE INFO:
If I remove the
<View>
{item.is_rtp_resto ?
null : <Text>hi</Text>
} </View>
entirely, then I do not get an error -- so I know something in that little section with the operator or how I am calling .is_rtp_resto must be causing the error...
Here is the full body of the mapping iterator. As you can see below, any calls to other attributes in the array (.url, .item_name) work fine.
const contents = collection.map((item, index) => {
return (
<Card key={index}>
<Image
style={[styles.image_card]}
source={{uri: item.url}} />
<View>
{item.is_rtp_resto ?
null : <Text>hi</Text>
} </View>
<View>
<Text style={styles.label}>{item.item_name}</Text>
</View>
</Card>
)
});

Resources