actionButton in RShiny : alternative to reset value

4,567 views
Skip to first unread message

Matt

unread,
Jun 16, 2014, 9:28:43 AM6/16/14
to shiny-...@googlegroups.com
I've read on topics that it's not possible to reset value of an actionButton with Shiny Package, but I couldn't find any trick to solve my problem.

I'd like to delete the text and the button in the main panel within this code :

library(shiny)
shinyUI(fluidPage(
    titlePanel("Trying to reset text !"),
    sidebarLayout(
        sidebarPanel(
            actionButton("button1","Print text")
        ),
        mainPanel(
          textOutput("textToPrint"),
          br(),
          uiOutput("uiButton2")
        )
    )
))
shinyServer(function(input, output) {
    output$textToPrint <- renderText({ 
        if(input$button1==0) (return("")) 
        else (return("Button clicked"))
    })
    output$uiButton2 <- renderUI({
        if(input$button1==0) (return ())
        else (return(actionButton("button2","Reset text and this button")))
    })
})

What is the alternative to impossible input$button1 = 0 ?

Thanks in advance for your help,

Matt

Mart Vogel

unread,
Jun 16, 2014, 10:10:08 AM6/16/14
to shiny-...@googlegroups.com
I'm not totally sure what you are trying to do, but it sounds like you could easily solve it with some javascript

Matt

unread,
Jun 16, 2014, 10:34:29 AM6/16/14
to shiny-...@googlegroups.com
I wish I click on button2 and it executes some code to replace "Print text" by "" and remove actionButton "button2".
I wanted to reset the value of input$button1 to 0, but it's not permitted.

I guess it's possible to do it without Javascript, but I'm curious about your method too.

Mart Vogel

unread,
Jun 16, 2014, 11:15:52 AM6/16/14
to shiny-...@googlegroups.com
My javascript knowledge is not really up to date, but you probably could use something like this. At least I used a lot of similar constructions in my shiny app.

var message = "Print text";

$('button2').live('click', function(evt) {
  var message = "Button clicked";
  $('button2').hide();
  $('input$button1').val = null;
})


On Monday, June 16, 2014 4:34:29 PM UTC+2, Matt wrote:
I wish I click on button2 and it executes some code to replace "Print text" by "" and remove actionButton "button2".
I wanted to reset the value of input$button1 to 0, but it's not permitted.

I guess it's possible to do it without Javascript, but I'm curious about your method too.


Le lundi 16 juin 2014 16:10:08 UTC+2, Mart Vogel a écrit :
I'm not totally sure what you are trying to do, but it sounds like you could easily solve it with some javascriptbloemen.jpg

Joe Cheng

unread,
Jun 17, 2014, 7:36:01 PM6/17/14
to Matt, shiny-...@googlegroups.com
I believe this problem would be very tricky to solve and maintain if you could set input$button1 = 0. The following approach is simpler and more robust. We introduce a reactive variable shouldShow that controls whether the text and button are showing or not. Clicking each button sets that variable, and the outputs are keyed off of that variable.

This is the best way to think of actionButtons IMHO, as having a side effect on your application--not as a counter variable. That's why I have resisted adding the ability to set the value to 0, I really believe there's always a better solution when you think of the buttons as emitters of click events rather than having a meaningful value.

shinyServer(function(input, output) {
    values <- reactiveValues(shouldShow = FALSE)

    observe({
      if (input$button1 == 0)
          return()
      values$shouldShow = TRUE
    })
    observe({
      if (is.null(input$button2) || input$button2 == 0)
          return()
      values$shouldShow = FALSE
    })

    output$textToPrint <- renderText({ 
        if (values$shouldShow)
          "Button clicked"
    })
    output$uiButton2 <- renderUI({
        if (values$shouldShow)
            actionButton("button2","Reset text and this button")
    })
})

--
You received this message because you are subscribed to the Google Groups "Shiny - Web Framework for R" group.
To unsubscribe from this group and stop receiving emails from it, send an email to shiny-discus...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Matt

