How to Integrate Custom Calendar Event Creation In a React Native Crowdbotics App

Accessing device calendars in a React Native app can be a bit tricky. Using open-source modules like react-native-add-calendar-event can be a great help when you are looking to show a calendar inside a modal or manipulate calendar events, such as by adding or editing events in the device's calendar.

This open-source package comes with a minimal UI and includes functions to handle calendars related to events in a React Native app. In this post, you are going to learn how to integrate this calendar module in a React Native app that is generated using the Crowdbotics app dashboard and add an event to the device's calendar app.

The conclusion of this post is going to enable you to add a custom event in the iOS calendar app in real-time.

Calendar edit confirmation prompt
Calendar event has been added to the mobile device calendar

Requirements

  • Nodejs version <= 10.x.x installed
  • watchman installed
  • Have access to one package manager such as npm or yarn
  • use react native version 0.60.x or above

Getting started with the Crowdbotics App Builder

To generate a new React Native project, you can use the react-native cli tool. Or, if you want to follow along, I am going to generate a new app using the Crowdbotics app building platform.

Crowdbotics app creation page

Register using either your GitHub credentials or your email. Once logged in, you can click the Create App button to create a new app. The next screen is going to prompt you as to what type of application you want to build. Choose Mobile App.

App type selection screen in Crowdbotics

Enter the name of the application and click the button Create App. After you link your GitHub account from the dashboard, you are going to have access to the GitHub repository for the app. This repo generated uses the latest react-native version and comes with built-in components and complete examples that can be the base foundation for your next app.

You should have cloned the repo to your local development environment in order to proceed. To build the React Native app, make sure to navigate inside the project directory through a terminal and run the following commands in series to install npm modules as well as any cocoapods for iOS development.

cd rncalendarexample-16754

yarn install

# after npm dependencies are installed
# make sure you have npx installed
npx pod-install

After the dependencies have installed, to run the app on a simulator you will have to build it for the appropriate mobile OS you are using.

# for iOS
react-native run-ios

# for Android
react-native run-android

Once the app building process has finished running, you can view the default navigation screen generated by the Crowdbotics app.

Default screen for React Native app generated through Crowdbotics

And that's it! You have successfully built a new React Native app from scratch using the Crowdbotics App Dashboard template.

Installing react-native-add-calendar-event

Start by adding the following dependencies in your React Native project. We are going to install two libraries right now:

  • react-native-add-calendar-event to add the calendar event
  • moment to format the date and time

Open up a terminal window and execute the below command.

yarn add react-native-add-calendar-event moment

For iOS developers, make sure you install the cocoapods for react-native-add-calendar-event. Run the following command from a terminal window.

npx pod-install

You have to add the permissions for this open-source module to work on iOS devices. Add the keys NSCalendarsUsageDescription and NSContactsUsageDescription inside the file ./ios/rncalendarexample_16754/Info.plist as shown below.

<dict>
<!-- rest of the file remains same -->
<key>NSCalendarsUsageDescription</key>
  <!-- this is a custom message that you can modify the display -->
  <string>Are you sure you want to allow this app to use Calendar?</string>
  <key>NSContactsUsageDescription</key>
  <string></string>
</dict>

Make sure the build the app again before running it.

# for iOS
react-native run-ios

# for Android
react-native run-android

Now you are good to work on the rest of the app.

Building the user interface

In this section, let's built the user interface for the app. Start by importing the necessary statements from different open source libraries we are using to build this app in App.js. Also, make sure to import the necessary core components from the react-native library.

import React, { useState } from 'react';
import {
  StyleSheet,
  Text,
  View,
  TextInput,
  TouchableOpacity
} from 'react-native';
import * as AddCalendarEvent from 'react-native-add-calendar-event';
import moment from 'moment';

Next, define a constant that is to display the current date and time in UTC mode. We are going to provide a static value for the current date and time for the calendar event, but you can use other modules like @react-native-community/datetimepicker to provide dynamic date and time value.

const TIME_NOW_IN_UTC = moment.utc();

Next, define a state variable inside the functional component App that is going to let the user add a custom value of the event name. If the user doesn't add a custom value for the event name, let us also pass a default name for the event. This is done by using useState React hook.

export default function App() {
  const [eventTitle, setEventTitle] = useState('Default event');

  // rest of the code
}

The UI for this demo app is going to contain a title, an input field for the user to enter the name of the calendar event, a date and time string to display the current formatted timestamp, and a button to add the calendar event to the device's calendar app. The input field is going to set the name of the calendar event to the default name of the event passed using the useState hook.

Here is the complete code for the App functional so far.

