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

如何在ggplot2中添加分隔标题、注释区与主绘图区的水平线?

如何用ggplot2绘制分隔标题区、注释区与主绘图区的水平线?

我需要重现经LaTeX期刊模板处理后的ggplot2散点图效果,核心是添加分隔标题区与主绘图区、注释区与主绘图区的水平线(见目标效果),但当前代码无法实现这一点。

当前使用的代码:

library(ggplot2)
theme_set(theme_bw())  # pre-set the bw theme.
data("midwest", package = "ggplot2")


# Scatterplot
gg <- ggplot(midwest, aes(x=area, y=poptotal)) + 
  geom_point(aes(col=state, size=popdensity)) + 
  geom_smooth(method="loess", se=F) + 
  xlim(c(0, 0.1)) + 
  ylim(c(0, 500000)) + 
  labs(y="Population", 
       x="Area", 
       title="Figure 4: Scatterplot", 
       caption = "Source: midwest") +
  theme(plot.background = element_rect(colour="black",size=1))

plot(gg)

目标效果:
目标效果

当前效果:
当前效果


解决方案

可以通过annotation_custom结合grid包的图形对象添加跨整个绘图宽度的水平线,同时调整主题边距和坐标裁剪设置,确保线和文字不重叠:

library(ggplot2)
library(grid)  # 用于创建线条图形对象

theme_set(theme_bw())  
data("midwest", package = "ggplot2")

gg <- ggplot(midwest, aes(x=area, y=poptotal)) + 
  geom_point(aes(col=state, size=popdensity)) + 
  geom_smooth(method="loess", se=F) + 
  xlim(c(0, 0.1)) + 
  ylim(c(0, 500000)) + 
  labs(y="Population", 
       x="Area", 
       title="Figure 4: Scatterplot", 
       caption = "Source: midwest") +
  coord_cartesian(clip = "off") +  # 允许图形元素超出主绘图区域
  # 添加标题下方的水平线(使用归一化坐标覆盖整个宽度)
  annotation_custom(
    grob = linesGrob(gp = gpar(col = "black", lwd = 1)),
    xmin = unit(0, "npc"), xmax = unit(1, "npc"),
    ymin = unit(0.92, "npc"), ymax = unit(0.92, "npc")
  ) +
  # 添加注释上方的水平线
  annotation_custom(
    grob = linesGrob(gp = gpar(col = "black", lwd = 1)),
    xmin = unit(0, "npc"), xmax = unit(1, "npc"),
    ymin = unit(0.08, "npc"), ymax = unit(0.08, "npc")
  ) +
  theme(
    plot.background = element_rect(colour="black", size=1),
    plot.title = element_text(hjust = 0.5, margin = margin(b = 20), size = 12, face = "bold"),
    plot.caption = element_text(hjust = 0.5, margin = margin(t = 20)),
    plot.margin = margin(50, 20, 50, 20)  # 调整上下边距,避免线与文字、边框重叠
  )

plot(gg)

关键说明

  1. coord_cartesian(clip = "off"):关闭绘图区裁剪,让水平线可以延伸到主图之外的标题/注释区域。
  2. annotation_custom + linesGrob:使用归一化父坐标(npc)定义水平线的位置和宽度,确保线覆盖整个绘图区域的宽度。
  3. 主题边距调整:通过plot.margin和文本元素的margin参数,留出足够空间放置水平线,避免与标题、注释或外边框重叠。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.22 06:36:19