从 Bokeh Google Maps 包装器 (fitBounds()) 调用 Javascript 方法

Posted

技术标签:

【中文标题】从 Bokeh Google Maps 包装器 (fitBounds()) 调用 Javascript 方法【英文标题】:Calling a Javascript method from the Bokeh Google Maps wrapper (fitBounds()) 【发布时间】:2019-11-03 09:05:02 【问题描述】:

我有一个带有多个 Lat/Lng 数据点的散景谷歌地图图,我想使用 Google Maps v3 API 的 fitBounds() 方法来设置缩放级别。

我有一个谷歌地图图正在运行,显示在我的网站上并显示数据点,但我需要手动设置缩放。

import bokeh.io
import bokeh.models
import bokeh.plotting
import pandas as pd

data = 
    'Latitude [deg]': [18.46, 25.7, 32.3],
    'Longitude [deg]': [-66, -80.2, -64.8],

data_frame = pd.DataFrame.from_dict(data)
data_source = bokeh.models.ColumnDataSource(data_frame)
mean_lat = data_frame['Latitude [deg]'].mean()
mean_lng = data_frame['Longitude [deg]'].mean()
gmap_options = bokeh.models.GMapOptions(lat=mean_lat, lng=mean_lng, zoom=10, map_type='satellite')
xy_gmap = bokeh.plotting.gmap('SuPeRSeCrEtAPIkey', gmap_options)
xy_gmap.circle(x='Longitude [deg]', y='Latitude [deg]', source=data_source, color="red")

# A callback like this? Could make the call in javascript after the page is loaded, and update map zoom??
# xy_gmap.fitBounds(x='Longitude [deg]', y='Latitude [deg]', source=data_source)

bokeh.io.show(xy_gmap)

我希望地图的边界以尽可能低的缩放比例包围我的数据框中的所有点(正如 fitBounds() 在 Javascript 中所做的那样)。目前地图只能缩放到手动设置的级别。

【问题讨论】:

【参考方案1】:

开始回答 bigreddot 描述的两种方法(使用 JS Bokeh.index 和 Python 集成)

散景索引

在 Javascript 控制台中,您可以使用以下命令(在某些 JS 代码中应该可以自我解释)

> var gmapPlotView;
> for (var property in Bokeh.index)  if (Bokeh.index[property].constructor.name == 'GMapPlotView') gmapPlotView = Bokeh.index[property];     // Get the correct object, in the case that you have multiple plots, but only one map plot
> var bounds = gmapPlotView.map.getBounds();                  // To start from existing bounds
> var bounds = google.maps.LatLngBounds();                    // To start with fresh bounds
> var place = new google.maps.LatLng(45.5983128 ,8.9172776);  // Coordinates of place to put bounds, repeat for all points
> bounds.extend(place);                                       // Add each place to the bounds object
> gmapPlotView.map.fitBounds(bounds);                         // Set the maps new bounds

请注意,Bokeh google maps 实现不会在 Google Maps 数据层上绘制您的数据,而是在地图上方的 bokeh 画布上绘制(这就是在地图图块和图表之间平移地图时存在延迟的原因)。

Python 集成

处理中……

【讨论】:

【参考方案2】:

从 Bokeh 1.2 开始,没有内置的方法可以实现这一点。我能提供的唯一建议是请注意,在 JavaScript 端有一个全局 Bokeh.index,并且您所做的相应 GmapPlot 有一个 GMapPlotView。此视图有一个属性.map,它是实际的 Google 地图对象。您可以从 JavaScript 代码调用 fitBounds 方法。 Bokeh GMapPlot 对象遵循 Google 的引导来绘制边界,因此如果它们得到更新,轴等应该响应。

否则,我只能建议opening a GitHub issue 讨论将其添加为新功能。

【讨论】:

感谢您为我指明正确的方向。我会研究这个方法,如果我能做点什么,我会提出问题并拉取请求。 请注意,如果您确实启动了 PR:在项目本身中真正做到这一点的方法是将新属性添加到 GMapPlot,然后在 BokehJS 中应用 fitBounds(或不) 基于该属性(即,Bokeh.index 不需要太多)

以上是关于从 Bokeh Google Maps 包装器 (fitBounds()) 调用 Javascript 方法的主要内容,如果未能解决你的问题,请参考以下文章

本地搜索运算符 Python 包装器 Google or-tools

我应该使用 Google Maps API/Geocoding 为商店查找器提供动力吗

快速链接器命令失败,退出代码为 1 Google Maps iOS Util pod install

获取 Google Maps v3 以调整 InfoWindow 的高度

我可以从一个外部库导入和编辑代码吗? (例如 google-maps-utils)

如何提示从嵌入式地图打开 Google Maps Directions 到 Google Maps Navigator 的页面?