Create an Expense Tracker using React-Native
Last Updated :
02 Jul, 2025
The Expense Tracker application, using React-Native, is an application where users can manage the transactions made and then visualize the expenditure with the help of a pie chart. The users can add transactions while providing the category of expenditure. The application will run on any device and is the scope of a much larger application. The application is cross-platform, which means it can run on any platform.
To give you a better idea of what we’re going to create, let’s watch a demo video.
Demo Video
Playground
Note: This Section is to interact with the app which you are going to build.
Prerequisites and Technologies Used
Approach
- The application will have a single screen.
- The application will have a pie chart and an add button.
- On pressing the add button, a form will open. The form contains the expense name, amount, and category from a select option.
- Finally, on pressing add, the expense list and chart are updated.
- The expenses are displayed in the form of a scrollable list.
- Each expense tile will also have a delete button to remove it from the list.
- We are using react-native-picker for a dropdown.
- We used react-native-chart-kit.
Step-by-Step Implementation
Step 1: Create a React Native Project
Now, create a project with the following command.
npx create-expo-app app-name --template
Note: Replace the app-name with your app name for example : react-native-demo-app
Next, you might be asked to choose a template. Select one based on your preference as shown in the image below. I am selecting the blank template because it will generate a minimal app that is as clean as an empty canvas in JavaScript.
It completes the project creation and displays a message: "Your Project is ready!" as shown in the image below.
Now go into your project folder, i.e., react-native-demo
cd app-name
Project Structure:
Step 2: Run Application
Start the server by using the following command.
npx expo start
Then, the application will display a QR code.
For the Android users,
- For the Android Emulator, press " a" as mentioned in the image below.
- For the Physical Device, download the " Expo Go " app from the Play Store. Open the app, and you will see a button labeled " Scan QR Code. " Click that button and scan the QR code; it will automatically build the Android app on your device.
For iOS users, simply scan the QR code using the Camera app.
If you're using a web browser, it will provide a local host link that you can use as mentioned in the image below.
Step 3: Update Dependencies
The updated dependencies in the package.json file will look like this.
"dependencies": {
"expo": "53.0.15",
"expo-status-bar": "~2.2.3",
"react": "18.2.0",
"react-native": "0.79.0",
"react-native-chart-kit": "^6.12.0",
"@react-native-picker/picker": "2.11.1"
}
Step 4: Start Coding
Example: We will place the state variables in the App.js and load all the components declared in the respective files here. The code is divided into different files to make it readable.
App.js
// App.js
import { StatusBar } from "expo-status-bar";
import { useEffect, useState } from "react";
import { Button, SafeAreaView, Text, View } from "react-native";
import { PieChart } from "react-native-chart-kit";
import styles from "./styles";
import Addform from "./add_expense";
import ExpenseComponent from "./expense_component";
export default function App() {
// Define state variables using the useState hook
const [name, setName] = useState("");
const [amount, setAmount] = useState("");
const [category, setCategory] = useState("Food");
const [expenses, setExpenses] = useState([]);
const categories = ["Food", "Clothes", "Bills", "Others"];
const [addForm, setAddForm] = useState(false);
// Function to open the add expense form
const addExpense = () => {
setAddForm(true);
};
// Initialize the chart data with default values
const [chartData, setChartData] = useState([
{
name: "Food",
amount: 0,
color: "#e62d20",
legendFontColor: "#7F7F7F",
legendFontSize: 15,
},
{
name: "Clothes",
amount: 0,
color: "#27e620",
legendFontColor: "#7F7F7F",
legendFontSize: 15,
},
{
name: "Bills",
amount: 0,
color: "#1c6bd9",
legendFontColor: "#7F7F7F",
legendFontSize: 15,
},
{
name: "Others",
amount: 0,
color: "#5adbac",
legendFontColor: "#7F7F7F",
legendFontSize: 15,
},
]);
// Render the components and UI
return (
<SafeAreaView style={styles.container}>
<StatusBar style="auto" />
<Text style={styles.heading}>Welcome to GeeksforGeeks</Text>
<Text style={styles.heading2}>
Expense Tracker using React-Native
</Text>
{/* Render the PieChart component with data */}
<PieChart
data={chartData}
width={300}
height={200}
chartConfig={{
backgroundGradientFrom: "#1E2923",
backgroundGradientTo: "#08130D",
color: (opacity = 1) => `rgba(26, 255, 146, ${opacity})`,
}}
accessor="amount"
backgroundColor="transparent"
paddingLeft="15"
absolute
/>
{/* Conditional rendering: If addForm is true,
render the Addform component */}
{addForm == true ? (
<Addform
name={name}
setName={setName}
amount={amount}
setAmount={setAmount}
category={category}
setCategory={setCategory}
categories={categories}
setExpenses={setExpenses}
expenses={expenses}
chartData={chartData}
setChartData={setChartData}
setAddForm={setAddForm}
/>
) : (
/* If addForm is false, render the "Add Expense" button */
<View style={styles.row}>
<Button
onPress={addExpense}
color="green"
style={styles.addButton}
title="Add Expense"
/>
</View>
)}
{/* Render the ExpenseComponent */}
<ExpenseComponent
expenses={expenses}
setExpenses={setExpenses}
chartData={chartData}
setChartData={setChartData}
/>
</SafeAreaView>
);
}
add_expense.js
// add_expense.js
import { Picker } from "@react-native-picker/picker";
import { Button, Text, TextInput, View } from "react-native";
import styles from "./styles";
// Define the Addform component which is used to add new expenses
export default function Addform({
name,
setName,
amount,
setAmount,
category,
setCategory,
categories,
setExpenses,
expenses,
chartData,
setChartData,
setAddForm,
}) {
return (
<View>
<Text style={styles.heading3}>Add Form</Text>
{/* Input field for expense name */}
<Text style={styles.label}>Expense Name</Text>
<TextInput
onChangeText={(value) => setName(value)}
value={name}
style={styles.textInput}
placeholder="Enter the expense name"
/>
{/* Input field for expense amount */}
<Text style={styles.label}>Amount</Text>
<TextInput
keyboardType="numeric"
onChangeText={(value) => {
// Ensure only numeric values are entered for the amount
value = value.replace(/[^0-9]/g, "");
setAmount(value);
}}
value={amount}
style={styles.textInput}
placeholder="Amount"
/>
{/* Dropdown to select expense category */}
<Text style={styles.label}>Category</Text>
<Picker
style={styles.textInput}
selectedValue={category}
onValueChange={(itemValue, itemIndex) => setCategory(itemValue)}
>
{categories.map((category, index) => {
return (
<Picker.Item
key={index}
label={category}
value={category}
/>
);
})}
</Picker>
{/* Buttons to add or cancel expense */}
<View style={styles.row}>
{/* Add Expense button */}
<Button
onPress={() => {
let amountNumber = parseInt(amount);
if (amountNumber <= 0 || name == "") {
// Validation: Ensure valid amount
// and name are entered
alert("Please enter a valid amount and name");
return;
}
// Add the new expense to the list of expenses
setExpenses([
...expenses,
{
id: new Date().getTime(),
category,
name,
amount: amountNumber,
},
]);
// Update the chart data to reflect the new expense
let newChartData = [...chartData];
let index = newChartData.findIndex(
(item) => item.name == category
);
newChartData[index].amount += amountNumber;
setChartData(newChartData);
// Reset form fields and close the form
setAddForm(false);
setName("");
setAmount("");
setCategory("Food");
}}
title="Add Expense"
/>
{/* Cancel button to close the form
without adding an expense */}
<Button
onPress={() => {
setAddForm(false);
}}
title="Cancel"
/>
</View>
</View>
);
}
expense_component.js
// expense_component.js
import { Alert, Button, ScrollView, Text, View } from "react-native";
import styles from "./styles";
export default function ExpenseComponent({
expenses,
setExpenses,
chartData,
setChartData,
}) {
return (
<ScrollView
style={{
marginBottom: 80,
}}
>
{expenses.map((expense) => {
console.log(expense);
return (
<ExpenseListTile
key={expense.id}
expense={expense}
chartData={chartData}
expenses={expenses}
setChartData={setChartData}
setExpenses={setExpenses}
/>
);
})}
</ScrollView>
);
}
const ExpenseListTile = ({
expense,
expenses,
setExpenses,
chartData,
setChartData,
}) => {
return (
<View style={styles.expenseTile}>
<Text style={styles.expenseTileText}>{expense.name}</Text>
<Text style={styles.expenseTileText}>{expense.category}</Text>
<Text style={styles.expenseTileText}>{expense.amount}</Text>
<Button
onPress={() => {
Alert.alert("Delete", "Are you sure you want to delete?", [
{
text: "Yes",
onPress: () => {
let newExpenses = [...expenses];
let index = newExpenses.findIndex(
(item) => item.id == expense.id
);
newExpenses.splice(index, 1);
setExpenses(newExpenses);
let newChartData = [...chartData];
let index2 = newChartData.findIndex(
(item) => item.name == expense.category
);
newChartData[index2].amount -= expense.amount;
setChartData(newChartData);
},
},
{
text: "No",
onPress: () => {
console.log("No");
},
},
]);
}}
title="Delete"
/>
</View>
);
};
styles.js
// styles.js
import { StyleSheet } from "react-native";
// styles sheet to store all the styles in one place
const styles = StyleSheet.create({
row: {
flexDirection: "row",
justifyContent: "space-evenly",
},
container: {
backgroundColor: "#fff",
height: "100%",
marginTop: 50,
},
heading: {
color: "green",
fontSize: 30,
textAlign: "center",
fontWeight: "bold",
},
addButton: {
padding: 10,
margin: 10,
},
heading2: {
color: "black",
fontSize: 25,
textAlign: "center",
fontWeight: "bold",
},
heading3: {
color: "black",
fontSize: 20,
textAlign: "center",
},
label: {
color: "black",
fontSize: 16,
textAlign: "left",
fontWeight: "bold",
marginLeft: 10,
},
expenseTile: {
// column with 3 cells
flexDirection: "row",
justifyContent: "space-between",
backgroundColor: "lightgrey",
width: "95%",
padding: 10,
margin: 10,
},
expenseTileText: {
fontSize: 20,
width: "22%",
textAlign: "center",
},
formAdd: {
// display: "none",
},
textInput: {
borderRadius: 12,
borderColor: "black",
borderWidth: 1,
padding: 10,
margin: 10,
},
});
export default styles;
Output:
Explanation
- The ExpenseComponent holds each of the expense elements and displays them.
- chartData is used to display the chart, and expenses is used to hold the individual expenses.
- We toggle the form using the addForm boolean variable.
- On pressing the Add Button, it is toggled so that we can show/hide the form.
Similar Reads
Create a Task Manager App using React-Native In this article, we'll walk you through the process of building a basic Task Manager app using React Native. The application enables users to effortlessly create, edit, complete/incomplete, and delete tasks, providing an uncomplicated yet impactful introduction to ReÂact Native's mobile app develop
12 min read
Expense Tracker using React The Expense Tracker project is a web application developed using React. Its main purpose is to assist users in keeping track of their expenses. With this app, users can easily add, and delete expenses to view a summary of their spending habits as well and it will show the available balance the user
7 min read
Create a Book Store using React-Native React-Native is a flexible frameworks for building mobile applications. We will develop a Book Store application, which allows users to search for a specific book, and store the book in the application. If the user wants to remove the book from the stored list, they can easily remove it by navigatin
6 min read
Create File Explorer App using React-Native Creating a File Explorer app using React Native provides a seamless way to explore and interact with the device's file system on both iOS and Android platforms. In this tutorial, we'll guide you through the process of building a simple yet functional File Explorer app.Output Preview:Prerequisites:No
3 min read
Create an Employee Management using React-Native Creating the Employee Management Application using React-Native is a skill-development project. In this project, the application administrator can manage employees by adding them dynamically, updating their details, and deleting them as needed. In this article, we will develop this Employee manageme
8 min read