【问题标题】:Collapse rowGroup Shiny折叠 rowGroup 闪亮
【发布时间】:2020-05-10 19:06:38
【问题描述】:

我有一个相当简单的应用程序(如下),我尝试使用 DataTable 输出分组表,并能够折叠组。我找到了在 jQuery here 中实现的解决方案,但我不知道如何将如此复杂的实现移到 R 中。

目前,我可以在一个组内折叠,但不能在整个组内折叠。有什么提示可以在 Shiny 中实现吗?

我的申请:

library(shiny)
library(DT)
library(shinyjs)

ui <- fluidPage(

   # Application title
   titlePanel("Collapse/Expand table"),

            mainPanel(
          DTOutput("my_table")

      )
   )


server <- function(input, output) {

    output$my_table<-DT::renderDataTable({

        datatable(mtcars[1:15,1:5],
                  extensions = 'RowGroup', 
                  options = list(rowGroup = list(dataSrc=c(3)),
                                 pageLength = 20),
                  callback = JS("
                                table.on('click', 'tr', function () {
                                    var rowsCollapse = $(this).nextUntil('.group');
                                    $(rowsCollapse).toggleClass('hidden');
                                 });"))
    })
}

# Run the application 
shinyApp(ui = ui, server = server)

编辑

给定 AEF 注释,可以调整代码以指定即使在单击表 body 后也必须发生。这确实会折叠任何行,直到下一组。剩下的部分是将点击限制在组行上。 回调应该是现在:

callback = JS("$('#DataTables_Table_0 tbody').on('click', 'tr', function () {
 $(this).nextUntil('.group').toggleClass('hidden');});"))

【问题讨论】:

  • 我对javascript不太了解,所以一直没搞清楚,所以我会告诉你我认为问题出在哪里:当你点击数据表的分组行时,如果你查看浏览器的控制台会有一个错误信息:Uncaught TypeError: Cannot read property 'row' of undefined。我建议在您的问题中添加javascript 标签,看看您是否可以获得额外的帮助,也许是github.com/rstudio/DT 上的问题?
  • 似乎问题在于事件处理程序附加到表本身而不是行。所以你给on函数的第二个参数似乎没有得到尊重。
  • 感谢您的评论,确实您是对的。调整回调允许折叠任何行。现在我只需要弄清楚如何将事件限制只对行进行分组。
  • 有人可以帮助解决这里发布的问题。 stackoverflow.com/questions/60401871/…

标签: javascript jquery r shiny datatables


【解决方案1】:

原来是DT的javascript代码的一个bug。有一个单击事件侦听器将记录单击单元格的所有信息。但是,RowGroup 扩展会创建不属于原始数据集的新行并导致错误。 此错误会停止进一步的 javascript 执行。

在您的情况下,tr.group 事件不起作用,因为之前的单元格单击事件引发了错误。

我们已经修复了这个错误,DT 的开发版本应该可以使用以下代码:

library(shiny)
library(DT)
ui <- fluidPage(# Application title
  titlePanel("Collapse/Expand table"),
  mainPanel(DTOutput("my_table")))

callback_js <- JS(
  "table.on('click', 'tr.dtrg-group', function () {",
  "  var rowsCollapse = $(this).nextUntil('.dtrg-group');",
  "  $(rowsCollapse).toggleClass('hidden');",
  "});"
)

server <- function(input, output) {
  output$my_table <- DT::renderDT({
    datatable(
      mtcars[1:15, 1:5],
      extensions = 'RowGroup',
      options = list(rowGroup = list(dataSrc = 3), pageLength = 20),
      callback = callback_js,
      selection = 'none'
    )
  })
}

# Run the application
shinyApp(ui = ui, server = server)

再次感谢您的报告!

DT 的 Github issue 代码:https://github.com/rstudio/DT/issues/759

【讨论】:

  • 在上面的示例中使用从 remotes::install_github('rstudio/DT') 安装的 DT 版本 0.13,我不得不将“group”更改为“dtrg-group”。我注意到在检查它时类名不同。更改后效果很好。
【解决方案2】:

关于这一点的另一个说明。 我注意到在标准的流体页面等中,这按预期工作。 但是,当我开始在 htmlTemplate 中使用它时,它就停止工作了。

在此过程中,它丢失了 .hidden 类,我不得不手动添加它。

.hidden {
  display: none !important;
}

然后它按预期工作。

【讨论】:

    【解决方案3】:

    感谢 AEF 的评论,我能够归结为问题。该事件必须由一个用户点击正文 $('#DataTables_Table_0 tbody') 并且仅在具有组标识符 'tr.group' 的行上发生。

    必须调整最终回调以将这两个条件都考虑在内。

    因此,具有可折叠行的应用程序如下所示:

    library(shiny)
    library(DT)
    library(shinyjs)
    
    ui <- fluidPage(
    
       # Application title
       titlePanel("Collapse/Expand table"),
    
                mainPanel(
              DTOutput("my_table")
    
          )
       )
    
    
    server <- function(input, output) {
    
        output$my_table<-DT::renderDataTable({
    
            datatable(mtcars[1:15,1:5],
                      extensions = 'RowGroup', 
                      options = list(rowGroup = list(dataSrc=c(3)),
                                     pageLength = 20),
                      callback = JS("
                                    $('#DataTables_Table_0 tbody').on('click', 'tr.group', function () {
                                        var rowsCollapse = $(this).nextUntil('.group');
                                        $(rowsCollapse).toggleClass('hidden');
                                     });"))
        })
    }
    
    # Run the application 
    shinyApp(ui = ui, server = server)
    

    【讨论】:

      【解决方案4】:

      正如@David Joequera 在 cmets 中所提到的,这是一个 JavaScript 错误,其中 Datatable 的默认事件处理程序之一会引发错误,因为 Group 行中不存在行属性。

      作为一种解决方法,我们可以删除此事件处理程序,以便隐藏的事件处理程序可以工作。

      另外,我建议您仅使用事件处理程序来定位组行,以便您只能完全关闭和打开组,而不能半隐藏组。您可以通过简单地将“.group”添加到您的事件侦听器目标来实现此目的。 导致这段代码:

      table.on('click', 'tr.group', function () {
         var rowsCollapse = $(this).nextUntil('.group');
         $(rowsCollapse).toggleClass('hidden');
      })
      

      为了删除事件处理程序,我们需要等到表被正确加载并且有问题的事件处理程序被附加,所以我建议使用一个小的超时。 1000 毫秒对我来说效果很好,不应该带来任何可用性问题。 所以将此代码添加到回调应该可以解决问题:

      setTimeout(function(){$('#DataTables_Table_0').off('click.dt','tbody td')},1000);
      

      请注意,要删除的 DataTable 的 ID 可能会在您的最终/实际解决方案中发生变化

      生成此演示代码:

      library(shiny)
      library(DT)
      library(shinyjs)
      
      ui <- fluidPage(
      
        # Application title
        titlePanel("Collapse/Expand table"),
      
        mainPanel(
          DTOutput("my_table")
      
        ),
      )
      
      
      server <- function(input, output) {
      
      output$my_table<-DT::renderDataTable({
      
      datatable(mtcars[1:15,1:5],
                extensions = 'RowGroup', 
                options = list(rowGroup = list(dataSrc=c(3)),
                               pageLength = 20),
                callback = JS("
                                 setTimeout(function(){$('#DataTables_Table_0').off('click.dt','tbody td')},1000);
                                 table.on('click', 'tr.group', function () {
                                      var rowsCollapse = $(this).nextUntil('.group');
                                      $(rowsCollapse).toggleClass('hidden');
                                   });"))
      })
      
      
      
      }
      
      # Run the application 
      shinyApp(ui = ui, server = server)
      

      【讨论】:

        猜你喜欢
        • 2016-05-12
        • 2019-11-06
        • 2021-09-05
        • 1970-01-01
        • 2018-03-06
        • 2023-04-06
        • 2019-11-13
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多