You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何使用grid.arrange实现2x2无图例图表布局并将图例置于右侧居中

解决方案

要实现2×2布局的子图+右侧垂直居中的统一图例,可以按以下步骤操作:

  1. 移除子图自带图例:给每个ggplot对象添加theme(legend.position = "none"),避免重复显示图例。
  2. 提取统一图例:从任意一个保留图例的临时图中提取图例元素。
  3. 自定义布局:使用gridExtra的布局矩阵,让图例占据右侧第三列的两行空间,实现垂直居中对齐。

完整代码示例:

library(ggplot2)
library(gridExtra)
library(grid)
library(dplyr)

# 创建不带图例的子图
a <- mtcars %>%
  ggplot(aes(x = disp, y = mpg, colour = hp)) +
  geom_point(size = 2) +
  geom_smooth(se = F, colour = "grey") +
  theme(legend.position = "none")

b <- mtcars %>%
  ggplot(aes(x = disp, y = mpg, colour = hp)) +
  geom_point(size = 2) +
  geom_smooth(se = F, colour = "grey") +
  theme(legend.position = "none")

c <- mtcars %>%
  ggplot(aes(x = disp, y = mpg, colour = hp)) +
  geom_point(size = 2) +
  geom_smooth(se = F, colour = "grey") +
  theme(legend.position = "none")

d <- mtcars %>%
  ggplot(aes(x = disp, y = mpg, colour = hp)) +
  geom_point(size = 2) +
  geom_smooth(se = F, colour = "grey") +
  theme(legend.position = "none")

# 自定义函数提取图例(无需额外安装包)
extract_legend <- function(plot) {
  tmp_gtable <- ggplot_gtable(ggplot_build(plot))
  legend_index <- which(sapply(tmp_gtable$grobs, function(x) x$name) == "guide-box")
  legend_grob <- tmp_gtable$grobs[[legend_index]]
  return(legend_grob)
}

legend <- extract_legend(
  mtcars %>% ggplot(aes(x = disp, y = mpg, colour = hp)) + geom_point(size = 2)
)

# 定义布局矩阵:图例占第三列两行
layout_matrix <- rbind(
  c(1, 2, 3),
  c(4, 5, 3)
)

grid.arrange(
  a, b, legend, c, d,
  layout_matrix = layout_matrix,
  widths = c(4, 4, 1),  # 调整列宽比例,图例列更紧凑
  heights = c(1, 1)      # 保持两行高度一致
)

关键说明

  • layout_matrix中数字3代表图例元素,它在两行的第三列重复出现,直接实现了图例垂直居中对齐两行的效果。
  • widths参数可以灵活调整各列宽度,让整体布局更协调。
  • 如果习惯使用简化工具,也可以用cowplot::get_legend()替代自定义的extract_legend函数,代码会更简洁。

内容的提问来源于stack exchange,提问作者Karl Seidl

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.17 18:23:11