散点图图例颜色的形状覆盖不是实际形状

4
您可以在下图中看到,“颜色”图例不正确。我期望看到的是一个有颜色的圆圈(例如,颜色一应该是绿色的圆圈),然而背景是绿色的,并且您可以看到黑色的覆盖,这似乎是某种范围框。

enter image description here

以下是我的代码:

library(ggmap)

c_map <- c(left = -86.817417, bottom = 36.133247, right = -86.793141, top = 36.153650)
campus <- get_stamenmap(c_map, zoom = 15, maptype = "toner-lines")

some_data <- read.csv('https://gist.githubusercontent.com/pconwell/085c1413e418adaa7c1e203c9680a0f8/raw/c7a3e5f7aa900de6bc2bcccd5dc5d9b8f7e31b81/some_data.csv')

ggmap(campus, darken = c(0.33, "white"), extent = "device") + 

  stat_density2d(data = some_data,
                 aes(x = longitude,
                     y = latitude,
                     fill = stat(nlevel),
                     alpha = stat(nlevel)),
                 size = 2,
                 bins = 12,
                 geom = "polygon"
  ) +

  scale_fill_gradientn(guide = "colorbar",
                       colours = c("#adddd1", "#3e98af", "#375980"),
                       breaks=c(0.2, 0.9), 
                       labels=c("Least","Most"), 
                       name = "Heat Map"
  ) +

  geom_point(data = some_data,
             aes(x = longitude,
                 y = latitude,
                 color = color,
                 shape = shape),
             alpha = .75,
             size = 4

  )  +

  scale_alpha_continuous(range = c(0.33, 0.66), 
                         guide = FALSE
  )

我该如何使图例正确显示颜色?图标在地图中显示正确,但在图例中未能正确显示。


不是直接关于问题,但建议:使用ggmap获取底图需要一个Google地图API密钥。将ggmap调用替换为仅在数据集上使用ggplot可以消除对API密钥的要求,但仍然重新创建了问题,使更多人能够提供帮助。 - camille
奇怪,我不记得曾经使用过API密钥 - 但如果使用stamen地图可能会有所不同。不过我会考虑改用ggplot。 - Patrick Conwell
1
我认为这是基于一段时间前的更新,通常需要一个API密钥。ggmap对于问题也不是必要的。在密度中似乎有一个大小参数,可能是从以前版本中保留下来的?在密度层中没有任何需要大小的内容,但是size = 2是创建颜色图例点周围大小为2的边框的原因 - 删除该参数即可消除边框。 - camille
我猜我之前输入了一个API密钥 - 我不记得了,ggmap也没有抱怨过...但回到你的观点,将ggplot换成ggmap会给我带来错误Error: 'data' must be a data frame, or other object coercible by 'fortify()', not an S3 object with class ggmap/raster,我猜这与get_stamenmap()有关,但我还没有想出如何解决。但我会继续寻找。 - Patrick Conwell
1
stat_density2d中的size = 2替换为color = 'transparent';多边形描边会被图例捕捉到。 - alistaire
@alistaire - 你真是个天才,谢谢! - Patrick Conwell
2个回答

3
一个简化版本的问题(去掉了需要使用ggmap和Google API密钥的要求),主要是关于多余的参数。逐层分解代码,因为这些层建立起图例中包含的内容。在您的stat_density2d中,size参数与设置为多边形的几何体没有任何关系;它只对轮廓线(如下所示)有意义:
library(ggplot2)

some_data <- read.csv('https://gist.githubusercontent.com/pconwell/085c1413e418adaa7c1e203c9680a0f8/raw/c7a3e5f7aa900de6bc2bcccd5dc5d9b8f7e31b81/some_data.csv')

ggplot(some_data, aes(x = longitude, y = latitude)) +
  geom_point(aes(color = color, shape = shape), alpha = 0.75, size = 4) +
  stat_density2d(aes(alpha = stat(nlevel)),
                 size = 2) + 
  guides(alpha = "none",
         color = guide_legend(override.aes = list(fill = NA)))

从上面的密度和图例中可以看出,size = 2 的效果是增加线条的粗细。

由于这对于多边形来说并不必要,因此可以删除 size 参数或将其设置为 0。此外,由于密度图层中有填充元素,会在图例中产生深色区域。通过在图例中明确将填充设置为 NA,可以消除这种情况。

ggplot(some_data, aes(x = longitude, y = latitude)) +
  geom_point(aes(color = color, shape = shape), alpha = 0.75, size = 4) +
  stat_density2d(aes(fill = stat(nlevel), alpha = stat(nlevel)),
                 size = 0,
                 geom = "polygon") + 
  guides(alpha = "none",
         color = guide_legend(override.aes = list(fill = NA)))


当我运行你的示例时,第二个图中的颜色图例仍然有边框。我认为这是由于图形设备(我在Windows上),因为当我使用Cairo_png()设备渲染时,边框消失了:我假设宽度为零。 - Mikko Marttila
@MikkoMarttila 奇怪。我用的是Mac,没有其他设备可以测试,但图形设备可能会很棘手。 - camille

1
背景和边界框来自多边形颜色的图例。这里有一个更简单的可重现示例:
library(ggplot2)
#> Warning: package 'ggplot2' was built under R version 3.5.3

set.seed(42)
df <- as.data.frame(MASS::mvrnorm(100, c(0, 0), matrix(c(1, .6), 2, 2)))

ggplot(df, aes(V1, V2)) +
  stat_density_2d(geom = "polygon") +
  geom_point(aes(colour = cut_number(V1, 5)))

你可以通过显式设置多边形几何体的颜色来解决这个问题:
ggplot(df, aes(V1, V2)) +
  stat_density_2d(geom = "polygon", colour = NA) +
  geom_point(aes(colour = cut_number(V1, 5)))

然而,我有点惊讶的是,即使相关图层没有任何映射到颜色的内容,多边形图例仍然显示出来。也许这是一个错误吗?
更新:我无法复制其他几何或统计数据的此行为,因此我更深入地研究了2D密度:奇怪的是,似乎多边形的颜色图例出现是因为StatDensity2d具有颜色的默认美学值:
StatDensity2d$default_aes
#> Aesthetic mapping: 
#> * `colour` -> "#3366FF"
#> * `size`   -> 0.5
StatDensity2d$default_aes <- aes()

ggplot(df, aes(V1, V2)) +
  stat_density_2d(geom = "polygon") +
  geom_point(aes(colour = cut_number(V1, 5)))

此内容由reprex package (v0.3.0)于2019-07-04创建


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