使用javascript时从闪亮应用程序下载plotly graph时出错

使用javascript时从闪亮应用程序下载plotly graph时出错,javascript,r,download,shiny,plotly,Javascript,R,Download,Shiny,Plotly,我有一个闪亮的应用程序,下面显示一个绘图或表格。我对表格不感兴趣,我的问题是关于绘图部分的。当我在浏览器中使用此工具打开应用程序时,我正在尝试下载绘图。我不熟悉javascript,我想知道当我第一次按下“下载”按钮并只下载我的未下载的绘图时,如何防止它下载这个空文件 library(shiny) library(plotly) d <- data.frame(X1 = rnorm(50,mean=50,sd=10), X2 = rnorm(50,mea

我有一个闪亮的应用程序,下面显示一个绘图或表格。我对表格不感兴趣,我的问题是关于绘图部分的。当我在浏览器中使用此工具打开应用程序时,我正在尝试下载绘图。我不熟悉javascript,我想知道当我第一次按下“下载”按钮并只下载我的未下载的绘图时,如何防止它下载这个空文件

library(shiny)
library(plotly)

d <- data.frame(X1 = rnorm(50,mean=50,sd=10), 
                X2 = rnorm(50,mean=5,sd=1.5), 
                Y = rnorm(50,mean=200,sd=25))

ui <-fluidPage(
  title = 'Download Plotly',
  sidebarLayout(

    sidebarPanel(
      selectInput("S","SELECT",choices = c("Table","Plot"),selected = "Plot"),
      uiOutput('down'),
      tags$script('
              document.getElementById("down").onclick = function() {
                  var gd = document.getElementById("regPlot");
                  Plotly.Snapshot.toImage(gd, {format: "png"}).once("success", function(url) {
                  var a = window.document.createElement("a");
                  a.href = url; 
                  a.type = "image/png";
                  a.download = "plot.png";
                  document.body.appendChild(a);
                  a.click();
                  document.body.removeChild(a);                      
                  });
                  }
                  ')
    ),

    mainPanel(
      uiOutput('regPlot')

    )
  )
)

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

output$down<-renderUI({
  if(input$S=="Table"){

      output$downloadData <- downloadHandler(
        filename = function() {
          paste(input$filename, input$extension, sep = ".")
        },

        # This function writes data to a file given to it by the argument 'file'.
        content = function(file) {
          sep <- "txt"=","
          # Write to a file specified by the 'file' argument
          write.table(data.frame(mtcars), file, sep = sep,
                      row.names = FALSE)
        }

      )
      downloadButton("downloadData", "Download",class = "butt1")
  }
  else{
    output$downloadData <- downloadHandler(
      filename = function(){
        paste(paste("test",Sys.Date(),sep=""), ".png",sep="")},
      content = function(file) {
        temp_dir <- tempdir()
        tempImage <- file.path(temp_dir, 'out.png')
        file.copy('out.png', tempImage, overwrite = TRUE)
        png(file, width = 1200, height = 800, units = "px", pointsize = 12, bg = "white", res = NA)
        dev.off()
      })
    downloadButton("downloadData", "Download",class = "butt1")
  }
})  

output$regPlot<-renderUI({
  if(input$S=="Plot"){
    output$pl<-renderPlotly(
    plot_ly(d, x = d$X1, y = d$X2, mode = "markers"))
    plotlyOutput("pl")
  }
  else{
    output$tbl =  DT::renderDataTable(datatable(
      d
    ))
    dataTableOutput("tbl") 
  }
  })

}

shinyApp(ui = ui, server = server)
库(闪亮)
图书馆(绘本)

这是下载绘图的代码。代码中的一些问题

在ui.R中定义下载按钮。并参考javascript代码中的下载按钮
id
。另外,
regplot
uiOutput
元素,而不是实际的绘图。在javascript代码中,绘图由
pl
引用

下面是一个已修复问题的示例代码。如果您使用的是javascript代码,则不需要闪亮的下载处理程序。如下所示,您只需从操作按钮下载即可

您可以在此基础上通过将actionButton替换为downloadButton并在服务器上添加相应的代码来下载数据表

library(shiny)
library(plotly)
library(DT)

ui <-fluidPage(
  title = 'Download Plotly',
  sidebarLayout(

    sidebarPanel(
      selectInput("S","SELECT",choices = c("Table","Plot"),selected = "Plot"),
      actionButton("downloadData", "Download",class = "butt1"),
      tags$script('
                  document.getElementById("downloadData").onclick = function() {
                  var gd = document.getElementById("pl");
                  Plotly.Snapshot.toImage(gd, {format: "png"}).once("success", function(url) {
                  var a = window.document.createElement("a");
                  a.href = url; 
                  a.type = "image/png";
                  a.download = "plot.png";
                  document.body.appendChild(a);
                  a.click();
                  document.body.removeChild(a);                      
                  });
                  }
                  ')
      ),

    mainPanel(
      uiOutput('regPlot')

    )
      )
    )

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

  d <- data.frame(X1 = rnorm(50,mean=50,sd=10), 
                  X2 = rnorm(50,mean=5,sd=1.5), 
                  Y = rnorm(50,mean=200,sd=25))

  output$regPlot<-renderUI({
    if(input$S=="Plot"){
      output$pl<-renderPlotly(
        plot_ly(d, x = d$X1, y = d$X2, mode = "markers"))
      plotlyOutput("pl")
    }
    else{
      output$tbl =  DT::renderDataTable(datatable(
        d
      ))
      dataTableOutput("tbl") 
    }
  })
}

shinyApp(ui = ui, server = server)
库(闪亮)
图书馆(绘本)
图书馆(DT)

ui因为我不希望这个actionbutton是永久的,所以我想把它放在uiOutput中,并在服务器中创建它。但是,当我在服务器中添加javascript代码时,actionbutton就丢失了。如果没有javascript并使用downloadhandler,这难道不是dobe吗?我这里有一个问题,谢谢,我已经调整好了!