R语言 在ggplot外部插入矩形以显示地块线

aydmsdu9  于 2023-02-06  发布在  其他
关注(0)|答案(1)|浏览(138)

我希望你能帮助我。我有一个想法,可视化图中的线段,可以放置在y轴或x轴旁边,这意味着它将在绘图区域之外。它应该看起来类似于下图:

我尝试了两种不同的方法来达到上面提到的输出:
1.我用grid包创建了两个视口,并将绘图放在底部的一个视口和顶部的一个视口中。这里的大问题是我需要ggplot的灰色背景面板开始的坐标,这样我就可以将顶部视口精确地放置在那里,以便线段与x轴长度一致。我的代码如下所示:

container_viewport <- viewport(x=0,y=0,height=1,width=1,just = c("left","bottom"))
pushViewport(container_viewport)
grid.draw(rectGrob())
popViewport()

section_viewport <- viewport(x=0.055,y=0.99,height=0.085,width=0.935,just=c("left","top"))
pushViewport(section_viewport)

plot_obj <- ggplot_build(testplot)
plot_data <- plot_obj$data[[1]]

grid.draw(rectGrob(gp = gpar(col = "red")))
popViewport()

plot_viewport <- viewport(x=0,y=0,height=0.9,width=1,just=c("left","bottom"))
pushViewport(plot_viewport)
grid.draw(ggplotGrob(testplot))
popViewport()

这看起来不错,但我不得不硬编码的坐标视口在顶部。
1.我使用grid.arrange()来排列垂直堆叠的图(而不是像其他方法中那样为矩形创建一个grob,我创建了一个ggplot)。这里,基本上存在相同的问题,因为我需要将表示顶部矩形的图放在x轴的正确位置。我的代码如下所示:

p1 <- plot_data %>%
  ggplot()+
  geom_rect(aes(xmin=-Inf,xmax=Inf,ymin=-Inf,ymax=Inf))
p2 <- testplot

test_plot <- grid.arrange(p1,p2,heights=c(1,10))

这种方法效果不太好。
因为我想创建一个可以普遍应用的解决方案,所以没有选择视口坐标的试错法,因为y轴标签或刻度标签的长度可以变化,因此背景面板的长度和坐标也会变化。当这一步完成后,矩形的分割应该不再是问题。
也许这是不可能的,但如果那样的话,我将感激任何帮助。谢谢!

o2g1uqev

o2g1uqev1#

这里我可能会使用patchwork。让我们从复制您的图开始:

library(ggplot2)
library(patchwork)

p <- ggplot(iris, aes(Sepal.Length, Sepal.Width)) +
  geom_point(color = "red") +
  labs(x = "test", y = "test")

p

这看起来非常相似。现在我们定义(在我们自己的坐标系中)我们希望截面在x轴上的哪个位置进行分割。

section_split <- 5.25

仅使用这个数字,我们添加矩形和文本注解,以覆盖原始图的"副本",并使用theme_void删除其轴注解:

p2 <- p + 
  annotate("rect", xmin = c(-Inf, section_split), ymin = c(-Inf, -Inf),
             xmax = c(section_split, Inf), ymax = c(Inf, Inf),
             fill = c("#00a2e8", "#ff7f27")) +
  annotate("text", label = c("Section A", "Section B"), size = 6,
           y = rep(mean(layer_scales(p)$y$range$range), 2),
           x = c((min(layer_scales(p)$x$range$range) + section_split)/2,
                 (max(layer_scales(p)$x$range$range) + section_split)/2)) +
  theme_void()

现在,我们只需在第一个图上方绘制第二个图,并将相对高度调整为约1:10

p2/p + plot_layout(heights = c(1, 10))

这样做的好处是,因为我们复制了原始图,所以两个图之间x轴的位置Map是相同的,并且patchwork将自动对齐面板。
创建于2023年2月4日,使用reprex v2.0.2

相关问题