R中如何以区县质心为基点为印度古吉拉特邦邻接区县填充渐变色
实现方案
坐标校准(必做,解决距离计算偏差)
GADM下载的原始数据为WGS84经纬度坐标系,直接计算几何距离存在误差,先转换为适配古吉拉特邦的等距投影坐标系(单位为米),方便按公里设置辐射半径:
# EPSG:24378为印度1975坐标系I区,单位米,适配古吉拉特邦区域的距离计算 dist_level_map_Gujarat_proj <- st_transform(dist_level_map_Gujarat, crs = 24378)
选定目标区县,提取辐射基准点
指定目标区县,提取其质心作为圈层辐射的圆心,替换代码中区县名即可适配不同目标:
# 示例以艾哈迈达巴德县为目标区县,按需替换NAME_2字段的取值 target_dist_name <- "Ahmadabad" target_centroid <- dist_level_map_Gujarat_proj %>% filter(NAME_2 == target_dist_name) %>% st_centroid()
距离计算与范围筛选
计算所有区县质心到目标点的直线距离,筛选出指定辐射半径覆盖的区县:
# 设置辐射半径,单位为米,示例为100公里 radius <- 100 * 1000 # 批量计算各区县到目标质心的距离 dist_level_map_Gujarat_proj$dist_to_target <- st_distance( st_centroid(dist_level_map_Gujarat_proj), target_centroid, by_element = TRUE ) %>% as.numeric() # 标记辐射范围内的区县,范围外取值为NA不参与渐变填色 dist_level_map_Gujarat_proj$fill_value <- ifelse( dist_level_map_Gujarat_proj$dist_to_target <= radius, dist_level_map_Gujarat_proj$dist_to_target, NA )
*如果只需要对和目标区县直接邻接的区县填色,不需要按半径筛选,可先用以下代码提取邻接区县,再对邻接区县做距离计算:
# 提取空间上直接邻接的区县 neighbor_flag <- st_touches( dist_level_map_Gujarat_proj %>% filter(NAME_2 == target_dist_name), dist_level_map_Gujarat_proj, sparse = FALSE ) %>% as.vector() # 仅保留邻接区县参与后续填色 dist_level_map_Gujarat_proj$fill_value[!neighbor_flag] <- NA
绘制圈层渐变填色图
完全匹配plotrix::draw.circle的视觉效果:三等分辐射圈层、紫色圈层边框、由深到浅的粉紫色渐变填充:
p_radius_gradient <- ggplot() + # 绘制辐射范围外的区县,统一浅灰色填充 geom_sf( data = dist_level_map_Gujarat_proj %>% filter(is.na(fill_value)), fill = "#f0f0f0", color = "white", linewidth = 0.3 ) + # 绘制辐射范围内的区县,按距离映射渐变填充 geom_sf( data = dist_level_map_Gujarat_proj %>% filter(!is.na(fill_value)), aes(fill = fill_value), color = "white", linewidth = 0.3 ) + # 高亮目标区县本身 geom_sf( data = dist_level_map_Gujarat_proj %>% filter(NAME_2 == target_dist_name), fill = "#990000", color = "white", linewidth = 0.5 ) + # 绘制紫色圈层参考线,对应100公里半径的三等分圈层,和draw.circle效果一致 geom_sf( data = st_buffer(target_centroid, dist = c(33000, 66000, 100000)), fill = NA, color = "purple", linetype = 1, linewidth = 0.5 ) + # 配置渐变色,完全复用draw.circle示例的色值,距离越近颜色越深 scale_fill_gradientn( colours = c("#ff00ff", "#ff77ff", "#ffccff"), na.value = "transparent", name = "距目标质心距离(米)" ) + theme_void() # 查看静态图 p_radius_gradient # 转换为交互图 ggplotly(p_radius_gradient)
自定义调整
- 渐变色可直接修改
scale_fill_gradientn()中colours参数的色值实现 - 辐射半径修改
radius变量的数值即可,单位为米 - 不需要显示圈层参考线直接删除对应
geom_sf()图层即可
内容的提问来源于stack exchange,提问作者LeMarque
相关产品推荐
相关产品推荐

