Notes on Shiny

Harold Nelson

2022-11-14

Notes on Shiny

Setup

Create a project “Shiny” in a folder with that name. Make this your working directory by opening the project.

Start a new shiny app using the pulldown. Use the name “Hello”. That will produce the following R code and put it in a folder named “Hello” in your shiny directory.

The code in app.R will look likw this.

#
# This is a Shiny web application. You can run the application by clicking
# the 'Run App' button above.
#
# Find out more about building applications with Shiny here:
#
#    http://shiny.rstudio.com/
#

library(shiny)

# Define UI for application that draws a histogram
ui <- fluidPage(

    # Application title
    titlePanel("Old Faithful Geyser Data"),

    # Sidebar with a slider input for number of bins 
    sidebarLayout(
        sidebarPanel(
            sliderInput("bins",
                        "Number of bins:",
                        min = 1,
                        max = 50,
                        value = 30)
        ),

        # Show a plot of the generated distribution
        mainPanel(
           plotOutput("distPlot")
        )
    )
)

# Define server logic required to draw a histogram
server <- function(input, output) {

    output$distPlot <- renderPlot({
        # generate bins based on input$bins from ui.R
        x    <- faithful[, 2]
        bins <- seq(min(x), max(x), length.out = input$bins + 1)

        # draw the histogram with the specified number of bins
        hist(x, breaks = bins, col = 'darkgray', border = 'white',
             xlab = 'Waiting time to next eruption (in mins)',
             main = 'Histogram of waiting times')
    })
}

# Run the application 
shinyApp(ui = ui, server = server)

Task 1

Modify the app as follows.

Let the user select the color of the histogram using a selectInput control.

Solution

#
# This is a Shiny web application. You can run the application by clicking
# the 'Run App' button above.
#
# Find out more about building applications with Shiny here:
#
#    http://shiny.rstudio.com/
#

library(shiny)

# Define UI for application that draws a histogram
ui <- fluidPage(

    # Application title
    titlePanel("Old Faithful Geyser Data"),

    # Sidebar with a slider input for number of bins 
    sidebarLayout(
        sidebarPanel(
            sliderInput("bins",
                        "Number of bins:",
                        min = 1,
                        max = 50,
                        value = 30),
            selectInput("color",
                        label = "Histogram Color",
                        c("red","yellow",'purple'))
        ),

        # Show a plot of the generated distribution
        mainPanel(
           plotOutput("distPlot")
        )
    )
)

# Define server logic required to draw a histogram
server <- function(input, output) {

    output$distPlot <- renderPlot({
        # generate bins based on input$bins from ui.R
        x    <- faithful[, 2]
        bins <- seq(min(x), max(x), length.out = input$bins + 1)

        # draw the histogram with the specified number of bins
        hist(x, breaks = bins, col = input$color, border = 'white',
             xlab = 'Waiting time to next eruption (in mins)',
             main = 'Histogram of waiting times')
    })
}

# Run the application 
shinyApp(ui = ui, server = server)

Task 2

Instead of limiting the selection of colors, use the rgb() function. It has three parameters, red, green, and blue. These have values in the range 0 to 1. Provide sliders in the UI to obtain these values.

Solution

#
# This is a Shiny web application. You can run the application by clicking
# the 'Run App' button above.
#
# Find out more about building applications with Shiny here:
#
#    http://shiny.rstudio.com/
#

library(shiny)

# Define UI for application that draws a histogram
ui <- fluidPage(

    # Application title
    titlePanel("Old Faithful Geyser Data"),

    # Sidebar with a slider input for number of bins 
    sidebarLayout(
        sidebarPanel(
            sliderInput("bins",
                        "Number of bins:",
                        min = 1,
                        max = 50,
                        value = 30),
            sliderInput("red",
                        "Red Value",
                        min = 0,
                        max = 1,
                        value = .5),
            sliderInput("green",
                        "Green Value",
                        min = 0,
                        max = 1,
                        value = .5),
            sliderInput("blue",
                        "Blue Value",
                        min = 0,
                        max = 1,
                        value = .5)
        ),

        # Show a plot of the generated distribution
        mainPanel(
           plotOutput("distPlot")
        )
    )
)

