rhandsontable freezes when within uiOutput and with user input validation

30 Views Asked by At

I have an R Shiny application that contains an rhandsontable within a uiOutput. The rhandsontable has some data validation rules. The table freezes if an invalid input is sitting in the cell (and the cell is open) and the user hits a button that changes the underlying data (e.g. a refresh / restart button).

I have found that the problem does not occur if the rhandsontable is placed directly in the UI. However this is not practical for my application.

Here is a reproducible example. Enter an invalid number (outside of the range 1:10), and don't escape the cell, just hit the restart button and the table will freeze up and no longer working until the app is restarted.


library(shiny)
library(rhandsontable)

ui <- fluidPage(
  actionButton("restart", "Restart"),
  #rHandsontableOutput("table") # this works
  uiOutput("table_UI") # this does not work
)

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

  refreshTrigger <- reactiveVal(FALSE)
  values <- reactiveValues(data = data.frame(Value = 1))

  observeEvent(input$restart, {
    # Reset the data to its initial state
    values$data <- data.frame(Value = 1)
    refreshTrigger(TRUE)
  })

  toListen <- reactive({
    list(values$data, refreshTrigger())
  })

  observeEvent(toListen(), {

    output$table_UI <- renderUI({
      rHandsontableOutput("table")
    }) # This does not work
    #rHandsontableOutput("table") # this works
    # Re-render the table
    output$table <- renderRHandsontable({
      rhandsontable(values$data) %>%
        hot_col("Value", format = "0", width = 70) %>%
        hot_validate_numeric("Value", min = 1, max = 10)
    })
    refreshTrigger(FALSE)
  })
}

shinyApp(ui = ui, server = server)
1

There are 1 best solutions below

0
On

I think your app runs into an infinite loop.

It is bad to put an output slot inside an observer. You can simply do:

server <- function(input, output, session) {
  
  Data <- data.frame(Value = 1)
  
  output$table_UI <- renderUI({
    rHandsontableOutput("table")
  }) 

  output$table <- renderRHandsontable({
    input$restart
    rhandsontable(Data) %>%
      hot_col("Value", format = "0", width = 70) %>%
      hot_validate_numeric("Value", min = 1, max = 10)
  })

}