折叠 rowGroup 闪亮

Posted

技术标签:

【中文标题】折叠 rowGroup 闪亮【英文标题】:Collapse rowGroup Shiny 【发布时间】: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函数的第二个参数似乎没有得到尊重。 感谢您的评论,确实您是对的。调整回调允许折叠任何行。现在我只需要弄清楚如何将事件限制只对行进行分组。 有人可以帮助解决这里发布的问题。 ***.com/questions/60401871/… 【参考方案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)

【讨论】:

以上是关于折叠 rowGroup 闪亮的主要内容,如果未能解决你的问题,请参考以下文章

如何在闪亮的应用程序中折叠侧边栏面板?

如何以编程方式折叠闪亮仪表板中的框

JQuery DataTables - 行分组、求和、可折叠、导出

ag-grid 修改 Row Group 的 Header 名称

以编程方式在闪亮仪表板中切换侧边栏菜单的显示

调整操作按钮的大小会导致闪亮仪表板中的标题错位