如何根据被动输入调用闪亮模块?

时间:2018-03-29 10:18:37

标签: r module shiny reactive-programming

我想基于无功输入调用嵌套模块服务器,并在主面板上显示返回输出。当函数callModule依赖于被动输入时,它似乎不起作用。

我认为这是一个常见的情况,当你构建一个复杂的应用程序但我一直在努力寻找解决方案。

下面是我的代码,或者您可以通过在R:

中输入以下命令来运行该应用程序

光泽:: runGist( “23abbb50a1df6a91af990a7401919044”)

提前谢谢。

library(shiny)

# innerModule 1
csvFile_Input <- function(id, label = ".csv file") {
  # Create a namespace function using the provided id
  ns <- NS(id)
  tagList(
    fileInput(ns("file"), label),
    checkboxInput(ns("heading"), "Has heading")
  )
}


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


  userFile <- reactive({
    req(input$file)
  })

  dataframe <- reactive({

    read.csv(userFile()$datapath,
             header = input$heading)
  })

  observe({
    msg <- sprintf("File %s was uploaded", userFile()$name)
    cat(msg, "\n")
  })



  return(dataframe)

}

# innerModule 2
othersource_Input <- function(id) {
  ns <- NS(id)
  textInput("text", label = h3("From the web"), value = "http://www.stats.ox.ac.uk/pub/datasets/csb/ch11b.dat")
}

othersource <- function(input, output, session){
  library(data.table)

  dataframe <- reactive({
    req(input$text)
    fread(input$text)
  })

   return(dataframe)
}

loadDataInput <- function(id){
  ns <- NS(id)
  wellPanel(
    tagList(
      uiOutput(ns("selectSource")),
      uiOutput(ns("text"))
    )
  )


}



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

  ns <- session$ns

  # Select source from user or from wibi
  output$selectSource<-renderUI(
    radioButtons(
      ns("dt"), "Data source",
      c(csvFile = "fromCSV", web = "fromWeb"),
      inline = TRUE
    )
  )

  dtype <- reactive({
    req(input$dt)
  })


  output$text <- renderUI({
    req(dtype())
    if(dtype() == "fromCSV"){
      csvFile_Input(ns("user"))
    } else if (dtype() == "fromWeb"){
      othersource_Input(ns("web"))
    }
  })


 data <- reactive({
    req(dtype())
    if(dtype() == "fromCSV"){
      callModule(csvFile, "user")
    } else if (dtype() == "fromWeb"){
      callModule(othersource, "web")
    }
  })


  output$viewinput <- renderPrint({
    print(data())
  })


  return(data)

}

loadDataOutput <- function(id){
  ns <- NS(id)
  verbatimTextOutput(ns("viewinput"))
}


ui <- fluidPage(
  titlePanel(paste("Calling module based on reactive input")),
  sidebarLayout(
    sidebarPanel(
      loadDataInput("test")
    ),
    mainPanel(
      loadDataOutput("test")
    )
  )
)

server <- function(input, output) {
  callModule(loadData, "test")
}

shiny::shinyApp(ui = ui, server = server)

1 个答案:

答案 0 :(得分:0)

您不应在callModulerenderXXX个函数内调用reactive。以下更改对我有用。

csvinput <- callModule(csvFile, "user")
otherinput <- callModule(othersource, "web")

data <- reactive({
  req(dtype())
  if(dtype() == "fromCSV"){
    csvinput()
  } else if (dtype() == "fromWeb"){
    otherinput()
  }
})

此外,您应该在ns("text")中使用othersource_Input。如果您想进一步解释,请提供一个最小的例子。