The patchwork library in R is a versatile tool designed to simplify the arrangement and combination of multiple ggplot2 plots into complex layouts. Introduced by Pedersen (2020), patchwork leverages an intuitive “+” operator, allowing users to effortlessly stack, align, or grid plots without requiring intricate code. This functionality is especially valuable in exploratory data analysis and publication-quality visualizations.
Compared to alternatives like cowplot or gridExtra, patchwork stands out due to its syntax simplicity and seamless integration with ggplot2. The library also supports advanced layout customization using plot_layout(), enabling nested plots and specific adjustments to column and row configurations (Wilke, 2019).
Widely adopted by data analysts, patchwork improves workflow efficiency by eliminating the need for manual layout designs. Moreover, its compatibility with other visualization tools underscores its adaptability in modern data science projects (Wickham et al., 2021).
# https://github.com/Z3tt/TidyTuesday/blob/main/R/2019_24_Meteorites.Rmd
# Clear R environment:
rm(list = ls())
# Load some R packages:
library(ggplot2)
library(dplyr)
library(showtext)
color_bgr <- "#1d1330"
my_font <- "Roboto Mono"
font_add_google(my_font, my_font)
showtext_auto()
df_meteor <- readr::read_csv("https://raw.githubusercontent.com/rfordatascience/tidytuesday/master/data/2019/2019-06-11/meteorites.csv")
df_meteor %>%
mutate(decade = year - year %% 10,
century = year - year %% 100) -> df_meteor
df_meteor %>%
filter(decade >= 1500, fall == "Fell") %>%
group_by(decade) %>%
count() %>%
ungroup() -> df_line
df_line %>%
pull(n) %>%
mean() -> avg
df_line %>%
filter(decade == 2010) -> df2010
df_line %>%
ggplot(aes(x = decade, y = n)) +
theme(plot.background = element_rect(fill = color_bgr, color = NA)) +
theme(panel.background = element_rect(fill = color_bgr, color = NA)) +
theme(panel.grid.minor = element_blank()) +
theme(panel.grid.major = element_line(linewidth = 0.01, colour = "#153915")) +
geom_line(size = 0.8, color = "green", alpha = 1) +
geom_ribbon(aes(ymin = -Inf, ymax = n), fill = "green", alpha = 0.15) +
geom_hline(aes(yintercept = avg), color = "green", linetype = "dashed") +
geom_point(data = df2010, color = "red", size = 15, alpha = 0.3) +
geom_point(data = df2010, color = "red", size = 6, alpha = 0.3) +
geom_point(data = df2010, color = "red", size = 1, alpha = 1) +
annotate("text", x = 1710, y = 85,
label = "WARNING!", color = "red",
family = my_font, size = 8, fontface = "bold") +
annotate("text", x = 1710, y = 76,
label = "The number of fallen meteorites\nis drastically decreasing!",
color = "grey90", family = my_font, size = 3.5) +
scale_x_continuous(expand = c(0, 0), breaks = seq(1500, 2050, by = 50),
limits = c(1490, 2055)) +
scale_y_continuous(expand = c(0,0), limits = c(-2, 100),
breaks = seq(0, 100, by = 10)) +
theme(axis.text = element_text(color = "green", size = 9)) +
theme(plot.margin = unit(rep(0.5, 4), "cm")) -> fig1
fig1
df_meteor_prev <- df_meteor %>%
filter(fall == "Fell",
decade >= 1500,
decade < 2010)
df_meteor_now <- df_meteor %>%
filter(fall == "Fell",
decade == 2010)
df_meteor_heavy <- df_meteor %>%
filter(fall == "Fell",
decade >= 1500) %>%
mutate(group = case_when(decade == 2010 ~ "now", TRUE ~ "prev")) %>%
group_by(group) %>%
top_n(1, mass) %>%
mutate(name = glue::glue("> {name} ({year})"),
class = glue::glue("> Class: {class}"),
mass = glue::glue("> Mass: {mass / 1000} kg"))
map_data("world") -> df_world
df_world %>%
ggplot(aes(x = long, y = lat)) +
theme(plot.background = element_rect(fill = color_bgr, color = NA)) +
theme(panel.background = element_rect(fill = color_bgr, color = NA)) +
theme(panel.grid.minor = element_blank()) +
theme(panel.grid.major = element_line(linewidth = 0.01, colour = "#153915")) +
geom_polygon(aes(group = group), fill = "#001810", color = "#004e00") +
geom_point(data = df_meteor_prev, color = "green", size = 0.8, alpha = 0.35) +
geom_point(data = df_meteor_now, color = "red", size = 9, alpha = 0.2) +
geom_point(data = df_meteor_now, color = "red", size = 3.3, alpha = 0.5) +
geom_point(data = df_meteor_now, color = "red", size = 1.5) +
geom_segment(data = df_meteor_heavy,
aes(x = long, xend = long, y = lat, yend = lat + 13.5),
color = "grey65", size = 0.5) +
geom_segment(data = df_meteor_heavy,
aes(x = long - 25.1, xend = long + 25.1, y = lat + 13.5, yend = lat + 13.5),
color = "grey65", size = 1.3) +
geom_text(data = df_meteor_heavy, aes(long - 23, lat + 28, label = name),
family = my_font, color = "green", size = 2.7, fontface = "bold", hjust = 0) +
geom_text(data = df_meteor_heavy, aes(long - 23, lat + 23, label = class),
family = my_font, color = "grey95", size = 2.7, fontface = "bold", hjust = 0) +
geom_text(data = df_meteor_heavy, aes(long - 23, lat + 18, label = mass),
family = my_font, color = "grey95", size = 2.7, fontface = "bold", hjust = 0) +
annotate("text", x = -169, y = -28, label = "Please Enter Password for User 'NASA1'",
color = "grey95", family = my_font, size = 2.8, hjust = 0) +
annotate("text", x = -169, y = -33, label = "> TRUMP123456",
color = "green", family = my_font, size = 2.8, hjust = 0) +
annotate("text", x = -169, y = -38, label = "Welcome Mr. President!",
color = "grey95", family = my_font, size = 2.8, hjust = 0) +
annotate("text", x = -169, y = -43, label = "> MapView.Basic(MeteoritesV19.06.12)",
color = "green", family = my_font, size = 2.8, hjust = 0) +
annotate("text", x = -169, y = -48, label = "Processing: |||||||||||||||||||| 100%",
color = "grey95", family = my_font, size = 2.8, hjust = 0) +
annotate("text", x = -169, y = -53, label = "Map `MeteoritesV19.06.12` loaded.",
color = "grey95", family = my_font, size = 2.8, hjust = 0) +
annotate("text", x = -169, y = -58, label = "> MapView.Highlight(MeteoritesV19.06.12$recent)",
color = "green", family = my_font, size = 2.8, hjust = 0) +
annotate("text", x = -169, y = -63, label = "Processing: |||||||||||||| 73.4%",
color = "grey95", family = my_font, size = 2.8, hjust = 0) +
scale_x_continuous(breaks = seq(-200, 200, by = 25), expand = c(0, 0)) +
scale_y_continuous(breaks = seq(-100, 100, by = 25)) +
scale_size_continuous(range = c(0.25, 1)) +
theme(axis.text = element_blank()) +
labs(title = "Meteorite Landings",
subtitle = "The dataset for this map, derived from publicly available NASA data, includes the location,\nmass, composition, and fall year of over 45,000 meteorites that have struck Earth.",
caption = "Data Source: National Aeronautics and Space Administration (NASA)") +
theme(plot.caption = element_text(color = "grey75", family = my_font, size = 9)) +
theme(plot.title = element_text(size = 18, family = my_font, color = "green", face = "bold")) +
theme(plot.subtitle = element_text(size = 10, family = my_font, color = "white")) +
theme(plot.margin = unit(rep(0.5, 4), "cm")) -> fig2
fig2