export default function App() {
  const [eventTitle, setEventTitle] = useState('Default event');

  return (
    <View style={styles.container}>
      <Text style={styles.title}>
        Add Event in device's Calendar from React Native App
      </Text>
      <View style={styles.inputContainer}>
        <Text style={styles.text}>Enter the Event title:</Text>
        <TextInput
          style={styles.input}
          value={eventTitle}
          onChangeText={text => setEventTitle(text)}
        />
        <Text style={styles.text}>Current Date and Time of the event:</Text>
        <Text style={styles.text}>
          {moment
            .utc(TIME_NOW_IN_UTC)
            .local()
            .format('lll')}
        </Text>
      </View>
      <TouchableOpacity style={styles.button}>
        <Text style={[styles.text, { color: 'white' }]}>
          Add this event to the calendar
        </Text>
      </TouchableOpacity>
    </View>
  );
}

The corresponding style references are created using the StyleSheet object.

const styles = StyleSheet.create({
  container: {
    flex: 1,
    alignItems: 'center',
    backgroundColor: '#f8f8f2',
    paddingTop: 60
  },
  title: {
    fontSize: 20,
    textAlign: 'center'
  },
  inputContainer: {
    marginVertical: 20
  },
  text: {
    fontSize: 16,
    color: '#000',
    marginVertical: 5
  },
  input: {
    fontSize: 14,
    marginVertical: 10,
    padding: 5,
    backgroundColor: '#ebebeb',
    borderColor: '#333',
    borderRadius: 4,
    borderWidth: 1,
    textAlign: 'center'
  },
  button: {
    alignItems: 'center',
    backgroundColor: 'purple',
    padding: 10,
    marginTop: 10,
    borderRadius: 10
  }
});

If you go back to the simulator, you are going to get the following result.

Interface for adding an event to the calendar

Creating a calendar event and handling the dialog

So far we have built the UI, but in this section let's add the functionality to access the device's calendar to add an event through our demo in real-time.

To add the calendar event, react-native-add-calendar-event module provides a function called AddCalendarEvent that is promise-based. Through this promise, you can add a new event directly to the calendar app for the mobile platform you are using. Using one of the methods of this promise-based function called AddCalendarEvent.presentEventCreatingDialog, it is simple to access an editable calendar event directly in our React Native app in the form of a dialog box. However, this method accepts one argument and is an eventConfig object.

This object needs the title of the event, the starting date string of the event, the end date string of the event, and, optionally, you can add a default description in form of notes. To provide a date string to this config object, we need to first convert the current date string into a string format. For that, add the below helper method before the App component in App.js.

const utcDateToString = momentInUTC => {
  let s = moment.utc(momentInUTC).format('YYYY-MM-DDTHH:mm:ss.SSS[Z]');
  return s;
};

This method takes one input and that is the UTC date stamp and uses the moment.js library to convert into the desirable string format required by the calendar app.

Now, go inside the functional component App and add the following helper method called addEventToCalendar.

This method is going to accept two arguments: the name of the event and the date string. Inside this method, you are also going to configure the eventConfig object and pass it as the argument for the promise-based method AddCalendarEvent.presentEventCreatingDialog().

function addEventToCalendar(title, startDateUTC) {
  const eventConfig = {
    title: eventTitle,
    startDate: utcDateToString(startDateUTC),
    endDate: utcDateToString(moment.utc(startDateUTC).add(1, 'hours')),
    notes: 'Default Event Description'
  };

  AddCalendarEvent.presentEventCreatingDialog(eventConfig)
    .then(eventInfo => {
      alert(JSON.stringify(eventInfo));
    })
    .catch(error => {
      alert('Error ', error);
    });
}

This promise handles whether the event is created or if the user has canceled the process of creating the event. This is done by eventInfo that returns an eventId. You can store this event ID in a state variable and add further functionalities such as editing an existing event in the calendar app (think of this as a challenge from this post).

Lastly, make sure to add this helper method as the value of onPress on the TouchableOpacity button component in App.js where you are returning JSX.

<TouchableOpacity style={styles.button} onPress={addEventToCalendar}>
  <Text style={[styles.text, { color: 'white' }]}>
    Add this event to the calendar
  </Text>
</TouchableOpacity>

Now go back to the simulator and try to add a new event. Here is a demo of the app we have built so far that actually stores the calendar event in the calendar app of an iOS device.

The app interface enables you to store a new event in the device's calendar

You can notice that the event id is returned by the promise. In case of canceling the process of creating a new event, you get a new action from the promise called CANCELLED as shown below.

The option to discard your event appears on the screen
Canceling the event creation triggers an alert

Finally, you can see the event has been stored on the iOS calendar app.

The device's calendar app shows the event as scheduled

Conclusion

I hope this post serves your purpose and that you learned something useful. The react-native-add-calendar-event package is great when it comes to adding functionality that requires you to add custom events from a React Native app to the real calendar app. Normally this type of functionality is used by most hotel rental and flight booking apps.

To explore more, I'd suggest you take a look at the following resource(s):

If you'd like to see more React Native tutorials written by me, I maintain a personal blog here.

Originally published:

May 28, 2020