0

I have a selectInput in a Shiny DT datatable. I needed to apply custom javascript to selectize the selectInput due to a formatting issue when using multiple = T (see other post: Shiny DT datatable using selectInput with multiple = TRUE). (As a side note, I also noticed that I must have a selectInput outside the datatable for the javascript to work, hence the hidden "dummy" selectInput; I would love to know why this is). When I do this, I am unable to vertically center the selectInput on its row. In the code below, if the initComplete line is commented out, the selectInput is vertically centered (due to the margin-bottom: 0 css), but the correct appearance and multiple selections are lost. I would appreciate help getting the selectInput vertically centered while keeping the correct formatting. Note that I've left out some additional javascript for binding/unbinding inputs to keep the code minimal.

require(shiny)
require(DT)

# Function to selectize one or more input ids
SelectizeIDs <- function(ids) {
  myStrings <- as.character(sapply(ids, function(id) {
    paste0("  $('#", id, "').selectize();")
  }))
  c(
    "function(settings){",
    myStrings,
    "}"
  )
}

shinyApp(
  ui = fluidPage(
    tags$head(tags$style(HTML("td .form-group {margin-bottom: 0;}"))),
    # Dummy selectInput is needed for SelectizeIDs() to work, not sure why
    div(style = "display: none;", selectInput(inputId = "dummy", label = NULL, choices = 1:2)),
    DT::dataTableOutput("mytable")
  ),
  server = function(input, output, session) {

    output$mytable <- DT::renderDataTable({
      DT::datatable(
        data = data.frame(
          Col1 = as.character(selectInput(
            inputId = "id1",
            label = NULL,
            choices = letters,
            multiple = T
          ))
        ),
        escape = F,
        selection = "none",
        options = list(
          initComplete = JS(SelectizeIDs("id1"))
        )
      ) 
    })
  }
)

Here is a screenshot using the code above showing the selectInput properly formatted but not vertically centered: enter image description here

Here is a screenshot using the code above but commenting out the initComplete line, showing the selectInput improperly formatted but vertically centered: enter image description here

Ben Ernest
  • 445
  • 3
  • 14

1 Answers1

1

Without the dummy selectize input, the selectize.js library is not included.

The CSS:

    tags$head(tags$style(
      HTML("td .form-group {margin-bottom: 0;} td .selectize-input {position: absolute; top: 50%; transform: translateY(-50%);} td .selectize-control {margin-bottom: 0;}")
    )),
Stéphane Laurent
  • 75,186
  • 15
  • 119
  • 225
  • Very nice, thanks. In my actual application I have other Shiny inputs on other rows, so I used `datatable() %>% formatStyle(..., lineHeight = "32px")` to set a constant line height so there are consistent margins around each input. – Ben Ernest Nov 30 '22 at 02:34
  • 1
    @BenErnest You can use the nice `remove_button` plugin: `paste0(" $('#", id, "').selectize({plugins: ['remove_button']});")`. – Stéphane Laurent Nov 30 '22 at 02:47
  • Excellent, remove_button looks great! – Ben Ernest Nov 30 '22 at 03:09
  • ran into an issue with wide tables when I selectize the selectInputs with extra JavaScript. https://stackoverflow.com/questions/76709796/datatable-with-selectinputs-resets-back-to-left-after-selection. Any chance you could take a look? – Ben Ernest Jul 18 '23 at 20:18