ggplot使用scale_linetype_manual时仅让geom_vline图例项为竖线的问题
解决方法
出现该问题的核心原因是ggplot2默认会将所有映射到colour和linetype的分类合并为同一个图例,导致geom_vline的图例样式会覆盖所有同组图例条目的展示形态。可以用以下两种方案实现需求:
方案1:原生ggplot2实现(无额外依赖,推荐)
仅需新增guides配置段,单独指定每个图例条目对应的图标样式即可,修改后完整代码如下:
library(ggplot2) # 补充示例数据集,实际使用时可删除该行 df <- data.frame(a = seq(-1,1,0.01), b = rnorm(201), c = rnorm(201, mean = 2)) ggplot(data = df) + geom_line(aes(x = a, y = b, colour = "one", linetype = "one"), size = 2) + geom_line(aes(x = a, y = c, colour = "two", linetype = "two"), size = 2) + # 开启geom_vline的图例展示 geom_vline(aes(xintercept = 0.5, colour = "three", linetype = "three"), alpha = 1, show.legend = T) + scale_colour_manual("", breaks = c("one", "two", "three"), values = c("blue", "red", "green")) + scale_linetype_manual("", breaks = c("one", "two", "three"), values = c("dashed", "solid", "solid")) + # 新增的图例样式覆盖配置 guides( colour = guide_legend(override.aes = list( # 前两个条目用折线默认的横线图标,第三个用竖线图标 key_glyph = c("path", "path", "vline"), size = c(2,2,2) )), linetype = guide_legend(override.aes = list( key_glyph = c("path", "path", "vline"), size = c(2,2,2) )) ) + theme_bw() + theme(legend.key.size = unit(2, "cm"), legend.position = c(0.05, 0.995), legend.justification = c(0.05, 0.995))
该方案支持ggplot2 3.3.0及以上版本使用。
方案2:用ggnewscale包拆分图例
如果需要更灵活的图例自定义,可以用ggnewscale包将折线和竖线的比例尺拆分为独立组,避免样式互相干扰:
library(ggplot2) library(ggnewscale) # 补充示例数据集,实际使用时可删除该行 df <- data.frame(a = seq(-1,1,0.01), b = rnorm(201), c = rnorm(201, mean = 2)) ggplot(data = df) + geom_line(aes(x = a, y = b, colour = "one", linetype = "one"), size = 2) + geom_line(aes(x = a, y = c, colour = "two", linetype = "two"), size = 2) + scale_colour_manual("", breaks = c("one", "two"), values = c("blue", "red")) + scale_linetype_manual("", breaks = c("one", "two"), values = c("dashed", "solid")) + # 插入新的颜色、线型比例尺,专门给竖线使用 new_scale_colour() + new_scale("linetype") + geom_vline(aes(xintercept = 0.5, colour = "three", linetype = "three"), alpha = 1, show.legend = T) + scale_colour_manual("", breaks = "three", values = "green") + scale_linetype_manual("", breaks = "three", values = "solid") + theme_bw() + theme(legend.key.size = unit(2, "cm"), legend.position = c(0.05, 0.995), legend.justification = c(0.05, 0.995))
使用该方案需要先安装ggnewscale包:install.packages("ggnewscale")
内容的提问来源于stack exchange,提问作者salomon
相关产品推荐
相关产品推荐

