You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Shiny应用中使用leaflet.extras捕获绘制多边形失败的问题求助

问题:Shiny Leaflet绘制多边形无法捕获事件及解决方法

问题详情

开发Shiny应用时,使用leaflet、leaflet.extras实现地图多边形绘制功能,但绘制完成后无法触发map_draw_created事件,点击Save按钮也无法保存多边形坐标,控制台无对应日志输出。已确认所有依赖包为最新版本。

简化代码如下:

#########################################################################
library(shiny)
library(leaflet)
library(leaflet.extras)

ui <- fluidPage(
  titlePanel("Draw Polygons on Map"),
  leafletOutput("map"),
  actionButton("save", "Save Drawn Areas"),
  dataTableOutput("coordsTable")
)

server <- function(input, output, session) {
  output$map <- renderLeaflet({
    leaflet() %>%
      addTiles() %>%
      setView(lng = 2.3522, lat = 48.8566, zoom = 12) %>%
      addDrawToolbar()
  })

  observeEvent(input$map_draw_created, {
    shape <- input$map_draw_created
    cat("Draw event triggered. Layer type:", shape$layerType, "\n")
    print(shape)
  })
}

shinyApp(ui = ui, server = server)
####################################################################################

原因分析

  1. addDrawToolbar()默认配置未明确锁定多边形绘制的事件监听逻辑,缺少必要的编辑权限配置,导致绘制完成后事件无法传递到Shiny服务器。
  2. 原代码未关联Save按钮与多边形数据的持久化存储逻辑,仅依赖map_draw_created事件但未保留数据,无法实现“保存”操作。

解决步骤

1. 配置DrawToolbar的绘制选项

明确指定允许绘制的类型(仅多边形),并启用编辑/删除功能,确保事件能正常触发并传递。

2. 用reactiveValues存储多边形数据

创建响应式变量累积保存所有绘制的多边形,方便后续展示或导出。

3. 关联事件与保存逻辑

  • 监听map_draw_created事件,将新绘制的多边形坐标存入响应式变量。
  • 监听Save按钮,将存储的坐标转换为表格格式展示。

修改后的完整代码

library(shiny)
library(leaflet)
library(leaflet.extras)
library(dplyr)

ui <- fluidPage(
  titlePanel("Draw Polygons on Map"),
  leafletOutput("map"),
  actionButton("save", "Save Drawn Areas"),
  dataTableOutput("coordsTable")
)

server <- function(input, output, session) {
  # 初始化响应式变量存储所有绘制的多边形
  drawn_polygons <- reactiveValues(data = data.frame())

  output$map <- renderLeaflet({
    leaflet() %>%
      addTiles() %>%
      setView(lng = 2.3522, lat = 48.8566, zoom = 12) %>%
      addDrawToolbar(
        targetGroup = "drawn",
        drawOptions = drawOptions(
          polygonOptions = polygonOptions(color = "#3388ff"),
          # 只启用多边形绘制,可按需添加其他类型
          polylineOptions = FALSE,
          circleOptions = FALSE,
          rectangleOptions = FALSE,
          markerOptions = FALSE,
          circleMarkerOptions = FALSE
        ),
        editOptions = editOptions(
          selectedPathOptions = selectedPathOptions(),
          # 允许编辑/删除已绘制图形
          edit = TRUE,
          remove = TRUE
        )
      ) %>%
      addLayersControl(overlayGroups = "drawn", position = "topright")
  })

  # 监听绘制完成事件,保存新多边形
  observeEvent(input$map_draw_created, {
    shape <- input$map_draw_created
    cat("Draw event triggered. Layer type:", shape$layerType, "\n")
    
    # 提取多边形坐标并格式化
    coords <- shape$geometry$coordinates[[1]] %>%
      as.data.frame() %>%
      rename(lng = V1, lat = V2) %>%
      mutate(polygon_id = nrow(drawn_polygons$data) + 1)
    
    # 追加到存储变量
    drawn_polygons$data <- rbind(drawn_polygons$data, coords)
  })

  # 监听Save按钮,展示所有多边形坐标
  observeEvent(input$save, {
    output$coordsTable <- renderDataTable({
      drawn_polygons$data
    })
  })
}

shinyApp(ui = ui, server = server)

验证方法

  1. 运行修改后的代码,在地图上绘制多边形,R控制台会输出事件触发日志。
  2. 点击Save按钮,下方表格会展示所有绘制的多边形坐标(包含多边形ID、经度、纬度)。

内容的提问来源于stack exchange,提问作者 cea

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.02 07:20:03