我试图仅绘制世界地图的一部分,由一个正方形限制,该正方形的限制为 lon (-30, 90) 和 lat (30, 82)。当我尝试使用 sf_crop 裁剪地图时,使用 ggplot 绘图时它不会返回所需的正方形,即使我确保使用的世界地图具有指定 crs = 4326 的“正常”crs。 我知道我可能可以用 coord_sf 引入地图限制,但我需要一个替代解决方案。我真的很感激任何帮助。
我尝试了以下代码,它产生了所描述的问题:
lapply(c("rnaturalearthdata", "sf", "ggplot2","dplyr"), require, character.only = TRUE)
world <- ne_coastline(scale = "small", returnclass = "sf") %>%
st_transform(world, crs = 4326)
world_cropped <- st_crop(world, xmin = -30, xmax = 90, ymin = 30, ymax = 82)
ggplot() +
geom_sf(data = world, fill = NA, color = "black")
ggplot() +
geom_sf(data = world_cropped, fill = NA, color = "black")
使用地理坐标 (WGS84 / EPSG:4326) 时,
sf
默认情况下通过 s2 使用球面几何操作。因此,由 4 个角定义的边界框并不是真正的矩形;而是由 4 个角定义的边界框。当投影到平面上时,它的 2 条边变成圆弧。我们可以通过使用 st_segmentize()
: 添加更多点到 bbox 的“直”边缘来可视化它
library(rnaturalearth)
library(ggplot2)
library(sf)
world <- ne_coastline(scale = "small")
bb_wgs84 <-
st_bbox(c(xmin = -30, xmax = 90, ymin = 30, ymax = 82), crs = "WGS84") |>
st_as_sfc()
world_cropped <- st_crop(world, bb_wgs84)
ggplot() +
geom_sf(data = st_segmentize(bb_wgs84, 1000), fill = "lightgreen", alpha = .2) +
geom_sf(data = bb_wgs84, fill = NA, color = "darkgreen", linewidth = 1) +
geom_sf(data = world_cropped, fill = NA)
可能最简单的解决方法是关闭 s2 进行裁剪操作,因此坐标被视为平面坐标,这允许您可能需要进行矩形裁剪。
sf_use_s2(use_s2 = FALSE)
#> Spherical geometry (s2) switched off
world_cropped <- st_crop(world, xmin = -30, xmax = 90, ymin = 30, ymax = 82)
#> although coordinates are longitude/latitude, st_intersection assumes that they
#> are planar
#> Warning: attribute variables are assumed to be spatially constant throughout
#> all geometries
sf_use_s2(use_s2 = TRUE)
#> Spherical geometry (s2) switched on
ggplot() +
geom_sf(data = st_segmentize(bb_wgs84, 1000), fill = "lightgreen", alpha = .2) +
geom_sf(data = bb_wgs84, fill = NA, color = "darkgreen", linewidth = 1) +
geom_sf(data = world_cropped, fill = NA)
创建于 2024-07-09,使用 reprex v2.1.0