html - 使用 removeUI 删除多个元素/使用 tags$div() 为每个变量分配一个 id 包装多个元素

标签 html css dynamic widget shiny

有人建议我使用 insertUI here并发现这是一个很棒的功能。以下代码允许使用 insertUI 为单个或多个元素生成控件小部件,但着重于合并 removeUI 相关部分。尝试了 jQuery 选项来删除插入的 UI 元素,但没有成功。我从 Shiny dynamic UI 中找到了以下内容,即 请注意,如果您在一次调用中插入多个元素,则必须将它们包装在 tagList() 或 tags$div() 中(后一个选项的优点是您可以为其指定一个 id以便以后更容易引用或删除它)。另外,comments here给出了一些线索,即 tags$div(id="sepal.width.div", sliderInput("sepal.width.slider", ...)),但我缺少 HTML/CSS 知识阻止我前进。我正在看 (a) 用 tags$div() 包装多个小部件元素,为每个变量分配一个唯一的 id,这将在 removeUI 中使用; (b) 通过 removeUI 调用多个元素。

varnames <- names(iris[,1:4]) # names
varinit <- apply(iris[,1:4],2,median) # initival value used in slider
varmin <- apply(iris[,1:4],2,min) # min.
varmax <- apply(iris[,1:4],2,max) # max. 

ListofSelVars <<- vector(mode="character")

# control widgets for all elements
allControls <- lapply(setNames(varnames, varnames), function(x) {

   sliderInput(x, x, varmin[x], varmax[x], c(varmin[x], varinit[x]), 
               round = -2)   
})

ui <- navbarPage(
   tabPanel("Plot",
            sidebarLayout(
               sidebarPanel(
                  checkboxGroupInput("ConditioningVariables", "Conditioning variables (choose one or more):",
                                     varnames,inline = TRUE),
                  # add an action button
                  actionButton("add", "Update UI elements")
               ),
               mainPanel()
            )
   )
)

server <- function(input, output, session) {
   observeEvent(input$add, {
      insertUI(
         selector ='#add',
         where = "afterEnd",
         ui = allControls[setdiff(input$ConditioningVariables,ListofSelVars)]
      )

      ## removeUI related goes, here
      ## removeUI(selector=paste0())
      ## setdiff(ListofSelVars,input$ConditioningVariables) gives elements to be removed

      ## Global variable, keep track of elements that are selected

      ListofSelVars <<- input$ConditioningVariables

   })

}
shinyApp(ui, server)

最佳答案

这是工作代码。主要问题在于此处的名称,即 Sepal.Width。我用一个像 div.Sepal.Width 这样的 id 包裹了每个 slider ,这样它就更容易移除了。 removeUI 需要一个 jQuery 选择器,所以看起来像 #div.Sepal.Width 这样的东西会起作用,但它不起作用,因为 .本身就是一个 jQuery 选择器,意思是 class,所以我们需要对 . 进行双重转义。当然你也可以在第一次创建div时去掉.,这样就避免了麻烦...

varnames <- names(iris[,1:4]) # names
varinit <- apply(iris[,1:4],2,median) # initival value used in slider
varmin <- apply(iris[,1:4],2,min) # min.
varmax <- apply(iris[,1:4],2,max) # max. 

ListofSelVars <<- vector(mode="character")

# control widgets for all elements
allControls <- lapply(setNames(varnames, varnames), function(x) {
  tags$div(id=paste0("div.",x), sliderInput(x, x, varmin[x], varmax[x], c(varmin[x], varinit[x]), 
              round = -2))
})

ui <- fluidPage(

  titlePanel("Dynamic sliders"),

  sidebarLayout(
    sidebarPanel(
      checkboxGroupInput("ConditioningVariables", "Conditioning variables (choose one or more):",
                         varnames,inline = TRUE),
      # add an action button
      actionButton("add", "Update UI elements")
    ),

    mainPanel(
      uiOutput("plot_out")
    )
  )
)

server <- function(input, output, session) {
  observeEvent(input$add, {

    insertUI(
      selector ='#add',
      where = "afterEnd",
      ui = allControls[setdiff(input$ConditioningVariables,ListofSelVars)]
    )

    ListofRemoval <- setdiff(ListofSelVars,input$ConditioningVariables)

    for (item in ListofRemoval) {
      item = gsub(".", "\\.", item, fixed=TRUE)
      item = paste0("#div\\.", item)
      removeUI(item)
    }

    ListofSelVars <<- input$ConditioningVariables

  })

}
shinyApp(ui, server)

关于html - 使用 removeUI 删除多个元素/使用 tags$div() 为每个变量分配一个 id 包装多个元素,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40457622/

相关文章:

javascript - 如何检测网页是否由移动浏览器或应用程序打开?

html - div标签的边距问题

html - 在 chrome 66 中禁用自动完成

jquery - 重置从上到下滑动 navbar-collapse

html - 事件标签的嵌套 CSS 规则

jquery - 输入点击不起作用

html - 背景图片未覆盖整个页面

c++ - 声明动态内存语句 C++

javascript - React 下拉问题 - 如何立即停止动态创建的下拉列表的所有更新

c++ - 顺时针旋转二维数组