在闪亮的应用程序中识别图中选定点的问题

Problem with identifying selected point in the plotly in a shiny app

我正在尝试在闪亮的应用程序中使用 Plotly 函数绘制一些地理数据。问题是我在地图上选择了点,没有正确发生如下所示:

根据上图,选中的点“NOE_TASAODF”标签为“KH”(地图侧) 并且它与 plotly 返回的信息不一致。 这是代码:

library(shiny)
library(plotly)
library(DT)
library(dplyr)    
ui <- fluidPage(
plotlyOutput("plot"),
verbatimTextOutput("hover"),
verbatimTextOutput("click"),
verbatimTextOutput("brushing"),
verbatimTextOutput("selecting"),
verbatimTextOutput("brushed"),
verbatimTextOutput("selected"))
server <- function(input, output) {
qom<<-structure(list(ID2 = c(183, 235, 248, 282, 290, 329, 676, 689, 
                             725, 777, 17, 25, 39, 41, 47, 49, 52, 67, 79, 112, 1, 2, 3, 5, 
                             7, 15, 16, 19, 20, 24), xpos = c(34.5836111111111, 34.4836111111111, 
                                                              35.0605555555556, 34.3677777777778, 34.6444444444444, 34.6472222222222, 
                                                              34.7180555555556, 34.6727777777778, 34.6513888888889, 34.7725, 
                                                              34.4994444444444, 34.6211111111111, 34.4463888888889, 34.5725, 
                                                              34.6394444444444, 34.5369444444444, 34.6655555555556, 34.625, 
                                                              34.5658333333333, 34.5122222222222, 34.6338888888889, 34.6391666666667, 
                                                              34.56, 34.6458333333333, 34.6086111111111, 34.6372222222222, 
                                                              34.5597222222222, 34.6452777777778, 34.6327777777778, 34.6152777777778
                             ), ypos = c(50.7491666666667, 50.4527777777778, 50.8752777777778, 
                                         50.5058333333333, 50.9227777777778, 50.8780555555556, 50.8672222222222, 
                                         50.8413888888889, 50.3944444444444, 50.5, 50.5108333333333, 50.8358333333333, 
                                         51.1144444444444, 50.4405555555556, 50.8763888888889, 50.4394444444444, 
                                         50.9141666666667, 50.9077777777778, 50.3733333333333, 50.5461111111111, 
                                         50.8686111111111, 50.8766666666667, 50.7961111111111, 50.8597222222222, 
                                         50.8422222222222, 50.8777777777778, 50.7961111111111, 50.8588888888889, 
                                         50.8694444444444, 50.8583333333333), DARON_BRON = c("B", "B", 
                                                                                             "B", "B", "B", "D", "B", "B", "B", "B", "B", "B", "B", "B", "D", 
                                                                                             "B", "B", "D", "B", "B", "D", "D", "D", "D", "D", "D", "N_A", 
                                                                                             "D", "D", "D"), NOE_TASADOF = c("F", "F", "F", "F", "F", "F", 
                                                                                                                             "F", "F", "F", "F", "KH", "KH", "KH", "KH", "KH", "KH", "KH", 
                                                                                                                             "KH", "KH", "KH", "J", "J", "J", "J", "J", "J", "J", "J", "J", 
                                                                                                                             "J")), row.names = c(NA, -30L), class = "data.frame")
output$plot <- renderPlotly({
    p<-plot_ly(data=qom,
            lat = ~xpos,
            lon = ~ypos,
            color = ~NOE_TASADOF ,
            mode   = 'markers',
            colors=c("blue","green","red"),
            marker = list(size=10),
            type = 'scattermapbox'
    ) %>%
        layout(
            mapbox = list(
                style = 'open-street-map',
                zoom =5
                ,center = list(lon = 50.88, lat = 34.66)
            )
        ) %>%  
        highlight("plotly_selected", dynamic = F,color = NULL)
    
    
    
    p<-p %>% 
        layout(dragmode = "select") %>%
        event_register("plotly_selecting")
    p
})
output$hover <- renderPrint({
    d <- event_data("plotly_hover")
    if (is.null(d)) "Hover events appear here (unhover to clear)" else d
})
output$click <- renderPrint({
    d <- event_data("plotly_click")
    if (is.null(d)) "Click events appear here (double-click to clear)" else qom[d[,2],]
})
output$brushing <- renderPrint({
    d <- event_data("plotly_brushing")
    if (is.null(d)) "Brush extents appear here (double-click to clear)" else d
})
output$selecting <- renderPrint({
    d <- event_data("plotly_selecting")
    if (is.null(d)) "Brush points appear here (double-click to clear)" else d
})
output$brushed <- renderPrint({
    d <- event_data("plotly_brushed")
    if (is.null(d)) "Brush extents appear here (double-click to clear)" else d
})
output$selected <- renderPrint({
    d <- event_data("plotly_selected")
    if (is.null(d)) "Brushed points appear here (double-click to clear)" else d
})
}
shinyApp(ui, server, options = list(display.mode = "showcase"))

