问题
I have a plot like this below:
library(ggplot2)
library(ggh4x) # remotes::install_github("teunbrand/ggh4x")
df1 <- data.frame(x = rep(1:12, times=4, each=1),
y = rep((1:12)^2, times=4, each=1),
Variable1 = rep(c("A","B"), times=1, each=24),
Variable2 = rep(c("C","D"), times=4, each=12))
g<-ggplot(df1, aes(x=x, y=y)) +
geom_point(size=1.5) +
theme(strip.background = element_rect(colour = "black", fill = "white",
size = 1.5, linetype = "solid"),
axis.title.x =element_text(margin = margin(t = 2, r = 20, b = 0, l = 0),size = 16),
axis.title.y =element_text(margin = margin(t = 2, r = 20, b = 0, l = 0),size = 16),
axis.text.x = element_text(angle = 0, hjust = 0.5,size = 14),
axis.text.y = element_text(angle = 0, hjust = 0.5,size = 14),
strip.text.x = element_text(size = 14),
strip.text.y = element_text(size = 13),
axis.line = element_line(),
panel.grid.major= element_blank(),
panel.grid.minor = element_blank(),
legend.text=element_text(size=15),
legend.title = element_text(size=15,face="bold"),
legend.key=element_blank(),
legend.position = "right",
panel.border = element_blank(),
strip.placement = "outside",
strip.switch.pad.grid = unit('0.25', "cm")) +
facet_nested( .~Variable1 + Variable2)
g
How could I increase the space among different boxes for the different facet labels? So for example, I want to increase the space between A
and C/D
. In this post is explained how to change the distance between the plot edge and the facet labels (using strip.switch.pad.grid
in theme
), but it doesn't work for separating facet boxes among them.
Does anyone know how to do it?
回答1:
ggplot2 and ggh4x don't have options to place the facet strips apart. However, that doesn't mean it can't be done: it just means that the solution is a bit uglier than you'd like. Because you'd have to dive into the gtable/grid structures underneath ggplot.
For completeness; this gives identical output to your code.
library(ggplot2)
library(ggh4x) # remotes::install_github("teunbrand/ggh4x")
library(grid)
df1 <- data.frame(x = rep(1:12, times=4, each=1),
y = rep((1:12)^2, times=4, each=1),
Variable1 = rep(c("A","B"), times=1, each=24),
Variable2 = rep(c("C","D"), times=4, each=12))
g<-ggplot(df1, aes(x=x, y=y)) +
geom_point(size=1.5) +
theme(strip.background = element_rect(colour = "black", fill = "white",
size = 1.5, linetype = "solid"),
axis.title.x =element_text(margin = margin(t = 2, r = 20, b = 0, l = 0),size = 16),
axis.title.y =element_text(margin = margin(t = 2, r = 20, b = 0, l = 0),size = 16),
axis.text.x = element_text(angle = 0, hjust = 0.5,size = 14),
axis.text.y = element_text(angle = 0, hjust = 0.5,size = 14),
strip.text.x = element_text(size = 14),
strip.text.y = element_text(size = 13),
axis.line = element_line(),
panel.grid.major= element_blank(),
panel.grid.minor = element_blank(),
legend.text=element_text(size=15),
legend.title = element_text(size=15,face="bold"),
legend.key=element_blank(),
legend.position = "right",
panel.border = element_blank(),
strip.placement = "outside",
strip.switch.pad.grid = unit('0.25', "cm")) +
facet_nested( .~Variable1 + Variable2)
Then here is the extra steps that you'd have to take for your plot, or any plot where the strip layout is horizontal without vertical strips. This should work for regular facet_grid()
too.
# How much to push the boxes apart
space <- unit(0.5, "cm")
# Convert to gtable
gt <- ggplotGrob(g)
# Find strip in gtable
is_strip <- which(grepl("strip", gt$layout$name))
strip_row <- unique(gt$layout$t[is_strip])
# Change cell height
gt$heights[strip_row] <- gt$heights[strip_row] + space
# Add space to strips themselves
gt$grobs[is_strip] <- lapply(gt$grobs[is_strip], function(strip) {
gtable::gtable_add_row_space(strip, space)
})
# Render
grid.newpage(); grid.draw(gt)
Created on 2020-05-26 by the reprex package (v0.3.0)
Note that this example is on R4.0.0. The grid::unit()
arithmetic behaviour might be slightly different in previous R versions.
As an aside, if you just want to add padding to the text, it is easier to just wrap newlines around the text:
df1$Variable1 <- factor(df1$Variable1)
levels(df1$Variable1) <- paste0("\n", levels(df1$Variable1), "\n")
EDIT: It might just be easiest to use ggtext textbox elements:
library(ggtext) # remotes::install_github("wilkelab/ggtext")
g + theme(
strip.background = element_blank(),
strip.text = element_textbox_simple(
padding = margin(5, 0, 5, 0),
margin = margin(5, 0, 5, 0),
size = 13,
halign = 0.5,
fill = "white",
box.color = "black",
linewidth = 1.5,
linetype = "solid",
)
)
g
来源:https://stackoverflow.com/questions/62029503/how-to-increase-space-among-different-boxes-created-for-the-facet-labels-using