I am new to shiny as well as stackoverflow and looking for some help with a problem that I am currently stuck at. I am trying to build a shiny app which collects some inputs from the user and creates visualization based on inputs on click of a button. Currently, that works fine, but one of the major ask is that, when the app loads for the first time, it shall have visualization prepared based on the default inputs.
I am pasting a sample code, which can explain the issue I am facing:
UI.R
#loading shiny
library(shiny)
ui<-shinyUI(fluidPage(
titlePanel("Iris Dataset"),
sidebarLayout(
sidebarPanel(
radioButtons("x", "Select X-axis:",
list("Sepal.Length"='a', "Sepal.Width"='b', "Petal.Length"='c', "Petal.Width"='d')),
radioButtons("y", "Select Y-axis:",
list("Sepal.Length"='e', "Sepal.Width"='f', "Petal.Length"='g', "Petal.Width"='h')),
actionButton("action","Submit")
),
mainPanel(
plotOutput("distPlot")
)
)
))
#SERVER.R
library(shiny)
#loading shiny
server<-shinyServer(function(input, output) {
observeEvent(input$action,{
output$distPlot <- renderPlot({if(input$x=='a'){i<-1}
if(input$x=='b'){i<-2}
if(input$x=='c'){i<-3}
if(input$x=='d'){i<-4}
if(input$y=='e'){j<-1}
if(input$y=='f'){j<-2}
if(input$y=='g'){j<-3}
if(input$y=='h'){j<-4}
s <- iris[, i]
k <- iris[, j]
plot(s,k)
})
})
})
shinyApp(ui<-ui, server<-server)
Now if you run this app, you would see that the inputs are selected at the first screen after load (which is as desired) but the visualization appears only after clicking "Submit" button, this is because of the observer event. In the actual app, there are calculation being performed after capturing the inputs at the click of the button. Hence, the calculation triggers only when the actionButton is clicked
Is there a way, we can still keep the "Submit" button and its observe event, but automatically trigger the visualization or the action performed within the observe event at the start i.e. when the app loads for the first time.
Using
renderPlot
or other render functions insideobserveEvent
is considered bad practice. What you are looking for is a reactive object that represents the plot parameters. You can then access this reactive object inside yourrenderPlot
context. Here is an exampleThe object
user_choice
will get updated whenever a user clicks the button or the app starts.There is also an
ignoreNULL
parameter inobserveEvent
but for some reason, that does not yield the same result.