unread,
Jun 18, 2014, 4:28:09 AM6/18/14
to shiny-...@googlegroups.com
Thank you very much Joe, your answer is really what I was looking for.
Also, thanks Mart, interesting to see that Javascript can combine with Shiny, but I'm not used to it right now, I'll have a look later ;).

Matt

O. Delaigue

unread,
Jan 31, 2017, 9:37:33 AM1/31/17
to Shiny - Web Framework for R
I'm sorry, but I have the same problem as others with not being able to reset the value of an actionButton.
Once the button is clicked, I would like to be able to set my parmeter by hand using sliderInput (and reboot the label of the button).
Here is a simplified example of my situation (in fact I have several parameters used to calibrate  a model by hand or automatically) :


ui <- fluidPage(
  sliderInput(inputId = "Param", label = "Free Param", min = 0, max = 10, value = 0),
  actionButton(inputId = "AutoParam", label = "Find the optimal Param"),
  plotOutput(outputId = "ParamPlot")
)

server <- function(input, output, session) {
  output$ParamPlot <- renderPlot({
    if (input$AutoParam > 0) {
      updateSliderInput(session, inputId = "Param", value = 5)
      updateActionButton(session, inputId = "AutoParam", label = "Param set to 5")
    }
    plot(input$Param, input$Param, main = input$Param,
         xlim = c(0, 10), ylim = c(0, 10))
  })
}

shinyApp(ui, server)


Matthieu

unread,
Jan 31, 2017, 10:28:16 AM1/31/17
to Shiny - Web Framework for R
Try to use Reactive Values. Have a look to the following code:

ui <- fluidPage(
  sliderInput(inputId = "Param", label = "Free Param", min = 0, max = 10, value = 0),
  actionButton(inputId = "AutoParam", label = "Find the optimal Param"),
  plotOutput(outputId = "ParamPlot")
)

