【问题标题】:Unable to select multiple columns using SelectInput button in ShinyApp无法使用 ShinyApp 中的 SelectInput 按钮选择多列
【发布时间】:2019-05-01 11:30:58
【问题描述】:

我正在使用 R 构建 shinyApp。目前我正在使用selectinput 来选择多个区域/列,方法是设置multiple=TRUE。但由于某些不可预见的原因,它无法正常工作。 它仅在我将 ALL 放入选择区域 时才有效。 我相信我的问题在于服务器的反应部分。我附上了我的代码如下。有人可以看看他们,让我知道他们有什么问题。非常感谢:)

  **Updated Codes**

  library(shiny)
  library(tidyr)
  library(dplyr)
  library(readr)
  library(DT)

  data_table<-mtcars[,c(2,8,1,3,4,5,9,6,7, 10,11)]

  data_table$disp<-NULL

  names(data_table)[3:10]<- rep(x = 
c('TS_lhr_Wave_1','TS_isb_Wave_2','TS_quta_Wave_1','TS_karach_Wave_2',                                                                            

'NTS_lhr_Wave_1','NTS_isb_Wave_2','NTS_quta_Wave_1','NTS_karach_Wave_2'), 
                              times=1, each=1)   

  # Define UI
  ui <- fluidPage(
  downloadButton('downLoadFilter',"Download the filtered data"),

  selectInput(inputId = "cyl",
              label = "cyl:",
              choices = c("All",
                          unique(as.character(data_table$cyl))),
              selected = "All",
              multiple = TRUE),


  checkboxGroupInput(inputId = "regions", label = "choose region",
                     choices =c("All", "lhr", "isb", "quta", "karach"), 
                     inline = TRUE,   selected = c("All")),


  checkboxGroupInput(inputId = "waves", label = "choose wave",
              choices =c("All", "Wave_1", "Wave_2"), inline = TRUE,
              selected = c("All")),


  DT::dataTableOutput('ex1'))


  # Define Server
  server <- function(input, output) {

  thedata <- reactive({

    if(input$cyl != 'All'){
      data_table<-data_table[data_table$cyl %in%   input$cyl,] }  


    #region
    cols <- c(1, 2)
    # print(input$regions)
    if  ('All' %in% input$regions){
      cols <- 1:ncol(data_table)
    }
    else{
      if  ('lhr' %in% input$regions){
        cols <- c(cols, c(3,7))

      }  
      if  ('isb' %in% input$regions){
        cols <- c(cols, c(4,8))

      }
      if  ('quta'  %in%  input$regions){
        cols <- c(cols, c(5,9))

      }
      if  ('karach'  %in%  input$regions){
        cols <- c(cols, c(6,10))

      }}                

    #else
    data_table<-data_table[,cols, drop=FALSE] 




    #waves
    colss <- c(1, 2)
    # print(input$regions)
    if  ('All' %in% input$waves){
      colss <- 1:ncol(data_table)
    }
    else{
      if  ('Wave_1' %in% input$waves){
        colss <- c(colss, c(3,5,7, 9))
      }  

      if  ('Wave_2'  %in%  input$waves){
        colss <- c(colss, c(4,6, 8, 10))
      }}                

    #else
    data_table<-data_table[,colss, drop=FALSE] 


  }) 


  output$ex1 <- DT::renderDataTable(DT::datatable(filter = 'top',
                                                  escape = FALSE, 
                                                  options = list(                                                                      


scrollX='500px',autoWidth = TRUE),{
                                                      thedata()   }))

  output$downLoadFilter <- downloadHandler(
    filename = function() {
      paste('Filtered data-', Sys.Date(), '.csv', sep = '')  },
    content = function(path){
      write_csv(thedata(),path)   })}

  shinyApp(ui = ui, server = server)

