Imagine a component that renders a difference (as text) of the current date (new Date()) and the given date as prop (always the same).
This component is rendered in a FlatList, and memoized with
areEqual = () => true // because the given prop is always the same.
If I want to re-render the item when refreshing the FlatList, I do
extraData={isRefreshing}
but, as the rendered items are memoized, I don't get any updates. Any ideas?
I have implemented a component, Card, which will be rendered in a FlatList. To avoid performance problems, I have memoized it (because it is a good practice to memoize items that are rendered in lists).
function Card({ description, location, date, images }) {
...
return (
<View>
...
<Text>{getReadableTimeSince(date)}</Text>
{/* will display something like '2 hours ago' or '5 minutes ago'... */}
</View>
);
}
function areCardPropsEqual(prevProps, nextProps) {
return prevProps.description === nextProps.description; // the only editable data of a card
}
export default memo(Card, areCardPropsEqual);
Now, in my screen, I am rendering a list of posts, using the Card component. My purpose is to provide a pull-to-refresh mechanism, in order to be able to get new posts and update the already rendered items data (the date since).
This is my Screen:
const [posts, setPosts] = useState([{ date: new Date() }]);
const [isRefreshing, setIsRefreshing] = useState(false);
const handleOnRefresh = async () => {
setIsRefreshing(true);
try {
const newPosts = await api.getNewPosts();
setPosts((prevPosts) => [...newPosts, ...prevPosts]);
} catch(err) {
...
}
setIsRefreshing(false);
}
const renderRefreshControl = () => (
<RefreshControl
refreshing={isRefreshing}
colors={[
...
]}
tintColor={colors.primary}
onRefresh={handleOnRefresh}
progressViewOffset={20}
/>
);
return (
<FlatList
...
data={posts}
extraData={isRefreshing} // <----- LOOK AT THIS
refreshControl={renderRefreshControl()}
/>
);
As you can see, I am passing the extraData prop to cause a re-render on the already rendered items.
So, if for example, one of the rendered cards date is showing "5 seconds ago", then, after the refresh, it will be showing "7 seconds ago". Just the typical social media apps behavior.
But, because of the memoization, it is not being re-rendered. How can I fix this?