Reputation: 313
Below is a simple reproducible app. I have two tabs. Tab 1 displays a chart while Tab 2 displays a chart and table.
I have also a download button in the side bar and an Rmd document.
The question is, the resulting html page I want to download fails unless I select Tab 2. When I select Tab 2 the download works fine even if I go back to Tab 1 before downloading. Obviously this is due in part to the reactive element on Tab 2.
However, I want the download to work whether or not I visit Tab 2. In other words when the app loads I can just click the download button and the resulting html page will contain the charts and the table from both tabs.
Is there a way to preload Tab 2? As you can see, I have tried the outputOptions function with suspendWhenHidden = FALSE but it doesn't seen to work.
Any help please?
Shiny:
library(shiny)
library(rmarkdown)
data(mtcars)
ui <- fluidPage(
titlePanel("Preload Plots"),
sidebarPanel(
uiOutput("down")
),
mainPanel(
fluidRow(
tabsetPanel(
tabPanel("Panel 1",
plotOutput("plot1")
),
tabPanel("Panel 2",
uiOutput("selectList"),
plotOutput("plot2"),
tableOutput("tbl")
)
)
)
)
)
server <- function(input, output){
output$plot1 <- renderPlot({
barplot(mtcars$cyl)
})
output$selectList <- renderUI({
selectInput("selectionBox", "Select Cyl Size", unique(mtcars$cyl), selected = 4)
})
cylFun <- reactive(
mtcars[mtcars$cyl == input$selectionBox, c("mpg", "wt")]
)
output$plot2 <- renderPlot({
plot(cylFun())
})
outputOptions(output, "plot2", suspendWhenHidden = FALSE)
output$tbl <- renderTable(
table(cylFun())
)
outputOptions(output, "tbl", suspendWhenHidden = FALSE)
output$down <- renderUI({
downloadButton("downloadPlots", "Download Plots")
})
output$downloadPlots <- downloadHandler(
filename = "plots.html",
content = function(file){
params = list(p2 = cylFun())
render("plots.Rmd", html_document(), output_file = file)
}
)
}
shinyApp(ui, server
Rmarkdown:
---
title: "plots"
output: html_document
---
```{r, echo = FALSE}
barplot(mtcars$cyl)
```
```{r, echo = FALSE}
plot(params$p2)
knitr::kable(params$p2)
```
Thanks
Andrew
Upvotes: 2
Views: 2451
Reputation: 230
An easily available hack to load all tabs using your downloadButton renderUI. Using req keyword as below. This will load all the outputs and all tabs will be loaded and then appear.
output$down <- renderUI({
req(plot1,selectList,plot2,tbl)
downloadButton("downloadPlots", "Download Plots")
})
Enjoy!
Upvotes: 0
Reputation: 1758
You have the right idea, suspendWhenHidden
seems to be the key. The problem is that the Rmd rendering needs cylFun
to have a value, and cylFun
depends on the selectionBox
input value you create with renderUI
. You have the suspendWhenHidden
option for the plot and table, but these cannot be calculated without selectionBox
, and the markdown works without them.
So just add
outputOptions(output, "selectList", suspendWhenHidden = FALSE)
and it should work. You can also remove the outputOptions
for the table and plot on tab 2.
Upvotes: 1