FullCalendar with React
Tags: react, redux, rails, beginners
Published: 2020-01-28 22:29:36

So I finally finished my final project for Flatiron School! I am beyond proud of how far I've come, but I am still yearning to learn more -- especially about CSS and UX/UI design. For the final project, we had to build an application with a React/Redux frontend with a Rails API backend. I've got to say, the React section has by far been the most fun for me. To challenge myself, I decided to learn how to implement FullCalendar into my petcare scheduling application.

<h2>Why FullCalendar</h2>

I knew I wanted a calendar on my application and did not want to waste time building it out myself. A lot of the curriculum tells us not to reinvent the wheel if we don't have a good reason to. So I turned to research and found that FullCalendar was a very popular JS calendar with many features. I liked how easy it was to load events in as well as edit them. After a few hours of reading through the docs and looking up videos, I decided to give it a go.

<h2>Importing FullCalendar into React</h2>

To get started, I needed to install FullCalendar via the command line.

```
npm install --save @fullcalendar/react @fullcalendar/core @fullcalendar/daygrid @fullcalendar/interaction
```

Then, I had to import FullCalendar along with the usually imports into my component.

```react
import React, { Component } from 'react'
import FullCalendar from '@fullcalendar/react'
import dayGridPlugin from '@fullcalendar/daygrid'
import interactionPlugin from '@fullcalendar/interaction'

export default class Schedule extends Component {
  // declare any necessary functions such as handleDateClick, etc.

  render() {
    return <FullCalendar 
                    defaultView="dayGridMonth" 
                    plugins={[dayGridPlugin, interactionPlugin]}
                    editable={true}
                    eventDrop={this.handleEventDrop}
                    eventClick={this.handleEventClick}
                    events={this.formatEvents()}
                />
  }
}
```

Note: The Interaction Plugin isn't necessary but makes interacting with events (i.e. editing and deleting) possible. React allows you to use all the usual FullCalendar features, these are just the ones I chose to keep it simple my first time around. Feel free to go wild with all the possible features!

<a href="https://fullcalendar.io/docs/react">FullCalendar React Docs</a>


<h2>Getting Events on the Calendar</h2>

FullCalendar uses the events prop to determine what to render to the calendar. The event prop expects an array of event objects with keys of title, start, and an optional end. It also has a key of extendedProps which it sends and props with keys it doesn't expect to. In order to easily access my event information when clicking on an event (the eventClick prop), I put any info I needed under the extendedProps key.

```react
// ex. events={[{title: 'Appointment', start: '02-10-2020'}, {title: "", start: "03-05-2020"}]}

// events={this.formatEvents()}

formatEvents() {
  return this.props.appointments.map(appointment => {
            const {title, end, start} = appointment

            let startTime = new Date(start)
            let endTime = new Date(end)

            return {
              title, 
              start: startTime,
              end: endTime, 
              extendedProps: {...appointment}
            }
        })
}
```

<h2>Editting Events</h2>

With eventClick and eventDrop, the user can easily edit an event. I used eventClick to open up a form for a user to view and edit any information about that appointment. In eventDrop, when the user drags an appointment to a different day, the appointment can be edited to start on that date.

```react
handleEventClick= ({event}) => {
    // openAppointment is a function I wrote to open a form to edit that appointment
    this.props.openAppointment(event.extendedProps)
}

handleEventDrop = (info) => {
        if(window.confirm("Are you sure you want to change the event date?")){
            console.log('change confirmed')

            // updateAppointment is another custom method
            this.props.updateAppointment({...info.event.extendedProps, start: info.event.start, end: info.event.end})

        } else {
            console.log('change aborted')
        }
   }
```

These FullCalendar methods made updating and persisting data very easy. I'm planning on playing around with FullCalendar more to learn more about the numerous features and how it works in vanilla JS.

If you have a favorite feature of FullCalendar that I haven't used, or if you have another calendar that you use in your applications, feel free to let me know! :)