在正确位置使用SelectInput时如何保存在DT中所做的编辑

时间:2019-07-17 09:05:52

标签: r shiny dt selectinput

使用通过SelectInput选择输入的可编辑数据表(数据包DT)时,所做的编辑不会保存在应有的位置。

选择特定变量将在第一行中显示数据表中的第50-60行。编辑它们会将编辑内容保存在第一行,而不是第50-60行。

在下面的示例中,您可以选择versicolor变量并删除setosa。然后将Petal.Length编辑为随机数。编辑应保存在第51行中,但应保存在第1行中。

我正在考虑基于索引列的解决方法,以便将编辑内容保存在行号(索引行)中。但是我不确定该怎么做。

#Packages
library(shiny)
library(shinyalert)
library(shinydashboard)
library(leaflet)
library(leaflet.extras)
library(DT)

#data
iris = iris

#Shiny-app (ui)
header = dashboardHeader(title = "SelectInput DataTable example")

sidebar = dashboardSidebar(selectInput("species", "Choose species:  ",    choices = iris$Species, selected = "setosa",  multiple = TRUE))

body = dashboardBody(fluidRow(dataTableOutput("table")))

ui = dashboardPage(skin = "red", header, sidebar, body)

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


  output$table = DT::renderDataTable(iris[iris$Species %in% input$species,], editable = TRUE)

  proxy = dataTableProxy('table')

  observeEvent(input$table_cell_edit, {
    info = input$table_cell_edit
    str(info)
    i = info$row
    j = info$col
    v = info$value
    iris[i, j] <<- DT::coerceValue(v, iris[i, j])
    replaceData(proxy, iris, resetPaging = FALSE)  # important
  })
}

shinyApp(ui = ui, server = server)

1 个答案:

答案 0 :(得分:1)

尝试一下:

#Packages
library(shiny)
library(shinydashboard)
library(DT)

#data
iris = iris

#Shiny-app (ui)
header = dashboardHeader(title = "SelectInput DataTable example")

sidebar = dashboardSidebar(selectInput("species", "Choose species: ", 
                                       choices = iris$Species, selected = "setosa",  multiple = TRUE))

body = dashboardBody(fluidRow(DT::dataTableOutput("table")))

ui = dashboardPage(skin = "red", header, sidebar, body)

# Javascript 
js <- function(rows){
  c(
    "function(settings){",
    "  var table = settings.oInstance.api();",
    sprintf("  var indices = [%s];", paste0(rows-1, collapse = ",")),
    "  table.rows(indices).remove().draw();",
    "}"
  )
}

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

  dat <- reactiveVal(iris)

  Rows <- reactive({
    which(iris$Species %in% input$species)
  })

  output$table = DT::renderDataTable({
    rows <- setdiff(1:nrow(iris), Rows())
    datatable(
      dat(), 
      editable = TRUE,
      options = list(
        initComplete = JS(js(rows))
      )
    )
  }, server = FALSE)

  observeEvent(input$table_cell_edit, {
    info = input$table_cell_edit
    info$row = Rows()[info$row+1] - 1
    dat(editData(dat(), info))
  })
}

shinyApp(ui = ui, server = server)