闪亮的点击/刷子不适用于非笛卡尔坐标?

时间:2016-08-06 16:40:36

标签: r ggplot2 shiny coordinate-systems brush

我正在开发一款应该让用户在ggplot2生成的世界地图上选择地理数据点的Shiny应用程序(如this example所示)。

如果我使用常规的coord_cartesian坐标系(会扭曲地图),但是如果我使用更合适的 coord_map 坐标系,则会失败。看来,点击/画笔事件在投影后没有收到正确的坐标。有什么方法可以解决或解决这个问题而不回复到笛卡尔坐标?

您可以在下面找到一个工作示例:

library(shiny)
library(ggplot2)
library(dplyr)

map_world <- function(world, mapPoints, xlim, ylim){
  # function to generate ggplot world map
  ggplot() + 
    geom_polygon(data=world, aes(x=long, y=lat, group=group)) +
    geom_point(data=mapPoints, aes(x=Longitude, y=Latitude), color="red") +
    # coord_map messes up the brush select
     coord_map(xlim=xlim, ylim=ylim)
    # coord_cartesian would work but distort the map
    # coord_cartesian(xlim=xlim, ylim=ylim)
}

mapPoints <- data.frame(Longitude=c(-103, -108, -130, -120),
                      Latitude=c(52, 40, 45, 54))
world <- map_data("world")

ui <- fluidPage(
  fluidRow(
    column(width = 6, 
           plotOutput("plot1", height = 300, 
                      click = "plot1_click", brush = "plot1_brush") )
  ),
  fluidRow(
    column(width = 6, 
           h4("Near points"), verbatimTextOutput("click_info") ),
    column(width = 6, 
           h4("Brushed points"), verbatimTextOutput("brush_info") )
  )
)

server <- function(input, output) {
  # output world map
  output$plot1 <- renderPlot({
    map_world(world = world, mapPoints = mapPoints, 
              xlim=c(-180,180), ylim=c(-90,90))
  })
  # output clicked points 
  output$click_info <- renderPrint({
    nearPoints(mapPoints, xvar="Longitude", 
                  yvar="Latitude", input$plot1_click)
  })
  # output brushed points 
  output$brush_info <- renderPrint({
    brushedPoints(mapPoints, xvar="Longitude", 
                  yvar="Latitude", input$plot1_brush)
  })
}

shinyApp(ui, server)

谢谢!

1 个答案:

答案 0 :(得分:1)

我使用ggplot尝试了一些解决方案,但plotOutput函数未提取的缩放存在一些问题。在帮助页面(http://shiny.rstudio.com/reference/shiny/latest/plotOutput.html)中,请注意以下内容:

  

对于plotOutput,如果可能,坐标将被缩放到数据空间。 (此时,由基本图形和ggplot2生成的图表支持此缩放,尽管由格子和其他图形生成的图不会。)如果无法缩放,则将发送原始像素坐标。对于imageOutput,坐标将以原始像素坐标发送。

  

使用ggplot2图形时,renderPlot中的代码应该返回一个ggplot对象;如果相反代码使用类似print(p)的内容打印ggplot2对象,则交互式图形的坐标将无法正确缩放到数据空间。

我尝试将ggplot移动到脚本的服务器部分,但它不起作用。

我建议的解决方案,使用基本图形:

library(shiny)
library(dplyr)
library(maps)
library(mapdata)


mapPoints <- data.frame(Longitude=c(-103, -108, -130, -120),
                        Latitude=c(52, 40, 45, 54))

ui <- fluidPage(
  fluidRow(
    column(width = 6, 
           plotOutput("plot1", height = 300, 
                      click = "plot1_click", brush = "plot1_brush") )
  ),
  fluidRow(
    column(width = 6, 
           h4("Near points"), verbatimTextOutput("click_info") ),
    column(width = 6, 
           h4("Brushed points"), verbatimTextOutput("brush_info") )
  )
)

server <- function(input, output) {
  # output world map
  output$plot1 <- renderPlot({
    map('worldHires')
    points(mapPoints$Longitude, mapPoints$Latitude, 
           col = "red", pch = 16)
  })
  # output clicked points 
  output$click_info <- renderPrint({
    nearPoints(mapPoints, xvar="Longitude", 
               yvar="Latitude", input$plot1_click)
  })
  # output brushed points 
  output$brush_info <- renderPrint({
    brushedPoints(mapPoints, xvar="Longitude", 
                  yvar="Latitude", input$plot1_brush)
  })
}

shinyApp(ui, server)