Search code examples
r-plotlyggplotly

How to convert geom_point(aes()) + geom_vline(aes()) to Plotly?


I found this tutorial online that helps convert ggplot2's geom_abline() to a Plotly graph: https://plotly.com/ggplot2/geom_abline/

It looks like we can simply make such conversion using ggplotly():

library(ggplot2)
library(plotly)

p <- ggplot(data, aes(x=x_val, y=y_val, colour=color_val)) + 
  geom_point() +
  geom_vline(aes(xintercept=xintercept_val), colour=color_val)
ggplotly(p)

However, I cannot convert my ggplot2 graph into a Plotly graph with the following code:

# notice that both my x_val and xintercept_val are dates.
# here's my ggplot2 code:
gg <- ggplot(data) +
  geom_point(aes(
    x_val,
    y_val,
    color=color_val,
    shape=shape_val
  )) +
  geom_vline(aes(
    xintercept=xintercept_val,
    color=color_val
  ))
ggplotly(gg)

Here's a screenshot of my ggplot2 graph (I cropped out the legends): ggplot2

Here's a screenshot of my Plotly graph using ggplotly(gg):ggplotly(gg)

Not sure why the vertical lines aren't showing up in Plotly.


Solution

  • Looks like you stumbled over a bug in ggplotly (perhaps you should raise an issue on github). The issue is that ggplotly internally converts the dates to numerics (same with categorical variables). However, inspecting the JSON representation via plotly_json shows that the xintercepts in geom_vline are not converted. That's why they don't show up. However, as a workaround you can make the conversion manually using as.numeric().

    As you provided no data I use a simple example dataset from the plotly website to which I added some dates. Try this:

    dat <- read.table(header=TRUE, text='
          cond xval yval
       control 11.5 10.8
       control  9.3 12.9
       control  8.0  9.9
       control 11.5 10.1
       control  8.6  8.3
       control  9.9  9.5
       control  8.8  8.7
       control 11.7 10.1
       control  9.7  9.3
       control  9.8 12.0
     treatment 10.4 10.6
     treatment 12.1  8.6
     treatment 11.2 11.0
     treatment 10.0  8.8
     treatment 12.9  9.5
     treatment  9.1 10.0
     treatment 13.4  9.6
     treatment 11.6  9.8
     treatment 11.5  9.8
     treatment 12.0 10.6
    ')
    
    dat$xval <- rep(as.Date(paste0("2020-", 1:10, "-01")), 2)
    
    max_date1 <- dat[dat$cond == "control", "xval"][which.max(dat[dat$cond == "control", "yval"])]
    max_date2 <- dat[dat$cond == "treatment", "xval"][which.max(dat[dat$cond == "treatment", "yval"])]
    
    # The basic scatterplot
    p <- ggplot(dat, aes(x=xval, y=yval, colour=cond)) + 
      geom_point()
    
    # Add colored lines for the date of the max yval of each group
    p <- p +
      geom_vline(aes(xintercept=as.numeric(max_date1)), colour="green") + 
      geom_vline(aes(xintercept=as.numeric(max_date2)), colour="lightblue")
    p
    fig <- ggplotly(p)
    
    fig
    

    Gives me this plot:

    enter image description here