R Shiny: Use Onclick Option of Actionbutton on the

2020-07-10 06:26发布

问题:

I want to make a Shiny App in which the user can press an actionbutton which would then trigger some code on the server side creating a file in the www folder and then opens/downloads the file.

Suppose the file is test.txt (in my case it would be a variety of R, Excel, and exe files which will be copied from different folders on a drive to the www folder).

My first try was to use the actionbutton with the onclick option as shown below

    ui <- fluidPage(
      actionButton("showtxt", "Show/Download File", onclick = "window.open('test.txt')")
    )


    server <- function(input, output, session){
      observeEvent(input$showtxt,{
        # Write some text
        write.table(c("Test"), file = "www/test.txt")
      })
    }


    shinyApp(ui=ui,server=server)

But this doesn't work since the onclick action is done before the observevent is evaluated.

I then tried to call a function inside to the onclick option as shown below

    CreateFileAndLink <- function(){
      write.table(c("Test"), file = "www/test.txt")
      return("window.open('test.txt')")
    }

    ui <- fluidPage(
      actionButton("showtxt", "Show/Download File", onclick = CreateFileAndLink())
    )

    server <- function(input, output, session){}

    shinyApp(ui=ui,server=server)

This works but has the downside that now the file is created when upon opening the Shiny App as opposed to creating the file when the user clicks the actionbutton. This is very inefficient if I were to use this piece of code multiple times in an App with relatively large files.

Maybe it is possible to make sure that the observevent is executed before the onclick-action, or maybe use the onclick option on the server side.

Any help would be greatly appreciated!

Cheers

UPDATE:

I found out that the great shinyjs package by Dean Attali contains a onclick function that might be of help here. I tried to run the code below but it didn't work :/

    library(shinyjs)
    ui <- fluidPage(
      useShinyjs(),
      actionButton("showtxt", "Show/Download File")
    )


    server <- function(input, output, session){
      observeEvent(input$showtxt,{
        # Write some text
        write.table(c("Test"), file = "www/test.txt")

        # Call Onclick
        onclick("showtxt", "window.open('test.txt')")
      })
    }


    shinyApp(ui=ui,server=server)

回答1:

I found a solution using the onclick function from the shinyjs package.

    library(shinyjs)
    ui <- fluidPage(
      useShinyjs(),
      actionButton("showtxt", "Show/Download File")
    )


    server <- function(input, output, session){
      observeEvent(input$showtxt,{
        # Write some text
        write.table(c("Test"), file = "www/test.txt")
      })


      # Call Onclick
      onclick("showtxt", runjs("window.open('test.txt')"))
    }


    shinyApp(ui=ui,server=server) 


标签: r shiny shinyjs