server <- function(input, output, session) {
  v <- reactiveValues(valueButton = 0) #
  
  # Each time button is click, add 1 to custom value of the button
  observeEvent(input$AutoParam, {
    v$valueButton = v$valueButton + 1 
    updateSliderInput(session, inputId = "Param", value = 5)
    updateActionButton(session, inputId = "AutoParam", label = "Param set to 5")
  })
  
  # Change on sliderInput
  observeEvent(input$Param, {
    # If change on slider is because of button, v$valueButton==1
    if(v$valueButton==0) {
      updateActionButton(session, inputId = "AutoParam", label = "Find the optimal Param")
    } 
    # reset value of valueButton
    v$valueButton = 0
  })
  
  output$ParamPlot <- renderPlot({

O. Delaigue

unread,
Feb 3, 2017, 3:11:01 AM2/3/17
to Shiny - Web Framework for R
Thank you Matthieu,  that's exactly what I needed!
I will try to adapt it to my real code.

Joe Cheng

unread,
Feb 3, 2017, 6:59:55 PM2/3/17
to O. Delaigue, Shiny - Web Framework for R
Not even reactiveValues is needed. You should just use an observeEvent.

observeEvent(input$AutoParam, {
updateSliderInput(...) # etc.
})
On Fri, Feb 3, 2017 at 12:11 AM O. Delaigue <arz...@hotmail.fr> wrote:
Thank you Matthieu,  that's exactly what I needed!
I will try to adapt it to my real code.

--
You received this message because you are subscribed to the Google Groups "Shiny - Web Framework for R" group.
To unsubscribe from this group and stop receiving emails from it, send an email to shiny-discus...@googlegroups.com.

O. Delaigue

unread,
Mar 13, 2017, 11:53:32 AM3/13/17
to Shiny - Web Framework for R, arz...@hotmail.fr
Thank you Joe!.

I have an other relative question.
In my case I need to use the eventReactive()
function instead of observeEvent() because I want to use objects (VAL and IDX in my example) in my plot and my table. In addition I have to know if this object comes from after a click on the actionButton in order to get the right result, so I think I have to use the reactiveValues() function.
To get the results
(VAL and IDX) my plot and my table, I think that I have to put the eventReactive() and the test on the value of the reactiveValues() inside a global reactive().
But beacause of the using of reactiveValues()and reactive() it is no possible to use the actionButton:

ui <- fluidPage(
  sliderInput
("Param1", label = "Param 1",

              min
=  0,
              max
= 10,
              value
= 0),

  sliderInput
("Param2", label = "Param 2",

              min
=  0,
              max
= 10,
              value
= 0),

  sliderInput
("Param3", label = "Param 3",

              min
=  0,
              max
= 10,
              value
= 0),

  sliderInput
("Param4",  label = "Param 4",

              min
=  0,
              max
= 10,
              value
= 0),
  actionButton
(inputId = "AutoParam", label = "Find the optimal Param"),

  plotOutput
(outputId = "ParamPlot"),
  tableOutput
("Criteria")

)

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

 
  RES
<- reactive({

   
    v
<- reactiveValues(valueButton = 0)
   
   
# Each time button is click, add 1 to custom value of the button

    MOD2
<- eventReactive(input$AutoParam, {

      v$valueButton
= v$valueButton + 1

     
Param1 <- 1
     
Param2 <- 2
     
Param3 <- 3
     
Param4 <- 4
      VAL
<- Param1 + Param2 + Param3 + Param4    
      updateSliderInput
(session, inputId = "Param1", value = Param1)
      updateSliderInput
(session, inputId = "Param2", value = Param2)
      updateSliderInput
(session, inputId = "Param3", value = Param3)
      updateSliderInput
(session, inputId = "Param4", value = Param4)
      updateActionButton
(session, inputId = "AutoParam", label = "Auto")
     
return(list(VAL = VAL))

   
})
   
   
# Change on sliderInput

    MOD1
<- eventReactive({input$Param1 ; input$Param2 ; input$Param3 ; input$Param4}, {

     
# If change on slider is because of button, v$valueButton==1
     
if (v$valueButton == 0) {

       
Param1 <- input$Param1
       
Param2 <- input$Param2
       
Param3 <- input$Param3
       
Param4 <- input$Param4
        VAL
<- Param1 + Param2 + Param3 + Param4
        updateActionButton
(session, inputId = "AutoParam", label = "reactiveValues() in a global reactive()")
       
return(list(VAL = VAL))

     
}
     
# reset value of valueButton

      v$valueButton
<- 0
   
})
   
   
if (v$valueButton == 0) {
      MOD
<- MOD1()$VAL
      isolate
(MOD1())
   
} else {
      MOD
<- MOD2()$VAL
   
}
   
    IDX
<- MOD * 2
   
   
return(list(MOD = MOD, IDX = IDX))
   
 
})
 
 
  output$ParamPlot
<- renderPlot({
   
print(str(RES()$MOD))
    plot
(RES()$MOD, RES()$MOD, main = "",
         xlim
= c(0, 40), ylim = c(0, 40))
 
})
  output$Criteria
<- renderTable({
    data
.frame(Param = c(RES()$MOD, RES()$IDX))
 
})
}

shinyApp
(ui, server)



Joe Cheng

unread,
Mar 13, 2017, 8:21:33 PM3/13/17
to O. Delaigue, Shiny - Web Framework for R
Sorry, I don't follow the question at all. Maybe you can make a simpler example to illustrate the scenario? Particularly, I don't understand what is important about the button click other than the eventReactive updating (why do you have to know whether the update is due to button click vs. something else?).

O. Delaigue

unread,
Mar 17, 2017, 5:25:52 AM3/17/17
to Shiny - Web Framework for R, arz...@hotmail.fr
Joe, you were right, I succeeded by avoiding the problem, which was not a real problem (i.e. missing feature) because in fact I were trying to retrieve an object that I did not need to calculate there!

    MOD1
<spa
Reply all
Reply to author
Forward
0 new messages