如何为条形图的彩色分组添加图例

4
我使用了在这里提出的解决方法,根据数据框中提供的变量为facet_wrap创建的分面的条纹着色。 我需要为条纹颜色(size)添加图例,该图例绘制在dummy中。 有什么办法可以从g2$layout中获取它,或者其他方法吗?
library(gtable)
library(grid)

d <- data.frame(fruit = rep(c("apple", "orange", "plum", "banana", "pear", "grape")), 
            farm = rep(c(0,1,3,6,9,12), each=6), 
            weight = rnorm(36, 10000, 2500), 
            size=rep(c("small", "large")))

p1 = ggplot(data = d, aes(x = farm, y = weight)) + 
  geom_jitter(position = position_jitter(width = 0.3), 
          aes(color = factor(farm)), size = 2.5, alpha = 1) + 
  facet_wrap(~fruit)

dummy <- ggplot(data = d, aes(x = farm, y = weight))+ facet_wrap(~fruit) + 
  geom_rect(aes(fill=size), xmin=-Inf, xmax=Inf, ymin=-Inf, ymax=Inf) +
  theme_minimal()

g1 <- ggplotGrob(p1)
g2 <- ggplotGrob(dummy)

gtable_select <- function (x, ...) 
{
  matches <- c(...)
  x$layout <- x$layout[matches, , drop = FALSE]
  x$grobs <- x$grobs[matches]
  x
}

panels <- grepl(pattern="panel", g2$layout$name)
strips <- grepl(pattern="strip-t", g2$layout$name)
g2$layout$t[panels] <- g2$layout$t[panels] - 1
g2$layout$b[panels] <- g2$layout$b[panels] - 1

new_strips <- gtable_select(g2, panels | strips)
grid.newpage()
grid.draw(new_strips)

gtable_stack <- function(g1, g2){
  g1$grobs <- c(g1$grobs, g2$grobs)
  g1$layout <- transform(g1$layout, z= z-max(z), name="g2")
  g1$layout <- rbind(g1$layout, g2$layout)
  g1
}

new_plot <- gtable_stack(g1, new_strips)
grid.newpage()
grid.draw(new_plot)
1个回答

2

这篇回答中借用以下函数,你可以先从虚拟图中提取出图例。

# Extract only the legend from "dummy" plot
g_legend <- function(dummy){ 
  tmp <- ggplot_gtable(ggplot_build(dummy)) 
  leg <- which(sapply(tmp$grobs, function(x) x$name) == "guide-box") 
 legend <- tmp$grobs[[leg]] 
return(legend)} 
# Assign the legend to a separate object
facet.legend <- g_legend(dummy)

您可以使用来自包gridExtragrid.arrange()...

library(gridExtra)
jpeg("plot-with-facet-legend.jpg", width = 8, height = 6, units = "in", res = 300)
print(grid.arrange(new_plot, facet.legend, nrow = 2, widths = c(7, 1), heights = c(6, 0.01)))
dev.off()

... 生成以下图表:

plot with additional legend for colored facet headers

另外:更紧凑的解决方案是直接从您的 g2 对象中获取图例,然后执行相同的 jpeg(...)print(grid.arrange(...)) 代码:

facet.legend <- g2$grobs[[which(sapply(g2$grobs, function(x) x$name) %in% "guide-box")]]

当然,您可以尝试使用widthsheights参数来制作更整洁的图表,可能还有其他比我的方法更好的解决方案,但希望这至少大致符合您的要求。


1
非常好用,谢谢!将 grid.arrange 更改为 ggdraw() + draw_plot(new_plot, 0, 0, 1, 1) + draw_plot(facet.legend, 0.63, 0.05, .3, .3),以便将 facet.legend 放在 new_plot 的顶部,利用图形的无法使用的空间,以节省空间。使用了 library(cowplot) - Jei

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接