🏥 🏭 Working on the COVID-19 response in Canada? Plotly & the Canadian government can help you and your organization. Learn more and get in touch.

Is there any other way to implement R's cumulative animation?

accumulate_by <- function(dat, var) {
  var <- lazyeval::f_eval(var, dat)
  lvls <- plotly:::getLevels(var)
  dats <- lapply(seq_along(lvls), function(x) {
    cbind(dat[var %in% lvls[seq(1, x)], ], frame = lvls[[x]])
  })
  dplyr::bind_rows(dats)
}

d <- txhousing %>%
  filter(year > 2005, city %in% c("Abilene", "Bay Area")) %>%
  accumulate_by(~date)

If you implement a cumulative animation in the manner of the function above, the number of rows will increase too much.

I use a thousand frames and a row of ten thousand. Because of the large number of data, the work in progress has been disturbed.

Is there any way to create a cumulative animation other than the example?
Help me!

1 Like

I’m currently facing the same issue. The approach described here is not applicable for a few thousand rows of data.

I don’t have a fully working solution, but my idea was to adapt the x-axis range based on the slider value instead of re-using the data for each frame:

library(plotly)

DF <- data.frame(
  x = seq(0, 12, length=50),
  y = runif(n = 50, min = 0, max = 10)
)

steps <- list()
for(i in 1:13){
  steps[[i]] <- list(args = list("xaxis", list(range = c(0, i))), 
                     label = i, 
                     method = "relayout", 
                     value = i
  )
}

# use animation_slider() / animation_button() / filter?
p <- plot_ly(DF, x = ~x, y = ~y, type = "scatter", mode = "lines") %>%
  layout(title = "Cumulative Animations in R without data redundancy",
         xaxis = list(range = steps[[1]]$args[[2]]$range),
         sliders = list(
           list(
             active = 0, 
             currentvalue = list(prefix = "X-max: "), 
             pad = list(t = 60), 
             steps = steps))) 
p

This unfortunately doesn’t provide us with the “Play”-button. But I thought it might be possible
to use animation_slider() / animation_button() in a similar way?

Here is another interesting approach for the python api using filter.

Here is the same question on SO

For those interested, here is an example on how to use filter transform and a custom range slider in R, however, I still don’t know how to add an animation (without precomputing each frame):

DF <- data.frame(x = rep(1:10, 2), y = runif(20), group = rep(LETTERS[1:2], each = 10))

steps <- list()

for (i in seq_along(unique(DF$x))) {
  steps[[i]] <- list(
    args = list('transforms[0].value', i),
    label = i,
    method = "restyle",
    value = i
  )
}

p_filter_slider <- plot_ly(
  DF,
  x = ~ x,
  y = ~ y,
  color = ~ group,
  type = "scatter",
  mode = "lines+markers",
  transforms = list(
    list(
      type = 'filter',
      target = 'x',
      operation = '<=',
      value = ~ x
    )
  )
) %>% layout(title = "Custom filter slider",
             xaxis = list(range = c(0.5, length(unique(DF$x))+0.5)),
             sliders = list(
               list(
                 active = 0, 
                 currentvalue = list(prefix = "X-max: "), 
                 pad = list(t = 20), 
                 steps = steps))
             )

p_filter_slider