# Define server logic required to draw a histogram
server <- function(input, output) {

    output$distPlot <- renderPlot({
        # generate bins based on input$bins from ui.R
        x    <- faithful[, 2]
        bins <- seq(min(x), max(x), length.out = input$bins + 1)

        # draw the histogram with the specified number of bins
        hist(x, breaks = bins, col = rgb(input$red,input$green,input$blue), border = 'white',
             xlab = 'Waiting time to next eruption (in mins)',
             main = 'Histogram of waiting times')
    })
}

# Run the application 
shinyApp(ui = ui, server = server)

Task 3

Use ggplot2 and add a density plot to the output. Use geom_density() with an adjust parameter. Let the user select the value of adjust in the range .1 to 5 with a starting value of 1. Use an input slider.

Note that the dataframe is “faithful” and the variable is “waiting”.

library(shiny)

# Define UI for application that draws a histogram
ui <- fluidPage(
  
  # Application title
  titlePanel("Old Faithful Geyser Data"),
  
  # Sidebar with a slider input for number of bins 
  sidebarLayout(
    sidebarPanel(
      sliderInput("bins",
                  "Number of bins:",
                  min = 1,
                  max = 50,
                  value = 30),
      sliderInput("adjust",
                  "Density Adjustment",
                  min = .1,
                  max = 3,
                  value = 1),
      sliderInput("red",
                  "Red Value",
                  min = 0,
                  max = 1,
                  value = .5),
      sliderInput("green",
                  "Green Value",
                  min = 0,
                  max = 1,
                  value = .5),
      sliderInput("blue",
                  "Blue Value",
                  min = 0,
                  max = 1,
                  value = .5)
    ),
    
    # Show a plot of the generated distribution
    mainPanel(
      plotOutput("distPlot"),
      plotOutput("densityPlot")
    )
  )
)

# Define server logic required to draw a histogram
server <- function(input, output) {
  library(ggplot2)
  output$distPlot <- renderPlot({
    # generate bins based on input$bins from ui.R
    x    <- faithful[, 2]
    bins <- seq(min(x), max(x), length.out = input$bins + 1)
    
    # draw the histogram with the specified number of bins
    hist(x, breaks = bins, col = rgb(input$red,input$green,input$blue), border = 'white',
         xlab = 'Waiting time to next eruption (in mins)',
         main = 'Histogram of waiting times')
  })
  
  output$densityPlot = renderPlot({
    ggplot(faithful,aes(waiting)) +
      geom_density(adjust = input$adjust) +
      ggtitle("Density of Waiting Time")
  })
}

# Run the application 
shinyApp(ui = ui, server = server)

Task 4

Repeat the previous exercise with tabbed output.

Solution

library(shiny)

# Define UI for application that draws a histogram
ui <- fluidPage(
  
  # Application title
  titlePanel("Old Faithful Geyser Data"),
  
  # Sidebar with a slider input for number of bins 
  sidebarLayout(
    sidebarPanel(
      sliderInput("bins",
                  "Number of bins:",
                  min = 1,
                  max = 50,
                  value = 30),
      sliderInput("adjust",
                  "Density Adjustment",
                  min = .1,
                  max = 3,
                  value = 1),
      sliderInput("red",
                  "Red Value",
                  min = 0,
                  max = 1,
                  value = .5),
      sliderInput("green",
                  "Green Value",
                  min = 0,
                  max = 1,
                  value = .5),
      sliderInput("blue",
                  "Blue Value",
                  min = 0,
                  max = 1,
                  value = .5)
    ),
    
    # Show a plot of the generated distribution
    tabsetPanel(type = "tabs",
                tabPanel("Histogram", plotOutput("distPlot")),
                tabPanel("Density", plotOutput("densityPlot"))
    )
  )
)

# Define server logic required to draw a histogram
server <- function(input, output) {
  library(ggplot2)
  output$distPlot <- renderPlot({
    # generate bins based on input$bins from ui.R
    x    <- faithful[, 2]
    bins <- seq(min(x), max(x), length.out = input$bins + 1)
    
    # draw the histogram with the specified number of bins
    hist(x, breaks = bins, col = rgb(input$red,input$green,input$blue), border = 'white',
         xlab = 'Waiting time to next eruption (in mins)',
         main = 'Histogram of waiting times')
  })
  
  output$densityPlot = renderPlot({
    ggplot(faithful,aes(waiting)) +
      geom_density(adjust = input$adjust) +
      ggtitle("Density of Waiting Time")
  })
}

# Run the application 
shinyApp(ui = ui, server = server)