编辑:问题可以通过将关键参数传递给 plotly 并从事件中获取来解决,如下所示:

library(shiny)
library(plotly)
library(DT)
library(dplyr)
ui <- fluidPage(
  plotlyOutput("plot"),
  verbatimTextOutput("hover"),
  verbatimTextOutput("click"),
  verbatimTextOutput("brushing"),
  verbatimTextOutput("selecting"),
  verbatimTextOutput("brushed"),
  verbatimTextOutput("selected"))
server <- function(input, output) {
  qom<<-structure(list(ID2 = c(183, 235, 248, 282, 290, 329, 676, 689, 
                           725, 777, 17, 25, 39, 41, 47, 49, 52, 67, 79, 112, 1, 2, 3, 5, 
                           7, 15, 16, 19, 20, 24), xpos = c(34.5836111111111, 34.4836111111111, 
                                                            35.0605555555556, 34.3677777777778, 34.6444444444444, 34.6472222222222, 
                                                            34.7180555555556, 34.6727777777778, 34.6513888888889, 34.7725, 
                                                            34.4994444444444, 34.6211111111111, 34.4463888888889, 34.5725, 
                                                            34.6394444444444, 34.5369444444444, 34.6655555555556, 34.625, 
                                                            34.5658333333333, 34.5122222222222, 34.6338888888889, 34.6391666666667, 
                                                            34.56, 34.6458333333333, 34.6086111111111, 34.6372222222222, 
                                                            34.5597222222222, 34.6452777777778, 34.6327777777778, 34.6152777777778
                           ), ypos = c(50.7491666666667, 50.4527777777778, 50.8752777777778, 
                                       50.5058333333333, 50.9227777777778, 50.8780555555556, 50.8672222222222, 
                                       50.8413888888889, 50.3944444444444, 50.5, 50.5108333333333, 50.8358333333333, 
                                       51.1144444444444, 50.4405555555556, 50.8763888888889, 50.4394444444444, 
                                       50.9141666666667, 50.9077777777778, 50.3733333333333, 50.5461111111111, 
                                       50.8686111111111, 50.8766666666667, 50.7961111111111, 50.8597222222222, 
                                       50.8422222222222, 50.8777777777778, 50.7961111111111, 50.8588888888889, 
                                       50.8694444444444, 50.8583333333333), DARON_BRON = c("B", "B", 
                                                                                           "B", "B", "B", "D", "B", "B", "B", "B", "B", "B", "B", "B", "D", 
                                                                                           "B", "B", "D", "B", "B", "D", "D", "D", "D", "D", "D", "N_A", 
                                                                                           "D", "D", "D"), NOE_TASADOF = c("F", "F", "F", "F", "F", "F", 
                                                                                                                           "F", "F", "F", "F", "KH", "KH", "KH", "KH", "KH", "KH", "KH", 
                                                                                                                           "KH", "KH", "KH", "J", "J", "J", "J", "J", "J", "J", "J", "J", 
                                                                                                                           "J")), row.names = c(NA, -30L), class = "data.frame")
  qom<-qom %>% mutate(key=row.names(qom))
  output$plot <- renderPlotly({
    p<-plot_ly(data=qom,
           lat = ~xpos,
           lon = ~ypos,
           key=~key,
           color = ~NOE_TASADOF ,
           mode   = 'markers',
           colors=c("blue","green","red"),
           marker = list(size=10),
           type = 'scattermapbox'
    ) %>%
  layout(
    mapbox = list(
      style = 'open-street-map',
      zoom =5
      ,center = list(lon = 50.88, lat = 34.66)
    )
  ) %>%  
  highlight("plotly_selected", dynamic = F,color = NULL)



p<-p %>% 
  layout(dragmode = "select") %>%
  event_register("plotly_selecting")
p
  })
  output$hover <- renderPrint({
d <- event_data("plotly_hover")
if (is.null(d)) "Hover events appear here (unhover to clear)" else d$key
  })
  output$click <- renderPrint({
d <- event_data("plotly_click")
if (is.null(d)) "Click events appear here (double-click to clear)" else qom[d$key,]
  })
  output$brushing <- renderPrint({
d <- event_data("plotly_brushing")
if (is.null(d)) "Brush extents appear here (double-click to clear)"     else d
  })
  output$selecting <- renderPrint({
d <- event_data("plotly_selecting")
if (is.null(d)) "Brush points appear here (double-click to clear)" else qom[d$key,]
  })
  output$brushed <- renderPrint({
d <- event_data("plotly_brushed")
if (is.null(d)) "Brush extents appear here (double-click to clear)" else d
  })
  output$selected <- renderPrint({
d <- event_data("plotly_selected")
if (is.null(d)) "Brushed points appear here (double-click to clear)" else d
  })
}
shinyApp(ui, server, options = list(display.mode = "showcase")) here

