2017-10-05 19 views
1

我有一個簡單的玩具示例,使用add/removeBtn模塊來添加和刪除「第一個」模塊的UI。我需要跟蹤添加/刪除被點擊的次數。如果我不使用模塊,這很容易,但我試圖在嵌套模塊的上下文中執行此操作。代碼在下面,但基本上,我似乎無法訪問主服務器函數中addRmBtnServer()的返回值。我相信這是一個簡單的修復,但我已經嘗試了很多方法,但似乎無法訪問我對addRmBtnServer()的調用結果。謝謝!R Shiny:如何將閃亮模塊的反應值返回到主服務器功能?

library(shiny) 

firstUI <- function(id) { uiOutput(NS(id, "first")) } 

firstServer <- function(input, output, session, a) { 

    output$first <- renderUI({ 
     selectInput(session$ns("select"), h4("Select"), paste0(isolate(a()),letters[1:4])) 
    }) 
} 

removeFirstUI <- function(id) { 
    removeUI(selector = paste0('#', NS(id, "first"))) 
} 

addRmBtnUI <- function(id) { 
    ns <- NS(id) 

    tags$div(
    actionButton(inputId = ns('insertParamBtn'), label = "Add"), 
    actionButton(ns('removeParamBtn'), label = "Remove"), 
    hr(), 
    tags$div(id = ns('placeholder')) 
) 
} 

addRmBtnServer <- function(input, output, session, moduleToReplicate, ...) { 
    ns = session$ns 

    params <- reactiveValues(btn = 0) 

    observeEvent(input$insertParamBtn, { 
     params$btn <- params$btn + 1 

     callModule(moduleToReplicate$server, id = params$btn, ...) 
     insertUI(
       selector = paste0('#', ns('placeholder')), 
       ui = moduleToReplicate$ui(ns(params$btn)) 
       ) 
    }) 

    observeEvent(input$removeParamBtn, { 
     moduleToReplicate$remover(ns(params$btn)) 
     params$btn <- params$btn - 1 
    }) 

    return(params$btn) 
} 

ui <- fluidPage(
      addRmBtnUI("addRm"), 
      textInput("a", label = "a", value = 1, width = '150px'), 
      verbatimTextOutput("view", placeholder = TRUE) 
     ) 

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

    pars <- callModule(
    addRmBtnServer, id = "addRm", 
    moduleToReplicate = list(
     ui = firstUI, 
     server = firstServer, 
     remover = removeFirstUI 
     ), 
    ) 

    output$view <- renderText({ pars() }) 

} 

shinyApp(ui = ui, server = server) 
+0

您可以使用服務器功能的返回值傳遞觀察值(輸入)。首先你從'fisrtServer'傳遞給'addRmBtnServer',然後從'addRmBtnServer'傳遞到'server'上下文。看到我的答案[這裏](https://stackoverflow.com/questions/46555355/passing-data-within-shiny-modules-from-module-1-to-module-2/46555851#46555851) –

回答

1

如評論所述,您可以將值作爲返回值傳遞給相應的服務器功能。下面有一個工作示例。我遺漏了firstUI,firstServerremoveFirstUI實現,因爲它們與您的問題無關。

library(shiny) 

addRmBtnUI <- function(id) { 
    ns <- NS(id) 

    tags$div(
    actionButton(inputId = ns('insertParamBtn'), label = "Add"), 
    actionButton(ns('removeParamBtn'), label = "Remove"), 
    hr(), 
    tags$div(id = ns('placeholder')) 
) 
} 

addRmBtnServer <- function(input, output, session, moduleToReplicate, ...) { 
    ns = session$ns 

    params <- reactiveValues(btn = 0) 

    observeEvent(input$insertParamBtn, { 
    params$btn <- params$btn + 1 

    callModule(moduleToReplicate$server, id = params$btn, ...) 
    insertUI(
     selector = paste0('#', ns('placeholder')), 
     ui = moduleToReplicate$ui(ns(params$btn)) 
    ) 
    }) 

    observeEvent(input$removeParamBtn, { 
    moduleToReplicate$remover(ns(params$btn)) 
    params$btn <- params$btn - 1 
    }) 

    return(reactive({params$btn})) 
} 

ui <- fluidPage(
    addRmBtnUI("addRm"), 
    verbatimTextOutput("view", placeholder = TRUE) 
) 

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

    pars <- callModule(
    addRmBtnServer, id = "addRm", 
    moduleToReplicate = list(
     ui = function(...){}, 
     server = function(...){}, 
     remover = function(...){} 
    ) 
) 
    output$view <- renderText({ pars() }) 
} 

shinyApp(ui = ui, server = server)