Skip to ContentGo to accessibility pageKeyboard shortcuts menu
OpenStax Logo
Introduction to Computer Science

11.5 Sample Native WAD with React Native and Node or Django

Introduction to Computer Science11.5 Sample Native WAD with React Native and Node or Django

Learning Objectives

By the end of this section, you will be able to:

  • Create a Todo native mobile application with React Native or Node
  • Create a React Native app and its components
  • Connect the front-end Native app with the back-end Node app

In the previous sections, you worked with Bootstrap, Django, React, and Node to build versions of a Todo web application. In this section, you will learn how to use React Native and Node to develop a Todo application for mobile devices. You are already familiar with Node. Like React, React Native is an open-source JavaScript framework used to build native applications for mobile devices.

Creating a Todo Web Application with React Native and Node

This application uses React Native and Node to implement a simple Todo mobile application. This application builds on top of the React and Node application discussed in 11.3 Sample Responsive WAD with Bootstrap/React and Node. For this version of the application, React Native serves as the front end handling the user interface and getting and setting data via HTTP requests. Node serves as the back end that makes use of the API built using the Django REST Framework in 11.2 Sample Responsive WAD with Bootstrap and Django.

Prerequisites

To build the Todo mobile application using React Native and Node, you need React Native v0.67, Node v14.17.5, ExpressJS v4.17.2, MongooseJS v6.1.9, and Axios v0.21.0. This Todo application will run using the Android emulator and will use Android Studio v2021.1.1.

  • To begin, download and install an emulator for your intended platform (iOS or Android).
  • If you plan to run the native app on an iOS device or emulator, download and install Xcode, which is Apple’s IDE that enables application development for Apple’s platforms.
  • If you plan to run the native app on an Android device or emulator, download and install Android Studio, which enables application development for Android mobile operating systems.
  • Figure 11.38 shows how to set up the Android emulator. Launch Android Studio. From the top navigation, select Tools > Device Manager. Click on Create device. In the Select Hardware pop-up, select Pixel 5 and click Next. On the next page, select Pie Download. Click on the Download link to obtain an image as shown. Click Next followed by Finish.
Screenshot of page to set up Android emulator.
Figure 11.38 This shows how to set up the Android emulator. (Android Studio is a trademark of Google LLC.)

Once the image has been created, it will appear in the Device Manager. Next, click on the Start button to launch the emulator. When the emulator is launched, it will turn on, as shown in Figure 11.39.

Screenshot of emulator showing a cell phone screen.
Figure 11.39 This is how the emulator will appear after it is launched. (Android Studio is a trademark of Google LLC.)

Creating the React Native App

After launching the emulator, create the React Native app by running the following command in a directory outside and separate from the nodebackend/ directory. Figure 11.40 shows the React Native application files in the reactnativefrontend/ directory.

$ npx react-native init reactnativefrontend
Screenshot of React Native application files in the reactnativefrontend/ directory.
Figure 11.40 When the React Native app is created, it will generate the React Native application files in the reactnativefrontend/ directory. (rendered in React Native, under MIT license; attribution: Copyright Rice University, OpenStax, under CC BY 4.0 license)

Next, navigate into the reactnativefrontend/ directory and launch the React Native application to confirm that the React Native front-end application has been created successfully. At this point, the application is not connected to the Node back end and will launch the Metro bundler, which bundles the JavaScript code that is deployed on the mobile device or emulator when the React Native front-end application is successfully completed. When this is done, run the command. Figure 11.41 shows the page in the terminal.

$ npx react-native start
Screenshot of react-native start command.
Figure 11.41 This page will appear when the react-native start command is run. (credit: React Native, under MIT license)

The next step is to open another terminal, navigate to the reactnativefrontend/ directory, and run the following command. This will build the front-end code and deploy it on the emulator, which may take a few minutes.

$ npx react-native run-android

When the application is successfully built, Figure 11.42 shows what should appear in the second terminal.

Screenshot of code.
Figure 11.42 This code should appear in the second terminal when the React Native application is successfully built. (attribution: Copyright Rice University, OpenStax, under CC BY 4.0 license)

Figure 11.43 shows how the native application should appear in the emulator.

Welcome page for React Native in emulator.
Figure 11.43 Once the React Native application is successfully built, this is how the native application should appear in the emulator. (Android Studio is a trademark of Google LLC.)

Creating the React Native App Components

The packages used by the React Native app for navigation and other features are different from the packages used by React. To install the required packages, in the reactnativefrontend/ directory, run the following list of commands:

