Shiny apps are not your standard websites!
shiny
is an R package that helps you write Shiny
apps. -
Production-ready apps must be deployed on a server. Posit provides free
server instances for Shiny users, but this can also be an instance
hosted by your institution. - You can also use Shiny to capture the
logic within the app and use it to return code that will reproduce
certain outputs (shinymeta) - More on
this later, but Shiny apps can also be embedded in things like RMarkdown
documents.
Task: Go to a new RStudio window and go to File –> New File –> Shiny web app. You’ll get a pop-up window that asks you to choose an app name and a directory.
Task: Pick your app name and
Multiple File
and click ‘Create’.
Note: The distinction between the ‘Multiple File’ and ‘Single file’ options is purely a matter of how you like to work. This choice will not affect functionality.
runApp()
in the console.Success: Voila! You have rendered your first app. As you’re building your app, you will end up pressing this button many…many times.
Now that you have a template shiny app set up, you can build on it!
Task: Let’s add a plot element to this app called
EruptionScatter
. Go to server.R and add this to the
server:
output$EruptionScatter <- renderPlot({
# just a little scatterplot
plot(faithful$eruptions,faithful$waiting,
pch = 19,col = scales::alpha("darkblue",0.5),
xlab = "Eruption time (mins)", ylab = "Waiting time to next eruption (mins)")
})
When you click “Render App”, it doesn’t appear in the app! Why not?
Because we also need to put it in the UI in order for it to appear.
After you have been writing code all day, the easiest oversights to make
are calling something the wrong type of render
object or
putting something in the server but forgetting to add it to the ui.
Task: You have to tell R what type of output object
it is. Add the element EruptionScatter
to the ui, so that
your mainPanel
section looks like this:
mainPanel(
plotOutput("distPlot"),
plotOutput("EruptionScatter")
)
Note: In order for something to appear in your app, it must be in the ui.R.
When you click “Run App,” yay! Your new plot element has appear in the UI.
Leaflet makes maps you can serve as standalone HTMLs. You can also embed them in:
They’re very flexible! And they’re interactive.
You can make a map in leaflet
that renders to an HTML
without any extra bells and whistles.
You can embed a Shiny app in a Markdown / Quarto page.
A Markdown document with shiny widgets and outputs is called an “interactive document.”
To make a Markdown document interactive, you add the following to the yaml header:
---
runtime: shiny
output:html_document
---
You can do it with an inline definition, like this:
library(palmerpenguins)
library(ggplot2)
library(shiny)
shinyApp(
ui = fluidPage(
checkboxGroupInput(
inputId = "species",
label = "Penguin species:",
c(
"Gentoo" = "Gentoo",
"Adelie" = "Adelie",
"Chinstrap" = "Chinstrap"
),
selected = c("Gentoo", "Adelie")
),
plotOutput("penguinPlot")
),
server = function(input, output) {
output$penguinPlot <- renderPlot({
penguins_plot <- subset(penguins, species == input$species)
p1 <- ggplot(
penguins_plot,
aes(x = bill_length_mm, y = bill_depth_mm, color = species)
) +
geom_point(size = 4) +
scale_color_brewer(palette = "Dark2") +
ylab("Bill depth (mm)") +
xlab("Bill length (mm)") +
theme_light(base_size = 14)
p1
})
},
options = list(height = 500)
)
You can also call a Shiny app defined in another directory; it would look like this:
library(shiny)
shinyAppDir(
system.file("examples/01_hello", package="shiny"),
options = list(width = "100%", height = 700)
)
You can embed shiny widgets in Markdown documents. Because those render differently than a static HTML file (like this one), there are instructions for creating interactive documents here and source code here.
Shiny has different display modes.
The default is display.mode = "normal"
which returns the
usual Shiny looking interface:
But you can also use display.mode = "showcase"
, which
shows the source code for the app alongside the content. This can be
nice for teaching!
Note that “showcase mode” (the shiny interface that shows both ui and code at the same time) won’t work in Markdown docs.
Sam Czik’s hiking/biking Strava dashboard (leaflet + flexdashboard)
A cool example of how to use Shiny instead of a lengthy paper appendix to illustrate a point: Beyond Temperature from the paper Projecting marine species range shifts from only temperature masks climate vulnerability by Jennifer McHenry, Heather Welch, Sarah E. Lester, and Vincent Saba
tidytuesday.rocks by Neal Grantham aggregates #TidyTuesday entries from the internet (and it uses an API!)
Sentify provides effective data viz on large datasets. By Charlie Thompson
A whole gallery of great apps, complete with source code (and a great way to get recognized for your Shiny work!) All the submissions are here and the winners from the last contest (2021) are here.
Novel-gazing, for analyzing your goodreads shelves as if they are ecological communities: https://msiple.shinyapps.io/NovelGazingApp/
Adopt Don’t Shop has sadly been deprecated because the shelter changed their website!
shiny.posit.co has great resources for building and deploying Shiny apps in both R and Python(!).
Appsilon’s virtual Shiny Conference is April 9-11 2025 (free registration link)
Mastering Shiny by Hadley Thee Wickham
Colin Fay has several talks on Shiny app workflow and production
Since you’re at UW, you can take advantage of UW IT’s UX testing consultations: https://uxdesign.uw.edu/consultations.html