updateTextAreaInput(). How to update rows attribute?


#1

I would like to update the high of a widget created by textAreaInput() function according to another input. I found the updateTextAreaInput() function, but unlikely it does not incorporate the possibility to change “rows” argument.

A minimal example would be:

library(shiny)

ui <- fluidPage(

  numericInput("rows", "Number of lines", 10),  
  textAreaInput("text", "Enter the text here", rows=10)
  
)

server <- function(input, output, session){
  
  observe({
    updateTextAreaInput(session, "text", rows = input$rows) # this gives an error (argument rows does not exist)...
  })
  
}

shinyApp(ui, server)

#2

Could you put the call to textAreaInput in the server, and use uiOutput in the UI? I that way you can re-create the UI dynamically. One problem of couse is that the content of the textAreaInput may get lost in the re-creation, so you would have to cache it.


#3

This seems to work:


library(shiny)

ui <- fluidPage(
  
  numericInput("rows", "Number of lines", 10),  
  uiOutput("text")
  
)

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

  # Define a reactive to preserve the value of the text area on updates.
  Text <- reactiveValues(
    Area = ""
  )
  
  # Event to update the reactive value when textArea changes
  observeEvent(input$textArea,
               Text$Area <- input$textArea)
  
  output$text <- 
    renderUI({
      textAreaInput(inputId = "textArea", 
                    label = "Enter the text here", 
                    value = Text$Area,
                    rows = input$rows)
    })
}

shinyApp(ui, server)

#4

Although the use of renderUI and uiOutput could solve my problem, I do not want to redo the input widget.
See the example below, where the textInput text introduced by the user is replaced by asterisks except the last character as he/she is typing.
Notice, from the example, that when the user types on the second textInput he/she must click every time in textInput window to type a new character, while this is not necessary for the first textInput.
In my case, I would like textAreaInput height fits the text while the user is typing. So, every linebreak “cols” attribute increases a unit, without having to click every time on the textInputArea window, which may very tedious for the user.

library(shiny)

ui <- fluidPage(

textInput(“pass”, “Enter password (update)”, “”),
uiOutput(“passui”)

)

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

observeEvent(input$pass,{
if (length(input$pass)){
pass <- strsplit(input$pass,split="")[[1]]
pass[-length(pass)] <- “*“
ast <- paste(pass, collapse=””)
} else {
ast <- “”
}
updateTextInput(session, “pass”, value=ast)
})

output$passui <- renderUI({
if (length(input$pass2)){
pass <- strsplit(input$pass2,split="")[[1]]
pass[-length(pass)] <- “*“
ast <- paste(pass, collapse=””)
} else {
ast <- “”
}
textInput(“pass2”, “Enter password (renderUI)”, value=ast)
})

}

shinyApp(ui, server)