7

我认为在闪亮的应用程序中使用 plotGoogleMaps 来使用 R 动态分析和显示空间数据真的很酷。我以前从未使用过任何一个包(它们相对较新)并且没有太多编程经验,所以我开始使用每个教程和示例,然后尝试将它们混合在一起。

我可以让代码的所有单个元素工作,但运行应用程序不会显示谷歌地图。我猜这与 plotGoogleMaps 试图在浏览器中绘图和闪亮的试图在浏览器中渲染绘图有关,但我不知道如何解决这个问题。我从闪亮的教程 Inputs & Outputs 中提取了大部分闪亮的代码,并按照plotGoogleMaps 教程

测试代码:

#load packages and data
library(shiny)
library(plotGoogleMaps)
data(meuse)

#convert data frame to SpatialPointDataFrame and set 
coordinates(meuse)<-~x+y
proj4string(meuse) <- CRS('+init=epsg:28992')

#will need to select column name for app, maybe not best way to do this, 
#but seems to work
formulaText<-paste('zinc')

#plot data on Google map, opens browser and works
mpgPlot <- plotGoogleMaps(meuse, zcol=formulaText)

用户界面

library(shiny)

# Define UI for meuse test
shinyUI(pageWithSidebar(

    # Application title
    headerPanel("Meuse Test"),

    # Sidebar with controls to select the variable to plot on map
    sidebarPanel(
        selectInput("variable", "Variable:",
                                choices=list("Zinc" = "zinc", 
                                         "Lead" = "lead", 
                                         "Copper" = "copper"), 
                                selected="Zinc")

    ),

    # Show the caption and plot of the requested variable on map
    mainPanel(
        plotOutput("mapPlot")
    )
))

服务器.R

library(shiny)
library(plotGoogleMaps)

data(meuse)
coordinates(meuse)<-~x+y
proj4string(meuse) <- CRS('+init=epsg:28992')

# Define server logic required to plot various variables on map
shinyServer(function(input, output) {

    # Compute the forumla text in a reactive expression since it is 
    # shared by the output$mapPlot ?I think I still need to do this...
    formulaText <- reactive({
#paste the input name in so it follows argument format for plotGoogleMaps?
#tried without, don't think it is probelm, works with test code...
        paste(input$variable)
    })


    # Generate a plot of the requested variable against mpg and only 
    # include outliers if requested
    output$mapPlot <- renderPlot({
        plotGoogleMaps(meuse, zcol=formulaText)
#also tried to specify alternative arguments like add=TRUE, 
#filename='mapPlot.htm', openMap=FALSE
    })
})

我知道 shiny 和 plotGoogleMaps 都是相当新的,我已经看到了一些向闪亮的 Google 小组发布问题的建议,但我不想重复发布,而 StackOverflow 是我的答案。最后,我还想为一个迄今为止对我帮助很大的社区做出一点贡献!如果这只是一种糟糕的方法,我愿意接受替代方案,我现在正在检查 googleVis ......

谢谢,亚历克斯

PS-

sessionInfo()
R version 3.0.1 (2013-05-16)
Platform: x86_64-w64-mingw32/x64 (64-bit)

locale:
[1] LC_COLLATE=English_United States.1252 
[2] LC_CTYPE=English_United States.1252   
[3] LC_MONETARY=English_United States.1252
[4] LC_NUMERIC=C                          
[5] LC_TIME=English_United States.1252    

attached base packages:
[1] grid      stats     graphics  grDevices utils     datasets  methods  
[8] base     

other attached packages:
[1] googleVis_0.4.3    plotGoogleMaps_2.0 maptools_0.8-25   
[4] lattice_0.20-15    foreign_0.8-54     rgdal_0.8-10      
[7] sp_1.0-11          shiny_0.6.0       

loaded via a namespace (and not attached):
[1] bitops_1.0-5   caTools_1.14   digest_0.6.3   httpuv_1.0.6.3
[5] Rcpp_0.10.4    RJSONIO_1.0-3  tools_3.0.1    xtable_1.7-1 

PPS-我在发布之前多次阅读了这篇文章,但现在我怀疑我的答案在那里。如果问题重复,请致歉。我认为这是……稀疏的东西htmlOutput()……?htmlOutput我感觉很稠密……

4

3 回答 3