【问题讨论】:

    标签: r datatable shiny dashboard dt


    【解决方案1】:

    所以你假设错误在服务器的反应部分是正确的,我发现了两个主要问题。

    1. 当您选择多个区域时,input$regions 是一个包含多个字符的向量,这就是为什么当 R 计算表达式 input$regions == 'lhr' 时,它仅将 input$regions 的第一个元素与 @ 进行比较987654324@ 并在控制台中打印出警告。

    2. 1234563 ,然后在评估第二个if时询问第八列@

    建议:在App开发过程中可以添加打印语句作为调试方法,在运行App的时候注意控制台看看到底发生了什么。我添加了一条打印语句作为评论,如果您想取消评论并尝试一下。

    thedata <- reactive({
    
    if(input$cyl != 'All'){
      data_table <- data_table[data_table$cyl %in% input$cyl,] }  
    
    #region
    all_cols <- names(data_table)
    region_cols <- c("cyl", "vs" )
    # print(input$regions)
    if  ('All' %in% input$regions){
      region_cols <- names(data_table)
    }
    else{
      if  ('lhr' %in% input$regions){
        region_cols <- c(region_cols, all_cols[grep('lhr', all_cols)])
    
      }  
      if  ('isb' %in% input$regions){
        region_cols <- c(region_cols, all_cols[grep('isb', all_cols)])
    
      }
      if  ('quta'  %in%  input$regions){
        region_cols <- c(region_cols, all_cols[grep('quta', all_cols)])
    
      }
      if  ('karach'  %in%  input$regions){
        region_cols <- c(region_cols, all_cols[grep('karach', all_cols)])
    
      }}                
    
    #waves
    waves_cols <- c("cyl", "vs" )
    # print(input$regions)
    if  ('All' %in% input$waves){
      waves_cols <- names(data_table)
    }
    else{
      if  ('Wave_1' %in% input$waves){
        waves_cols <- c(waves_cols, all_cols[grep('Wave_1', all_cols)])
      }  
    
      if  ('Wave_2'  %in%  input$waves){
        waves_cols <- c(waves_cols, all_cols[grep('Wave_2', all_cols)])
      }}                
    # print(intersect(region_cols, waves_cols))
    data_table <- data_table[,intersect(region_cols, waves_cols), drop=FALSE]
    })
    

    至于评论中的问题,似乎我在选择"All"时忘记添加if语句(:P),它现在的工作方式是一旦选择“全部”就不需要了评估另一个 if 语句。

    现在前两列总是被选中(而不是重复),无论是否选择了任何区域。

    【讨论】:

    • 非常感谢你,伙计:) 出现了一个小问题,当我选择“全部”时,我什么也得不到。并且还有“cyl”和“vs”的重复。你能看看他们吗?非常感谢:)
    • 嗨,伙计,我非常感谢您为使代码正常工作所付出的努力,您的天才:) 我已经更新了代码并添加了 checkboxGroupinput 而不是 selectinput。剩下的最后一件事是:如果我在“选择区域”和“选择波浪”中选择任何东西,我会得到一个错误。但是,如果我在一个中选择“全部”,那么我会得到结果。有没有办法解决?谢谢
    • 您再次面临我在回答中提到的第二个问题,当您到达波浪部分时,data_table 变量会发生变化。如果您只有 4 列,则不能要求第 7 列。在处理reactive() 时,您拥有的过滤器越多,您就应该越小心。如果您按名称选择列可能会有所帮助,可能类似于 all_cols &lt;- names(data_table); if(......) cols &lt;- all_cols[grep('Wave_1', all_cols)]
    • 谢谢大佬,可以更新代码吗?真的很感激:)
    • 非常感谢你,伙计。你简直太棒了!我非常感谢你:) 最好的问候
    猜你喜欢
    • 2019-06-19
    • 2019-06-08
    • 2019-05-01
    • 2021-03-31
    • 1970-01-01
    • 2018-09-17
    • 2018-07-08
    相关资源
    最近更新 更多