Plotly in R: How to make ggplot2 charts interactive with ggplotly


The ggplot2 package is generally the preferred tool of choice for constructing data visualisations in R. The main reason for this is because of its grounding in the grammar of graphics, which essentially breaks a plot down into a system of fully customisable coordinates and layers, enabling superior design flexibility than the base R graphics. With ggplot2, users can produce elegant, professional-looking visualisations that communicate results powerfully to the desired audience.

However, ggplot2 runs into some limitations regarding user interactivity. This becomes increasingly problematic when creating interactive documents using R Markdown or dashboard apps in R Shiny, where interactivity is a crucial component of communicating information effectively.

Fortunately, the plotly library significantly enhances the design of interactive charts in R, allowing users to hover over data points, zoom into specific areas, pan back and forth through time, and much more.

In this blog post, we show:

·       How to make static ggplot2 charts interactive using ggplotly

·       How to edit text within a ggplotly tooltip

·       How to format dates and currency values with scales

·       How to customise/disable the plotly mode bar

·       How to customise/disable ggplotly interactivity


Step 1

We start with a simple line chart produced using ggplot2. The data we are using in our example is anonymous sales and target data between 2011 and 2017. To begin, simply load the ggplot2 package, then build your plot (see ggplot2 cheat sheet for help).


p <- ggplot(data = df, aes(x = Date, y = Revenue)) +
   geom_line(colour = "grey", aes(Date, Target)) +
   geom_line(colour = "#408FA6")

Step 2

This static ggplot2 chart can quickly be made interactive by simply placing it inside the ggplotly function (after installing and loading plotly).


p <- ggplot(data = df, aes(x = Date, y = Revenue)) +
   geom_line(colour = "grey", aes(Date, Target)) +
   geom_line(colour = "#408FA6")

The static plot has now been brought to life. Users can now zoom, hover, pan and export the plot, and more.

However, the chart still needs some work, specifically the default tooltip (the box of information that appears when hovering over a data point).

Step 3

I want to edit the tooltip to display the information that we want, in a suitable format. To do so, first we insert group = 1 in the aesthetics of the ggplot to override the default behaviour; then define the text we want to appear (use <br> for a new line); and finally add tooltip = “text” to the ggplotly function.

p <- ggplot(data = df, aes(x = Date, y = Revenue, group = 1,
            text = paste("Date: ", Date,
                         "<br>Revenue: $", Revenue,
                         "<br>Target: $", Target)
)) +
   geom_line(colour = "grey", aes(Date, Target)) +
   geom_line(colour = "#408FA6")
ggplotly(p, tooltip = "text")

Although the chart has been improved, the values in the axis and tooltip need to be in a more suitable format so it’s easier to read.

Step 4

Using the scales library, we can define the y axis in a currency format quite easily. I also divided the revenue and target by one million and rounded it to one decimal place, to make the values more readable. The date can be formatted as desired (see here for date formatting options).


p <- ggplot(df, aes(x = Date, y = Revenue/1000000, group = 1, 
text = paste("Date: ", format(Date, "%B %Y), 
"<br>Revenue: $", round(Revenue/1000000, digits = 1), "million", 
"<br>Target: $", round(Target/1000000, digits = 1), "million")
)) +
scale_y_continuous(labels=dollar_format(prefix="$",suffix=" m"))+
geom_line(colour = "grey", aes(Date, Target/1000000)) +
geom_line(colour = "#408FA6") +
ggplotly(p, tooltip = "text")

This plot is now looking good and is fully interactive. For example, we can zoom into specific points, and pan back and forth through time:


However, we may want to disable or hide some interactive options. Luckily, the plot interactions and mode bar above the chart are fully customisable.

Step 5

In this case, I would like the mode bar to display all the time (as opposed to when hovered over) and want the option of zooming and panning my plot only, with panning being the default option.

First, to define the default interaction, in the layout function we use dragmode:

ggp <- ggplotly(p, tooltip = "text") %>% layout(dragmode = "pan")

To customise the mode bar, the config function is used. Here, the displayModeBar can be set to static to appear all the time, or hover to appear when the cursor is over the plot. The collaborate and displaylogo options are also disabled (note: they are removed separately from the modeBarButtonsToRemove function).  And then the mode bar buttons to be removed are listed.

ggp %>% config(displayModeBar = "static", collaborate = F, displaylogo = FALSE, modeBarButtonsToRemove = list("sendDataToCloud", "toImage", "autoScale2d", "resetScale2d", "hoverClosestCartesian", "hoverCompareCartesian", "select2d", "lasso2d", "zoomIn2d", "zoomOut2d", "toggleSpikelines")

With that, the original static plot has been converted into an interactive chart, using ggplotly.


Alternatively, the zoom, panning, scaling etc. interactivity can be disabled as follows:

ggp <- ggplotly(p, tooltip = "text") %>% 
   layout(xaxis = list(fixedrange = TRUE)) %>%
   layout(yaxis = list(fixedrange = TRUE)) %>%
   config(displayModeBar = F)

For more information and examples of interactive charts in R, visit the Plotly graphic library.