$ npm install @react-navigation/native@6.0.7
$ npm install @react-navigation/native-stack@6.3.0
$ npm install axios@0.25.0
$ npm install moment@2.29.1
$ npm install react-native-modal@13.0.0
$ npm install react-native-safe-area-context@3.3.2
$ npm install react-native-screens@3.10.2
$ npm install react-native-snackbar@2.4.0
$ npm install react-native-vector-icons@9.0.0

The first step is to create the Todo component. In the reactnativefrontend/ directory, create the directory src/Screens/. In the src/Screens/ directory, create the file TodoList.js. The following code shows the imports required to create the screen components.

import React, {useState, useEffect} from 'react';
import {
  View,
  Text,
  StyleSheet,
  TextInput,
  FlatList,
  TouchableOpacity,
  Dimensions,
  StatusBar,
  Alert,
} from 'react-native';
import axios from 'axios';
import {COLORS} from '../utils/colors';
import MaterialIcon from 'react-native-vector-icons/MaterialIcons';
import MaterialCommunityIcon from 'react-native-vector-icons/MaterialCommunityIcons';
import Modal from 'react-native-modal';
import Snackbar from 'react-native-snackbar';
import {duration} from 'moment';

Once this is done, the following code includes the return() function that renders the screen components.

return (
  <View style={styles.container}>
    <StatusBar backgroundColor={COLORS.DARKALT} />
    <Text style={styles.heading}>Welcome to Todo List App!</Text>
    <Text style={styles.heading}>Your Tasks</Text>

    {todos.length == 0 ? (
      <View style={styles.center}>
        <MaterialCommunityIcon
          name="note-multiple"
          size={90}
          color={COLORS.LIGHTALT}
        />
        <Text style={styles.noTasksText}>No Tasks Added</Text>
      </View>
    ) : (
      <>
        <View style={styles.todosContainer}>
          <FlatList
            data={todos}
            renderItem={({item}) => (
              <View style={styles.todo}>
                <Text
                  style={item.complete ? styles.completedStyle : styles.text}>
                  {item.title}
                </Text>
                <TouchableOpacity
                  style={styles.deleteTodo}
                  onPress={() => deleteTodo(item._id)}>
                  <Text style={{color: COLORS.WHITE}}>X</Text>
                </TouchableOpacity>
              </View>
            )}
          />
        </View>

        <TouchableOpacity
          style={styles.addButton}
          onPress={() => {
            setModalActive(true);
          }}>
          <MaterialIcon name="add" size={32} color={COLORS.LIGHT} />
        </TouchableOpacity>
      </>
    )}

    <Modal
      isVisible={modalActive}
      animationIn={'slideInUp'}
      animationOut={'slideInDown'}>
      <View style={styles.modalView}>
        <TouchableOpacity
          style={styles.modalCloseBtn}
          onPress={() => setModalActive(false)}>
          <Text style={styles.modalCloseBtnText}>X</Text>
        </TouchableOpacity>
        <Text style={styles.addTaskHeading}>Add Task</Text>
        <TextInput
          style={styles.taskInput}
          placeholder="Enter task here.."
          onChangeText={text => setNewTodo(text)}
          value={newTodo}
        />
        <TouchableOpacity style={styles.createBtn} onPress={() => addTodo()}>
          <Text style={styles.createBtnText}>Create Task</Text>
        </TouchableOpacity>
      </View>
    </Modal>
  </View>
);

The following code creates the modal pop-up screen that is used to create a Todo list.

<Modal 
  isVisible={modalActive}
  animationIn={'slideInUp'}
  animationOut={'slideInDown'}>
  <View style={styles.modalView}>
    <TouchableOpacity
      style={styles.modalCloseBtn}
      onPress={() => setModalActive(false)}>
      <Text style={styles.modalCloseBtnText}>X</Text>
    </TouchableOpacity>
    <Text style={styles.addTaskHeading}>Add Task</Text>
    <TextInput
      style={styles.taskInput}
      placeholder="Enter task here.."
      onChangeText={text => setNewTodo(text)}
      value={newTodo}
    />
   <TouchableOpacity style={styles.createBtn} onPress={() => addTodo()}>
      <Text style={styles.createBtnText}>Create Task</Text>
    </TouchableOpacity>
  </View>
</Modal>

Next, update the reactnativefrontend/App.js file, as shown in the following code, to render the screen components declared in the TodoList.js file.

