Search code examples
rshinyr-leaflet

shape_click$id is NULL


Based on this example here, I wanted to dynamically link the map with a Highchart by simply clicking on the area of interest. However the shape_click funtion returns a $id NULL. I tried it with different shapefile and it doesn't work. You'll se below the code from the example adjusted (data available here to get the $id from the shape_click function.

library(shiny)
library(dplyr)
library(leaflet)
library(sf)
library(rmapshaper)

ui <- fluidPage(
  
  titlePanel("heatmap"),
  
  # Sidebar with a slider input for year of interest
  sidebarLayout(
    sidebarPanel(
      sliderInput("year",h3("Select year or push play button"),
                  min = 2000, max = 2002, step = 1, value = 2000,
                  animate = TRUE)
    ),
    
    # Output of the map
    mainPanel(
      leafletOutput("unemployment"),
      verbatimTextOutput('summary')
    )
  )
)

server <- function(input, output) {
  #to get the spacial data: from file in link above
  data.p <- sf::st_read("input/gpr_000a11a_e.shp") %>% 
    st_transform(4326) %>%
    rmapshaper::ms_simplify()
  data.p$PRUID <- as.character(data.p$PRUID) %>% as.numeric
  data.p <- data.p[which(data.p$PRUID < 60),]
  
  lng.center <- -99
  lat.center <- 60
  zoom.def <- 3
  
  #dataframe with same structure as statscan csv after processing
  unem <- runif(10,min=0,max=100)
  unem1 <- unem+runif(1,-10,10)
  unem2 <- unem1+runif(1,-10,10)
  unemployment <- c(unem,unem1,unem2)
  #dataframe with same structure as statscan csv after processing
  X <- data.frame("id" = c(10,11,12,13,24,35,46,47,48,59,
                           10,11,12,13,24,35,46,47,48,59,
                           10,11,12,13,24,35,46,47,48,59),
                  "Unemployment" = unemployment,
                  "year" = c(rep(2000,10),rep(2001,10),rep(2002,10))
  )
  
  data <- left_join(data.p, X, by = c("PRUID"= "id"))
  
  output$unemployment <- renderLeaflet({
    leaflet(data = data.p) %>%
      addProviderTiles("OpenStreetMap.Mapnik", options = providerTileOptions(opacity = 1), group = "Open Street Map") %>%
      setView(lng = lng.center, lat = lat.center, zoom = zoom.def) %>%
      addPolygons(group = 'base', 
                  fillColor = 'transparent', 
                  color = 'black',
                  weight = 1.5)  %>%
      addLegend(pal = pal(), values = X$Unemployment, opacity = 0.7, title = NULL,
                position = "topright")
  })
  
  get_data <- reactive({
    data[which(data$year == input$year),]
  })
  
  pal <- reactive({
    colorNumeric("viridis", domain = X$Unemployment)
  })
  
  observe({
    data <- get_data()
    leafletProxy('unemployment', data = data) %>%
      clearGroup('polygons') %>%
      addPolygons(group = 'polygons', 
                  fillColor = ~pal()(Unemployment), 
                  fillOpacity = 0.9,
                  color = 'black',
                  weight = 1.5)
  })
  output$summary <- renderPrint({
    event <- input$unemployment_shape_click
    print(event)
  })
  
}

# Run the application 
shinyApp(ui = ui, server = server)

Solution

  • You have to add a layerId in your addPolygons call.

    Just change the last observe to (If PRUID represents the ID-column):

    observe({
        data <- get_data()
        leafletProxy('unemployment', data = data) %>%
          clearGroup('polygons') %>%
          addPolygons(group = 'polygons', 
                      fillColor = ~pal()(Unemployment), 
                      fillOpacity = 0.9, layerId = data$PRUID,
                      color = 'black',
                      weight = 1.5)
      })