annotation_scale()搭配coords_sf()时比例尺不准确的问题求助
解决annotation_scale()无法识别地理范围的问题
你的问题出在底图数据没有空间参考(CRS)信息:你用map_data()得到的是普通data.frame,虽然经纬度是地理坐标,但ggplot和ggspatial无法识别它的单位(度),导致annotation_scale()错误计算了比例尺长度。
修复方案:将底图转为sf对象并使用geom_sf绘制
把map_data返回的多边形数据转换成sf格式,指定正确的地理坐标系(WGS84,EPSG:4326),再用geom_sf()替代geom_polygon(),这样annotation_scale()就能读取到空间元数据,正确计算比例尺。
修改后的完整代码:
library(ggplot2) library(maps) library(mapdata) library(ggpubr) library(ggspatial) library(sf) # 获取底图数据并转换为sf对象 region <- map_data("world2Hires") region <- subset(region, region %in% c('Canada', 'USA')) region$long = (360 - region$long)*-1 # 转换经纬度 # 将data.frame转为sf对象,指定CRS为WGS84(EPSG:4326) region_sf <- st_as_sf(region, coords = c("long", "lat"), crs = 4326) %>% group_by(region, group) %>% summarise(do_union = FALSE) %>% st_cast("POLYGON") # 拆分加拿大和美国图层 Canada_sf <- subset(region_sf, region == 'Canada') USA_sf <- subset(region_sf, region == 'USA') # 设置地图范围 lons = c(-68, -59.5) lats = c(43, 48) # 绘制地图 study.area <- ggplot() + coord_sf(xlim = lons, ylim = lats) + geom_sf(data = Canada_sf, colour = "grey20", fill = "grey85") + geom_sf(data = USA_sf, colour = "grey20", fill = "grey93") + xlab("Longitude") + ylab("Latitude") + theme_bw() + theme(panel.grid.minor = element_blank(), panel.grid.major = element_blank(), panel.background = element_blank(), axis.text = element_text(size = 11), axis.title = element_text(size = 12)) + theme(plot.margin = unit(c(0.5,0.5,0.2,0.3), "cm")) + # geom_point(data = mydata, aes(long, lat, fill=type), colour="black", pch=21) # 取消注释恢复你的数据点 labs(shape = "year") + annotation_scale(location = "bl", width_hint = 0.5) # 可指定位置和宽度比例 study.area
关键修改点说明:
st_as_sf():将普通经纬度数据转为sf对象,crs = 4326告诉系统这是WGS84地理坐标系(常用的GPS经纬度)。group_by() + summarise() + st_cast():修复map_data拆分组后的多边形结构,确保sf对象能正确识别多边形边界。geom_sf():替代geom_polygon(),直接绘制sf空间对象,保留CRS信息供annotation_scale()读取。
这样修改后,annotation_scale()就能识别地图的地理范围,生成符合实际长度的比例尺(比如你的范围会显示几十公里的比例尺)。
内容的提问来源于stack exchange,提问作者maribio18
相关产品推荐
相关产品推荐

