Reputation: 372
I'm looking at figures from Moreira et al. (Nature, 2020) where they have graphs indicating sample size and treatments under the barplots such as this:
Is there a way to reproduce this in ggplot? This would be very useful to indicate all the necessary information regarding an experiment in a compact manner.
Some dummy data for the plot:
library(tidyverse)
tibble(
Rodent = c(rep("Mouse",11),
rep("Hamster",7),
rep("Guinea pig",4),
rep("Gerbil",12)),
`Weight (gm)` = rnorm(34,25,10),
`Long whiskers` = c(rep("+",11),rep("-",7),rep("+",4),rep("-",12)),
`Long tail` = c(rep("+",11),rep("-",7),rep("+",4),rep("-",12)),
`Albino or normal` = c(rep("Albino",11),rep("Normal",7),rep("Albino",4),rep("Normal",12))
) %>%
ggplot(aes(Rodent,`Weight (gm)`,fill = `Albino or normal`)) +
geom_boxplot()
Upvotes: 2
Views: 409
Reputation: 124138
There are probably two or three approaches to achieve your desired result. Personally I prefer to do it via patchwork
, i.e create a second plot with the additional information you want to display and glue it to your main plot:
library(tidyverse)
d <- tibble(
Rodent = c(rep("Mouse",11),
rep("Hamster",7),
rep("Guinea pig",4),
rep("Gerbil",12)),
`Weight (gm)` = rnorm(34,25,10),
`Long whiskers` = c(rep("+",11),rep("-",7),rep("+",4),rep("-",12)),
`Long tail` = c(rep("+",11),rep("-",7),rep("+",4),rep("-",12)),
)
p1 <- d %>%
ggplot(aes(Rodent,`Weight (gm)`)) +
geom_boxplot()
d1 <- d %>%
select(-`Weight (gm)`) %>%
count(Rodent, `Long whiskers`, `Long tail`) %>%
distinct() %>%
mutate(n = as.character(n)) %>%
pivot_longer(-Rodent)
p2 <- d1 %>%
ggplot(aes(Rodent, fct_rev(name), label = value)) +
geom_text(size = 10) +
labs(x = NULL, y = NULL) +
theme_minimal() +
theme(panel.grid = element_blank(), axis.text.x = element_blank())
library(patchwork)
p1 / p2
EDIT With a legend on the right it looks like so. I simply added a color legend where I mapped Rodent
on color
:
p1 <- d %>%
ggplot(aes(Rodent,`Weight (gm)`, color = Rodent)) +
geom_boxplot() +
theme(legend.position = "right")
p2 <- d1 %>%
ggplot(aes(Rodent, fct_rev(name), label = value)) +
geom_text(size = 10) +
labs(x = NULL, y = NULL) +
theme_minimal() +
theme(panel.grid = element_blank(), axis.text.x = element_blank())
p1 / p2
Upvotes: 3