您可以使用 customdata 参数传递唯一标识符,在这种情况下我从您的 data.frame 传递了 ID2 - 请查看点击事件:

qom <-structure(list(ID2 = c(183, 235, 248, 282, 290, 329, 676, 689, 725, 777,
17, 25, 39, 41, 47, 49, 52, 67, 79, 112, 1, 2, 3, 5, 7, 15, 16, 19, 20, 24),
xpos = c(34.5836111111111, 34.4836111111111, 35.0605555555556,
34.3677777777778, 34.6444444444444, 34.6472222222222, 34.7180555555556,
34.6727777777778, 34.6513888888889, 34.7725, 34.4994444444444,
34.6211111111111, 34.4463888888889, 34.5725, 34.6394444444444,
34.5369444444444, 34.6655555555556, 34.625, 34.5658333333333,
34.5122222222222, 34.6338888888889, 34.6391666666667, 34.56, 34.6458333333333,
34.6086111111111, 34.6372222222222, 34.5597222222222, 34.6452777777778,
34.6327777777778, 34.6152777777778 ), ypos = c(50.7491666666667,
50.4527777777778, 50.8752777777778, 50.5058333333333, 50.9227777777778,
50.8780555555556, 50.8672222222222, 50.8413888888889, 50.3944444444444, 50.5,
50.5108333333333, 50.8358333333333, 51.1144444444444, 50.4405555555556,
50.8763888888889, 50.4394444444444, 50.9141666666667, 50.9077777777778,
50.3733333333333, 50.5461111111111, 50.8686111111111, 50.8766666666667,
50.7961111111111, 50.8597222222222, 50.8422222222222, 50.8777777777778,
50.7961111111111, 50.8588888888889, 50.8694444444444, 50.8583333333333),
DARON_BRON = c("B", "B", "B", "B", "B", "D", "B", "B", "B", "B", "B", "B",
"B", "B", "D", "B", "B", "D", "B", "B", "D", "D", "D", "D", "D", "D", "N_A",
"D", "D", "D"), NOE_TASADOF = c("F", "F", "F", "F", "F", "F", "F", "F", "F",
"F", "KH", "KH", "KH", "KH", "KH", "KH", "KH", "KH", "KH", "KH", "J", "J",
"J", "J", "J", "J", "J", "J", "J", "J")), row.names = c(NA, -30L), class =
"data.frame")

library(shiny)
library(plotly)
library(DT)
library(dplyr)
ui <- fluidPage(
  plotlyOutput("plot"),
  verbatimTextOutput("hover"),
  verbatimTextOutput("click"),
  verbatimTextOutput("brushing"),
  verbatimTextOutput("selecting"),
  verbatimTextOutput("brushed"),
  verbatimTextOutput("selected")
)

server <- function(input, output) {
  
  output$plot <- renderPlotly({
    p <- plot_ly(
      data = qom,
      lat = ~ xpos,
      lon = ~ ypos,
      color = ~ NOE_TASADOF ,
      mode   = 'markers',
      colors = c("blue", "green", "red"),
      marker = list(size = 10),
      type = 'scattermapbox',
      customdata = ~ ID2
    ) %>%
      layout(mapbox = list(
        style = 'open-street-map',
        zoom = 5
        ,
        center = list(lon = 50.88, lat = 34.66)
      )) %>%
      highlight("plotly_selected", dynamic = F, color = NULL)

    p <- p %>%
      layout(dragmode = "select") %>%
      event_register("plotly_selecting")
    p
  })
  
  output$hover <- renderPrint({
    d <- event_data("plotly_hover")
    if (is.null(d))
      "Hover events appear here (unhover to clear)"
    else
      d
  })
  
  output$click <- renderPrint({
    d <- event_data("plotly_click")
    if (is.null(d)){
      "Click events appear here (double-click to clear)"
    } else {
      qom[qom$ID2 == d$customdata, ]
    }
  })
  
  output$brushing <- renderPrint({
    d <- event_data("plotly_brushing")
    if (is.null(d))
      "Brush extents appear here (double-click to clear)"
    else
      d
  })
  
  output$selecting <- renderPrint({
    d <- event_data("plotly_selecting")
    if (is.null(d))
      "Brush points appear here (double-click to clear)"
    else
      d
  })
  
  output$brushed <- renderPrint({
    d <- event_data("plotly_brushed")
    if (is.null(d))
      "Brush extents appear here (double-click to clear)"
    else
      d
  })
  
  output$selected <- renderPrint({
    d <- event_data("plotly_selected")
    if (is.null(d))
      "Brushed points appear here (double-click to clear)"
    else
      d
  })
  
}

shinyApp(ui, server, options = list(display.mode = "showcase"))