Creating legend with circles leaflet R

后端 未结 1 541
广开言路
广开言路 2020-12-14 10:23

I\'m trying to create a leaflet map with points sized by a variable. Is it possible to create a legend with different sized circles representing the different variable value

相关标签:
1条回答
  • 2020-12-14 11:11

    You're in luck. A closer look at the leaflet.js shows that the configurations your add inside the addLegend command, are used literally to create the legend items:

    Lines 1083 - 1086 from leaflet.js:

    for (var i = 0; i < colors.length; i++) {
      legendHTML += '<i style="background:' + colors[i] + ';opacity:' +
                    options.opacity + '"></i> ' + labels[i] + '<br/>';
    }
    

    This way, we can sneak in some extra styling. Within the colors arguement, we add some width and height to change the size of the i tag (= the legend circle). And (this is optional) we can make the labels a div with modified alignment style, because they tend to be stuck way to the top of the line, if the circle gets big.

    I took the liberty to create a custom legend function for you. This takes an additional value for the circle sizes. (It's a very minimal function for just this one application.) It then adds the styling I mentioned above without you needing to worry about typos or other errors. Note that the standard size is 10.

    Code below. Have fun! And please write if there are any mistakes or bugs. I could not test for every possible scenario.

    library(shiny)
    library(leaflet)
    
    #create data
    Points<-data.frame(x=runif(10,20,21), y=runif(10,0,1), var=rep(c(5,10),5))
    map = leaflet() %>% addTiles()
    
    # Set up shiny app
    shinyApp(
      ui = bootstrapPage(
        tags$style(type = "text/css", "html, body {width:100%;height:100%}",
          ".leaflet .legend i{
          border-radius: 50%;
          width: 10px;
          height: 10px;
          margin-top: 4px;
          }
        "),
        leafletOutput("myMap", width = "100%", height = "100%")
      ),
    
      server = function(input, output){
        addLegendCustom <- function(map, colors, labels, sizes, opacity = 0.5){
          colorAdditions <- paste0(colors, "; width:", sizes, "px; height:", sizes, "px")
          labelAdditions <- paste0("<div style='display: inline-block;height: ", sizes, "px;margin-top: 4px;line-height: ", sizes, "px;'>", labels, "</div>")
        
          return(addLegend(map, colors = colorAdditions, labels = labelAdditions, opacity = opacity))
        }
        
        output$myMap = renderLeaflet({map %>% 
          addCircleMarkers(Points$x,Points$y,radius=Points$var) %>%
          addLegendCustom(colors = c("blue", "blue", "red"), labels = c("A", "B", "C"), sizes = c(10, 20, 40))
        })
      }
    )
    
    0 讨论(0)
提交回复
热议问题