英文:
Only render leaflet map when zoom passes a threshold in Shiny
问题
在Shiny应用程序中,我已经构建了一个Leaflet地图,根据缩放级别的不同显示不同的图层。
我使用了leafletProxy
与observeEvent
以及Leaflet的input$MAPID_zoom
来构建这个地图。
server <- shinyServer(function(input, output, session) {
output$map <- renderLeaflet({
leaflet() %>%
addTiles() %>%
mapOptions(zoomToLimits="first") %>%
setView(lat = 47.218637, lng = -1.554136, zoom = 7)
})
observeEvent(
eventExpr = input$map_zoom, {
map_proxy <- leafletProxy(mapId = "map", session = session)
if(input$map_zoom < 8){
map_proxy %>%
clearMarkers() %>%
addMarkers(
data = df, lng = ~lng, lat = ~lat
)
} else {
map_proxy %>%
clearMarkers() %>%
addMarkers(
data = df_2, lng = ~lng, lat = ~lat
)
}
}
)
})
然而,这会在缩放级别变化时重新渲染Leaflet地图。我希望地图只在if语句中的阈值被超过时才重新渲染。有什么方法可以解决这个问题?
UI和数据的代码如下:
library(shiny)
library(leaflet)
df <- data.frame(
location_name = c('S1', 'S2'),
lng = c(-1.554136, -2.10401),
lat = c(47.218637, 47.218637),
stringsAsFactors = FALSE
)
df_2 <- data.frame(
location_name = c('S3', 'S4'),
lng = c(-1.654136, -2.2401),
lat = c(47.218637, 47.218637),
stringsAsFactors = FALSE
)
ui <- shinyUI(
fluidPage(
leafletOutput(outputId = 'map')
)
)
英文:
I have built a leaflet map in a Shiny application that shows different layers depending on what zoom you have.
I have built this combining leafletProxy
with observeEvent
and leaflet's input$MAPID_zoom
.
server <- shinyServer(function(input, output, session) {
output$map <- renderLeaflet({
leaflet() |>
addTiles() |>
mapOptions(zoomToLimits="first") |>
setView(lat = 47.218637, lng = -1.554136, zoom = 7)
})
observeEvent(
eventExpr = input$map_zoom, {
map_proxy <- leafletProxy(mapId = "map", session = session)
if(input$map_zoom < 8){
map_proxy |>
clearMarkers() |>
addMarkers(
data = df, lng = ~lng, lat = ~lat
)
} else {
map_proxy |>
clearMarkers() |>
addMarkers(
data = df_2, lng = ~lng, lat = ~lat
)
}
}
)
})
However, this rerenders the leaflet map every time the zoom changes. I would like the map to only render when the threshold in the if-statement is surpassed. What would be a way to approach this?
Code for UI and data:
library(shiny)
library(leaflet)
df <- data.frame(
location_name = c('S1', 'S2'),
lng = c(-1.554136, -2.10401),
lat = c(47.218637, 47.218637),
stringsAsFactors = FALSE
)
df_2 <- data.frame(
location_name = c('S3', 'S4'),
lng = c(-1.654136, -2.2401),
lat = c(47.218637, 47.218637),
stringsAsFactors = FALSE
)
ui <- shinyUI(
fluidPage(
leafletOutput(outputId = 'map')
)
)
答案1
得分: 1
我无法重现你的问题,但这里有一个解决方案。
你需要创建两个图层并调整可见性。
server <- shinyServer(function(input, output, session) {
output$map <- renderLeaflet({
leaflet() %>%
addTiles() %>%
mapOptions(zoomToLimits="first") %>%
setView(lat = 47.218637, lng = -1.554136, zoom = 7) %>%
addMarkers(
data = df, lng = ~lng, lat = ~lat, group = "S1S2"
) %>%
addMarkers(
data = df_2, lng = ~lng, lat = ~lat, group="S3S4")
})
observeEvent(
eventExpr = input$map_zoom, {
map_proxy <- leafletProxy(mapId = "map", session = session)
if(input$map_zoom < 8){
map_proxy %>%
showGroup("S1S2") %>%
hideGroup("S3S4")
} else {
map_proxy %>%
showGroup("S3S4") %>%
hideGroup("S1S2")
}
}
)
})
在这里,每个图层都有不同的组ID,根据缩放级别,我们隐藏或显示相应的组。
英文:
I can't reproduce your problem but here is a solution.
You have to create both layers and play with visibility.
server <- shinyServer(function(input, output, session) {
output$map <- renderLeaflet({
leaflet() |>
addTiles() |>
mapOptions(zoomToLimits="first") |>
setView(lat = 47.218637, lng = -1.554136, zoom = 7) |>
addMarkers(
data = df, lng = ~lng, lat = ~lat, group = "S1S2"
) |>
addMarkers(
data = df_2, lng = ~lng, lat = ~lat, group="S3S4")
})
observeEvent(
eventExpr = input$map_zoom, {
map_proxy <- leafletProxy(mapId = "map", session = session)
if(input$map_zoom < 8){
map_proxy |>
showGroup("S1S2") |>
hideGroup("S3S4")
} else {
map_proxy |>
showGroup("S3S4") |>
hideGroup("S1S2")
}
}
)
})
Here each layer gets a different group id and depending of the zoom level we hide or show corresponding group.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论