简体   繁体   English

ggplot 将水平线添加到分组的分类数据并共享图例

[英]ggplot add horizontal line to grouped categorical data and share legend

Here is some code that makes a categorical bar chart and places a mean line on the chart.这是一些制作分类条形图并在图表上放置平均线的代码。 The problem is that the legends are separate and I can't figure out how to stick them together.问题是图例是分开的,我不知道如何将它们粘在一起。 I think I have made a dummy variable in the past and included it in the scale_manual arguments but geom_vline doesn't handle the "fill" mappings.我想我过去制作了一个虚拟变量并将其包含在 scale_manual arguments 但 geom_vline 不处理“填充”映射。 Any ideas?有任何想法吗?

library(tidyverse)
data(mtcars)

y = mean(mtcars$mpg)
x = unique(mtcars$cyl)
meanDf <- 
  data.frame(x, y )


mtcars$mean = y
mtcars$group = "mean"

mtcars %>%


ggplot(aes(x = factor(cyl), y = mpg, fill = factor(carb))) +
  geom_col(position = "dodge") +
  geom_hline(data = meanDf, aes(yintercept = y, color = "")) +
  scale_fill_manual(name = "", values = c("blue", "red", "green", "white", "black", "yellow"), labels = paste("myLabel", 1:6)) +
  scale_color_manual(name = "", values = "red", label = "myLabel") +
  theme(panel.background = element_rect(fill = "white")) +
  theme(legend.background = element_rect(color = "black", fill = "white")) 
  
  

I think for readability, it's better to separate them out.我认为为了可读性,最好将它们分开。 However, for formatting purpose, you sure can bring them as close as you want by dropping the legend.title (not just assigning it an empty string) and adjusting the legend.margin and legned.spacing .但是,出于格式化目的,您可以通过删除legend.title (不仅仅是为其分配一个空字符串)并调整legend.marginlegned.spacing来使它们尽可能接近。 For instance,例如,

library(tidyverse)
data(mtcars)

y = mean(mtcars$mpg)
x = unique(mtcars$cyl)
meanDf <- 
  data.frame(x, y )


mtcars$mean = y
mtcars$group = "mean"

mtcars %>%
  ggplot(aes(x = factor(cyl), y = mpg, fill = factor(carb))) +
  geom_col(position = "dodge") +
  geom_hline(data = meanDf, aes(yintercept = y, color = "")) +
  scale_fill_manual(name = "", values = c("blue", "red", "green", "white", "black", "yellow"), labels = paste("myLabel", 1:6)) +
  scale_color_manual(name = "", values = "red", label = "myLabel") + 
  theme(
    legend.title = element_blank(), 
    legend.margin = margin(t = 0, b = 0, r = 2, l = 2),
    legend.spacing.y = unit(.5, "pt")
  )

Output Output 资源

One option would be to use only the fill scale and make use of custom key glyph.一种选择是仅使用fill比例并使用自定义键字形。

  1. Set the color for the geom_hline as an argument instead of mapping on the color aes.geom_hline的颜色设置为参数,而不是在color aes 上进行映射。 Instead map a constant eg "" on the fill aes.取而代之的是 map fill aes 上的常量,例如"" A Drawback is that we get a warning.缺点是我们会收到警告。
  2. Add an additional color and label to scale_fill_manual .将额外的颜色和 label 添加到scale_fill_manual
  3. To get a line as the key glyph for the geom_hline I make use of a custom key glyph which conditionally on the fill color switches between draw_key_path and the default key glyph for geom_col .为了获得一条线作为geom_hline的键字形,我使用了一个自定义键字形,它有条件地在draw_key_pathgeom_col的默认键字形之间切换fill颜色。 To make this work I use a "red2" as the additional fill color for the hline which I switch to "red" inside the custom key glyph function.为了完成这项工作,我使用"red2"作为线的附加填充颜色,我在自定义键字形 function 内切换为"red"
library(tidyverse)
data(mtcars)

y = mean(mtcars$mpg)
x = unique(mtcars$cyl)
meanDf <- data.frame(x, y )

mtcars$mean = y
mtcars$group = "mean"

draw_key_cust <- function(data, params, size) {
  if (data$fill %in% c("red2")){
    data$colour <- "red"
    data$fill <- NA
    draw_key_path(data, params, size)  
  } else
    GeomCol$draw_key(data, params, size)
}

mtcars %>%
  ggplot(aes(x = factor(cyl), y = mpg, fill = factor(carb))) +
  geom_hline(data = meanDf, aes(yintercept = y, fill = ""), color = "red") +
  geom_col(key_glyph = "cust") +
  scale_fill_manual(name = NULL, values = c("red2", "blue", "red", "green", "white", "black", "yellow"), labels = c("label", paste("myLabel", 1:6))) +
  theme(panel.background = element_rect(fill = "white")) +
  theme(legend.background = element_rect(color = "black", fill = "white"))
#> Warning: Ignoring unknown aesthetics: fill

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM