ggplot2中同一特征的颜色与形状图例合并技术问询
合并ggplot2中的颜色与形状图例
要合并颜色(colour)和形状(shape)图例,核心是让这两个美学映射绑定到同一个变量,并且统一图例的配置(名称、排列等),避免生成两个独立的引导项。下面针对你的代码给出具体解决方案:
问题分析
你当前的代码中,虽然colour和shape都映射到了EQ变量,但因为以下两点导致图例分开:
- 在
labs()中设置了shape = element_blank(),使得形状图例的标题为空,与颜色图例的默认标题(EQ)不一致 - 在
guides()中分别配置了shape和colour的引导规则,强制生成两个独立图例
修改后的完整代码
library(ggplot2) library(dplyr) # 确保加载dplyr以支持sample_n函数 # 你的示例数据 ALL_Spans <- structure(list(UG = c("100", "124", "108", "92", "124", "84", "100", "100", "124", "84"), S = c(12, 12, 12, 12, 12, 12, 12, 12, 12, 12), EQ = c("Cai", "AASHTO LRFD", "Suksawang & Nassif", "AASHTO LRFD", "Modified Henry", "Modified Henry", "Analytical Data", "Rigid Rotation", "Rigid Rotation", "Rigid Rotation"), DF = c(0.818313323177077, 1.01028571424963, 0.741281190719393, 1.08244897959184, 0.858545454545455, 0.858545454545455, 0.789710362673591, 0.71825, 0.926666666666667, 0.926666666666667), Girder = c("Exterior Girder", "Exterior Girder", "Exterior Girder", "Interior Girder", "Interior Girder", "Exterior Girder", "Exterior Girder", "Interior Girder", "Exterior Girder", "Exterior Girder" ), Type = c("Moment LLDF", "Shear LLDF", "Moment LLDF", "Shear LLDF", "Moment LLDF", "Moment LLDF", "Moment LLDF", "Moment LLDF", "Moment LLDF", "Moment LLDF"), L = c(240L, 300L, 260L, 220L, 300L, 200L, 240L, 240L, 300L, 200L), group = c("Cai 12", "AASHTO LRFD 12", "Suksawang & Nassif 12", "AASHTO LRFD 12", "Modified Henry 12", "Modified Henry 12", "Analytical Data 12", "Rigid Rotation 12", "Rigid Rotation 12", "Rigid Rotation 12" )), row.names = c(NA, -10L), class = "data.frame") b <- ggplot(data = ALL_Spans, aes(x = L, y = DF, colour = EQ, shape = EQ)) + geom_point(stroke = 0.2, size = 2) + geom_line(size = 0.2, linetype = "dotted") + # 保持两个scale的名称一致(默认均为EQ,也可手动指定name参数) scale_shape_manual(values = c(0,19,3,2,4,5,6,8)) + scale_colour_manual(values = c("black", "red", rep("black",6))) + scale_x_continuous(breaks = seq(200,300,20), limits = c(200,300)) + labs(x = "x", y = element_blank()) + # 移除shape的空标题设置,统一图例标题 theme_classic() + theme(legend.title.align = 0.5, legend.position = "bottom", axis.text = element_text(size=8, colour="black"), axis.title.x = element_text(size=8, colour="black"), axis.line = element_blank(), axis.ticks = element_line(colour = "black", size = 0.2), legend.text = element_text(size=8, margin = margin(-10,5,-10,-4.5)), legend.title = element_text(size=8, margin = margin(-10,1.5,-10,0)), legend.spacing.x = unit(0.1, 'cm'), legend.spacing.y = unit(0, 'cm'), legend.background = element_blank(), panel.margin.y = unit(0.3, "lines"), legend.box.background = element_rect(color = "black", size = 0.2)) + # 仅配置colour的引导规则,同时控制颜色和形状,关闭独立的shape引导 guides(colour = guide_legend(nrow=2, byrow=TRUE), linetype = FALSE, shape = FALSE) + facet_grid(Type~Girder) print(b)
关键修改点说明
- 统一图例标题:移除了
labs()中的shape = element_blank(),让colour和shape的图例标题保持一致(默认都是EQ),这是合并图例的核心前提。如果需要自定义标题,只需在labs()中添加colour = "你的自定义标题",shape图例会自动继承该标题。 - 合并引导配置:在
guides()中仅保留colour的引导设置,同时将shape设为FALSE,这样ggplot会自动把形状和颜色合并到同一个图例中,共享nrow=2, byrow=TRUE的排列规则。 - 优化映射写法:将
shape = EQ移到了顶层的aes()中,让代码更整洁(多个图层共享的映射推荐放在顶层)。
这样修改后,颜色和形状就会合并成一个图例,每个条目同时显示对应的颜色和形状,完全符合你的需求。
内容的提问来源于stack exchange,提问作者Maral Dorri
相关产品推荐
相关产品推荐

