FlatList Sticky Header Example
This is a simple example of Sticky Headers in FlatList Component of ReactNative made with NativeBase and Create React Native App tool. Detailed Setup instructions can be found below.
Find Full Code here
1. Aim
We aim to create a simple App that implements sticky headers as shown in the GIF above.
2. Installation
Create React Native App: Use CRNA tool to create an App like this
$ npm install -g create-react-native-app
$ create-react-native-app my-app
$ cd my-app/
$ npm start
NativeBase
npm install native-base --save
Important: additional steps are required to import fonts from native base. Refer to this Configure all dependencies by running the following command
react-native link
3. Setting Things Up
With all required Libraries installed, we can start with some real coding. In the root of your project create a folder src
. Inside this folder we create a file by the name of StickyHeader.js
.
Note: You might have some problems setting up the project due to version conflicts, make sure you use same versions as mentioned below in the package.json
By the end of all this your project structure and package.json
file should look something like this.
4. Making our List Component
In your StickyHeader.js
inside src
folder add the following code.
Code src/StickyHeader.js
import React from "react";
import { FlatList } from "react-native";
import { Text, ListItem, Left, Body, Icon, Right, Title } from "native-base";
export default class App extends React.Component {
constructor() {
super();
this.state = {
data: [
{ name: "Movies", header: true },
{ name: "Interstellar", header: false },
{ name: "Dark Knight", header: false },
{ name: "Pop", header: false },
{ name: "Pulp Fiction", header: false },
{ name: "Burning Train", header: false },
{ name: "Music", header: true },
{ name: "Adams", header: false },
{ name: "Nirvana", header: false },
{ name: "Amrit Maan", header: false },
{ name: "Oye Hoye", header: false },
{ name: "Eminem", header: false },
{ name: "Places", header: true },
{ name: "Jordan", header: false },
{ name: "Punjab", header: false },
{ name: "Ludhiana", header: false },
{ name: "Jamshedpur", header: false },
{ name: "India", header: false },
{ name: "People", header: true },
{ name: "Jazzy", header: false },
{ name: "Appie", header: false },
{ name: "Baby", header: false },
{ name: "Sunil", header: false },
{ name: "Arrow", header: false },
{ name: "Things", header: true },
{ name: "table", header: false },
{ name: "chair", header: false },
{ name: "fan", header: false },
{ name: "cup", header: false },
{ name: "cube", header: false }
],
stickyHeaderIndices: []
};
}
componentWillMount() {
var arr = [];
this.state.data.map(obj => {
if (obj.header) {
arr.push(this.state.data.indexOf(obj));
}
});
arr.push(0);
this.setState({
stickyHeaderIndices: arr
});
}
renderItem = ({ item }) => {
if (item.header) {
return (
<ListItem itemDivider>
<Left />
<Body style={{ marginRight: 40 }}>
<Text style={{ fontWeight: "bold" }}>
{item.name}
</Text>
</Body>
<Right />
</ListItem>
);
} else if (!item.header) {
return (
<ListItem style={{ marginLeft: 0 }}>
<Body>
<Text>{item.name}</Text>
</Body>
</ListItem>
);
}
};
render() {
return (
<FlatList
data={this.state.data}
renderItem={this.renderItem}
keyExtractor={item => item.name}
stickyHeaderIndices={this.state.stickyHeaderIndices}
/>
);
}
}
Explained
- We import our FlatList component from ReactNative. Also we take care of a few other imports from NativeBase as we will require them further.
- Next we are hard-coding our app data in our App state. Our data here just has a name and a boolean variable for header.
- Next we fetch the indices of all the headers we would like to stick in our List. Notice how we have done that in the componentWillMount method.
- In our render method, we have simply passed our FlatList Component with data provided. renderItem is called each time a new item appears in our List data.
- keyExtractor prop is required to properly differentiate between data items using a unique key. We have used the names here.
- stickyHeaderIndices will take an array of all the indices we want to stick. We pass the array we previously populated in 3.
- Lastly, in the renderItem method we include a check for header items and children items. Accordingly we show different styles for each.
5. Finishing Up
We have successfully made our List component. Go ahead and include it in our App.js file. Build and run.