4

感谢ramnathv 的代码,我设法plotGoogleMaps在没有任何 .html 编程知识的情况下嵌入到闪亮中:

library(plotGoogleMaps)
library(shiny)

runApp(list(
  ui = pageWithSidebar(
   headerPanel('Map'),
   sidebarPanel(""),
   mainPanel(uiOutput('mymap'))
   ),
   server = function(input, output){
    output$mymap <- renderUI({
      data(meuse)
      coordinates(meuse) = ~x+y
      proj4string(meuse) <- CRS("+init=epsg:28992")
      m <- plotGoogleMaps(meuse, filename = 'myMap1.html', openMap = F)
      tags$iframe(
        srcdoc = paste(readLines('myMap1.html'), collapse = '\n'),
        width = "100%",
        height = "600px"
      )
    })
   }
))

请注意,不显示图例。我已经在其他地方发布了关于这个问题的问题

于 2014-06-07T16:55:48.910 回答
3

(免责声明:不是闪亮的专家)

renderPlot 适用于 R 图形设备。在这种情况下,plotGoogleMaps 正在生成一个独立的 HTML 文件,该文件不会输出到图形设备。

由于 plotGoogleVis 生成的 .html 文件被设计为独立的(即它们不是可以合法插入到 Shiny 应用程序文档中的文档片段),我认为您需要将它们嵌入到 aniframe中以使它们正确呈现(即plotGoogleVis输出到文件,然后使用 ui.R 加载文件tags$iframe)。

如果您的总体目标只是在地图上可视化数据,那么使用 Leaflet 可能会更好——已经有一个包为 Leaflet bindings 提供了 Shiny

于 2013-08-07T20:55:20.600 回答
1

我不太了解plotGoogleMaps,但正如乔纳森所说,它似乎是在生成一个 HTML,而不是一个可以用于 Shiny 的绘图。

稍加努力,您就可以自己将 Shiny 绑定到 Google 地图。您可能想要放弃ui.R并使用带有 Google 地图的自定义 HTML 前端(在此处阅读 Google 地图开发人员指南)。您的页面将像这样开始(直接来自 Google 的“hello world”示例):

<!DOCTYPE html>
<html>
  <head>
    <meta name="viewport" content="initial-scale=1.0, user-scalable=no" />
    <style type="text/css">
      html { height: 100% }
      body { height: 100%; margin: 0; padding: 0 }
      #map-canvas { height: 100% }
    </style>
    <script type="text/javascript"
      src="https://maps.googleapis.com/maps/api/js?key=API_KEY&sensor=SET_TO_TRUE_OR_FALSE">
    </script>
    <script type="text/javascript">
      function initialize() {
        var mapOptions = {
          center: new google.maps.LatLng(-34.397, 150.644),
          zoom: 8,
          mapTypeId: google.maps.MapTypeId.ROADMAP
        };
        var map = new google.maps.Map(document.getElementById("map-canvas"),
            mapOptions);
      }
      google.maps.event.addDomListener(window, 'load', initialize);
    </script>
  </head>
  <body>
    <div id="map-canvas"/>
  </body>
</html>

不要忘记在上面添加您的 API 密钥。现在您需要编写绑定(参见教程)。这是一个让您入门的示例:

var map_binding = new Shiny.OutputBinding();

$.extend(map_binding, {

  find: function(scope) {
    return $(scope).find('#map-canvas');
  },

  renderValue: function(el, data) {

    // Parse the data sent from R.
    var map_data = jQuery.parseJSON(data);

    // ... 
    // Render points or whatever on map.
    ///

  }
});

Shiny.outputBindings.register(map_binding, "map_binding");

将它包含在一个单独的 JavaScript 文件中,并将其加载到 HTML 页面的头部。

您需要进行编辑renderValue(),以便从 R 中输入的任何数据都显示在地图上。renderValue()每次更新地图时都会调用。要了解如何在地图上实际显示点(或您要显示的任何内容),请再次查看 Google 的文档(例如此处),该文档通常提供您需要的大部分代码。

现在在 R 端,您将在server.R

output$map <- renderText({
  RJSONIO::toJSON(some_data)
})

您将在哪里将任何数据发送到要绘制的地图(通过renderValue()函数)。

于 2013-08-09T10:20:31.770 回答