Skip to content

Instantly share code, notes, and snippets.

@cararthompson
Created June 8, 2026 16:54
Show Gist options
  • Select an option

  • Save cararthompson/91013701548841d17c9a3a56949c95dd to your computer and use it in GitHub Desktop.

Select an option

Save cararthompson/91013701548841d17c9a3a56949c95dd to your computer and use it in GitHub Desktop.
Jitter graph
library(ggplot2)
# Our starting point ----
beak_lengths <- palmerpenguins::penguins |>
ggplot() +
geom_jitter(
aes(
x = bill_length_mm,
y = species,
fill = species,
size = body_mass_g
),
shape = 21,
width = 0,
height = 0.15
) +
labs(
title = "Beak lengths in the dataset",
subtitle = "The adelie penguins all have beaks shorter than 50mm - you'll be safe with them",
x = "Beak length (mm)"
) +
theme_minimal(base_size = 16) +
theme(legend.position = "none", axis.title.y = element_blank())
# Change the colours ----
penguin_colours <- c(
"Adelie" = "#E59608",
"Gentoo" = "#005410",
"Chinstrap" = "#F2B7C4"
)
beak_lengths +
scale_fill_manual(values = penguin_colours)
# Add `theme_glasgow()` ----
beak_lengths +
scale_fill_manual(values = penguin_colours) +
theme_glasgow() +
theme(legend.position = "none", axis.title.y = element_blank())
# Add annotations ----
beak_means_df <- penguins |>
dplyr::group_by(species) |>
dplyr::summarise(mean_length = mean(bill_len, na.rm = TRUE))
penguins |>
ggplot() +
geom_segment(
data = beak_means_df,
aes(x = mean_length, xend = mean_length, y = -Inf, yend = species),
linetype = 3
) +
geom_jitter(
aes(
x = bill_len,
y = species,
fill = species,
colour = dplyr::case_when(
species == "Gentoo" ~ "#ffffff",
.default = "#343536"
),
size = body_mass
),
shape = 21,
width = 0,
height = 0.15
) +
ggtext::geom_textbox(
data = beak_means_df,
aes(
x = mean_length,
y = species,
label = paste0(
species,
" mean<br>**",
janitor::round_half_up(mean_length),
"mm**"
)
),
hjust = 0,
nudge_y = -0.4,
box.colour = NA,
family = "Noto Sans",
colour = "#343536",
fill = NA
) +
scale_fill_manual(values = penguin_colours) +
scale_colour_identity() +
labs(
title = "Beak lengths in the dataset",
subtitle = "The adelie penguins all have beaks shorter than 50mm - you'll be safe with them",
x = "Beak length (mm)"
) +
theme_glasgow() +
theme(legend.position = "none", axis.title.y = element_blank())
# Make interactive ----
interactive_plot <- penguins |>
ggplot() +
geom_segment(
data = beak_means_df,
aes(x = mean_length, xend = mean_length, y = -Inf, yend = species),
linetype = 3
) +
ggiraph::geom_jitter_interactive(
aes(
x = bill_len,
y = species,
fill = species,
colour = dplyr::case_when(
species == "Gentoo" ~ "#ffffff",
.default = "#343536"
),
size = body_mass,
tooltip = paste(bill_len, "mm<br>A ", sex, " penguin from ", island)
),
shape = 21,
width = 0,
height = 0.15
) +
ggtext::geom_textbox(
data = beak_means_df,
aes(
x = mean_length,
y = species,
label = paste0(
species,
" mean<br>**",
janitor::round_half_up(mean_length),
"mm**"
)
),
hjust = 0,
nudge_y = -0.4,
box.colour = NA,
family = "Noto Sans",
colour = "#343536",
fill = NA
) +
scale_fill_manual(values = penguin_colours) +
scale_colour_identity() +
labs(
title = "Beak lengths in the dataset",
subtitle = "The adelie penguins all have beaks shorter than 50mm - you'll be safe with them",
x = "Beak length (mm)"
) +
theme_glasgow() +
theme(
legend.position = "none",
axis.title = element_blank(),
axis.text = element_blank()
)
ggiraph::girafe(
ggobj = interactive_plot,
options = list(
ggiraph::opts_tooltip(css = glasgow_tooltip_css),
ggiraph::opts_hover(css = "stroke:#343536"),
ggiraph::opts_hover_inv(css = "opacity:0.5")
),
height_svg = 6,
width_svg = 9
)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment