I am writing a Shiny app that loads a sequence of images (i.e., frames) and contains an "Autoplay" button to go through all the images automatically.
Here is an MRE version of the relevant parts of the code. The Autoplay button is indirectly generated as a UI object because there's also a dynamic frame-selection slider involved. Sample PNG files can be obtained here.
library(shiny)
ui <- fluidPage(
sidebarPanel(uiOutput("play")), # autoplay button
mainPanel(imageOutput("image_frame"))
)
server <- function(input, output) {
frame <- reactiveValues(out=1, autoplay=FALSE)
# Finding where the images are stored and what their names are ---
image <- reactive({
file_path <- "~" # Home folder on Linux
file_list <- list.files(file_path, pattern="*.png")
return(list(path=file_path, name=file_list))
})
# Determining which frame will be printed ------------------------
tot_frames <- reactive(length(image()$name))
output$play <- renderUI(actionButton("play", "Autoplay"))
observeEvent(input$play, {
frame$autoplay <- TRUE
frame$out <- 1:tot_frames()
})
# Printing selected frame ----------------------------------------
frame_path_to_print <- reactive({
filename <- image()$name[frame$out]
out <- paste0(image()$path, filename)
return(out)
})
# This is how I intuitively think it should work, except it doesn't
if (isolate(frame$autoplay)) {
for (f in isolate(frame$out)) {
output$image_frame <- list(
src=paste0(image()$path, image()$name[f])
)
Sys.sleep(0.1)
}
} else {
output$image_frame <- renderImage(
list(src=frame_path_to_print())
)
}
}
shinyApp(ui, server)
I've managed to add "previous" and "next" buttons successfully, but I can't get the "autoplay" one to work. In addition to the code above, I've tried several things, like having it call the same action as the "next" button over a loop or an *apply function, and I've tried putting those in several places of the server function, but nothing works. I am still a bit confused about how reactive environments work, so I wouldn't be surprised to know that's not the way to do it at all, but I can't find anything about it on the Internet.