import React from 'react';
import {NavigationContainer} from '@react-navigation/native';
import {createNativeStackNavigator} from '@react-navigation/native-stack';
import TodoList from './src/Screens/TodoList';

const Stack = createNativeStackNavigator();

const App = () => {
  return (
    <NavigationContainer>
      <Stack.Navigator>
        <Stack.Screen
          name="TodoList"
          component={TodoList}
          options={{headerShown: false}}
        />
      </Stack.Navigator>
    </NavigationContainer>
  );
};
export default App;

When this is done, relaunch the Metro bundler and deploy the native application by running the following commands:

$ npx react-native start
$ npx react-native run-android

Next, create a Todo item (Figure 11.44).

Screenshot of page to create Todo items.
Figure 11.44 After relaunching the Metro bundler and deploying the native application, this screen allows users to create a Todo item. (Android studio is a trademark of Google LLC.)

After the Todo item is created, it should appear on the main screen as seen in Figure 11.45.

Screenshot of Welcome page for creating your Todo List App.
Figure 11.45 Here is how the Todo item should appear on the main screen. (Android studio is a trademark of Google LLC.)

Connecting the Front-End Native App with the Back-End Node App

The next step is to connect the front-end React Native app with the back-end Node app. To do this, open reactnativefrontend/src/Screens/Todolist.js. Add the API_BASE variable and configure the IP address to the local computer, running the Express web server, as shown in the following code.

import axios from 'axios';
import {COLORS} from '../utils/colors';
import MaterialIcon from 'react-native-vector-icons/MaterialIcons';
import MaterialCommunityIcon from 'react-native-vector-icons/MaterialCommunityIcons';
import Modal from 'react-native-modal';
import Snackbar from 'react-native-snackbar';
import {duration} from 'moment';

const width = Dimensions.get('window').width;

const API_BASE = 'http://192.168.1.183:8080';

Next, add the Axios calls to interact with the REST API provided via the Express web server to interact with the MongoDB database.

const [todos, setTodos] = useState([]);
  const [modalActive, setModalActive] = useState(false);
  const [newTodo, setNewTodo] = useState('');

  useEffect(() => {
    GetTodos();
  }, [todos]);

  const GetTodos = () => {
    axios
      .get(`${API_BASE}/api/todos`)
      .then(response => {
        setTodos(response.data);
      })
      .catch(err => {
        console.error('Error: ', err);
        Snackbar.show({
          text: '' + err,
          duration: Snackbar.LENGTH_LONG,
          backgroundColor: 'red',
          textColor: COLORS.WHITE,
        });
      });
  };

  const completeTodo = async id => {
    const data = await axios.put(`${API_BASE}/api/todos/${id}`);

    setTodos(todos =>
      todos.map(todo => {
        if (todo._id === data._id) {
          todo.complete = data.complete;
        }

        return todo;
      }),
    );
  };

  const deleteTodo = async id => {
    const data = await axios.delete(`${API_BASE}/api/todos/${id}`);

    setTodos(todos => todos.filter(todo => todo._id !== data._id));
  };

  const addTodo = async () => {
    if (newTodo == '') {
      Alert.alert('Error!', 'Please enter a task first!');
      return;
    } else {
      await axios
        .post(`${API_BASE}/todo/new`, {
          text: newTodo,
        })
        .then(function (response) {
          const data = response.data;
          setTodos([...todos, data]);
          setModalActive(false);
          setNewTodo('');
        })
        .catch(function (error) {
          console.log('Error: ', error);
        });
    }
  };
Citation/Attribution

This book may not be used in the training of large language models or otherwise be ingested into large language models or generative AI offerings without OpenStax's permission.

Want to cite, share, or modify this book? This book uses the Creative Commons Attribution License and you must attribute OpenStax.

Attribution information
  • If you are redistributing all or part of this book in a print format, then you must include on every physical page the following attribution:
    Access for free at https://openstax.org/books/introduction-computer-science/pages/1-introduction
  • If you are redistributing all or part of this book in a digital format, then you must include on every digital page view the following attribution:
    Access for free at https://openstax.org/books/introduction-computer-science/pages/1-introduction
Citation information

© Oct 29, 2024 OpenStax. Textbook content produced by OpenStax is licensed under a Creative Commons Attribution License . The OpenStax name, OpenStax logo, OpenStax book covers, OpenStax CNX name, and OpenStax CNX logo are not subject to the Creative Commons license and may not be reproduced without the prior and express written consent of Rice University.