天天看点

Google地图官方API-在地图上绘图(自定义叠加层)

自定义叠加层

介绍

叠加层是地图上与纬度/经度坐标绑定的对象,因此在您拖动或缩放地图时它们会移动。有关预定义叠加层类型的信息,请参见 在地图上绘制。

Maps JavaScript API提供了一个 用于创建您自己的自定义叠加层的类。该 是一个基类,提供您在创建叠加层时必须实现几种方法。该类还提供了一些方法,可以在屏幕坐标和地图上的位置之间进行转换。 OverlayViewOverlayView

添加自定义叠加层

以下是创建自定义叠加层所需步骤的摘要:

将您的自定义叠加层对象设置prototype为的新实例google.maps.OverlayView()。实际上,这将覆盖覆盖类。

为您的自定义叠加层创建一个构造函数,并设置所有初始化参数。

onAdd()在原型中实现一个方法,然后将叠加层附加到地图上。OverlayView.onAdd() 当地图准备好附加叠加层时,将调用。

draw()在原型中实现一种方法,并处理对象的视觉显示。OverlayView.draw() 首次显示对象时将调用。

您还应该实现一种onRemove()方法来清除在叠加层中添加的所有元素。

以下是每个步骤的更多详细信息。您还可以看到完整的工作示例: view example。

子类覆盖

下面的示例OverlayView用于创建简单的图像叠加层。

// This example creates a custom overlay called USGSOverlay, containing

// a U.S. Geological Survey (USGS) image of the relevant area on the map.

// Set the custom overlay object's prototype to a new instance

// of OverlayView. In effect, this will subclass the overlay class therefore

// it's simpler to load the API synchronously, using

// google.maps.event.addDomListener().

// Note that we set the prototype to an instance, rather than the

// parent class itself, because we do not wish to modify the parent class.

var overlay;

USGSOverlay.prototype = new google.maps.OverlayView();

// Initialize the map and the custom overlay.

function initMap() {

var map = new google.maps.Map(document.getElementById('map'), {

zoom: 11,
center: {lat: 62.323907, lng: -150.109291},
mapTypeId: 'satellite'           

});

var bounds = new google.maps.LatLngBounds(

new google.maps.LatLng(62.281819, -150.287132),
  new google.maps.LatLng(62.400471, -150.005608));
           

// The photograph is courtesy of the U.S. Geological Survey.

var srcImage = '

https://developers.google.com/maps/documentation/

' +

'javascript/examples/full/images/talkeetna.png';
           

// The custom USGSOverlay object contains the USGS image,

// the bounds of the image, and a reference to the map.

overlay = new USGSOverlay(bounds, srcImage, map);

}

现在,我们为USGSOverlay该类创建一个构造函数,并将传递的参数初始化为新对象的属性。

/* @constructor /

function USGSOverlay(bounds, image, map) {

// Initialize all properties.

this.bounds_ = bounds;

this.image_ = image;

this.map_ = map;

// Define a property to hold the image's div. We'll

// actually create this div upon receipt of the onAdd()

// method so we'll leave it null for now.

this.div_ = null;

// Explicitly call setMap on this overlay.

this.setMap(map);

我们尚无法将此叠加层附加到叠加层的构造函数中的地图上。首先,我们需要确保地图的所有窗格均可用,因为它们指定了对象在地图上的显示顺序。API提供了一个指示此情况已发生的辅助方法。我们将在下一部分中处理该方法。

初始化叠加

首次实例化叠加层并准备显示它时,我们需要通过浏览器的DOM将其附加到地图上。API通过调用叠加层的onAdd() 方法来指示该叠加层已添加到地图。要处理此方法,我们创建一个

来保存图像,添加一个元素,将其附加到 ,然后将叠加层附加到地图的窗格之一。窗格是DOM树中的一个节点。

类型为的窗格 指定地图上不同图层的堆叠顺序。以下窗格可用,并按从下到上的堆叠顺序进行枚举: MapPanes

mapPane是最低的窗格,位于图块上方。它可能不会收到DOM事件。(窗格0)。

overlayLayer包含折线,多边形,地面叠加层和图块图层叠加层。它可能不会收到DOM事件。(窗格1)。

markerLayer包含标记。它可能不会收到DOM事件。(窗格2)。

overlayMouseTarget包含接收DOM事件的元素。(窗格3)。

floatPane包含信息窗口。它位于所有地图叠加层上方。(窗格4)。

因为我们的图像是“地面叠加层”,所以我们将使用overlayLayer 窗格。有了该窗格后,我们将把它的对象作为子对象附加到它。

/**

  • onAdd is called when the map's panes are ready and the overlay has been
  • added to the map.

    */

USGSOverlay.prototype.onAdd = function() {

var div = document.createElement('div');

div.style.borderStyle = 'none';

div.style.borderWidth = '0px';

div.style.position = 'absolute';

// Create the img element and attach it to the div.

var img = document.createElement('img');

img.src = this.image_;

img.style.width = '100%';

img.style.height = '100%';

img.style.position = 'absolute';

div.appendChild(img);

this.div_ = div;

// Add the element to the "overlayLayer" pane.

var panes = this.getPanes();

panes.overlayLayer.appendChild(div);

};

绘制覆盖

请注意,我们在上面的代码中没有调用任何特殊的可视显示。draw()每当需要在地图上绘制叠加层(包括首次添加叠加层)时,API 都会在叠加层上调用单独的方法。

因此draw(),我们将实现此方法,MapCanvasProjection 使用来检索叠加层,getProjection()并计算锚定对象的右上和左下点的确切坐标。然后,我们可以调整的大小

。反过来,这将调整图像的大小以匹配我们在叠加层的构造函数中指定的边界。

USGSOverlay.prototype.draw = function() {

// We use the south-west and north-east

// coordinates of the overlay to peg it to the correct position and size.

// To do this, we need to retrieve the projection from the overlay.

var overlayProjection = this.getProjection();

// Retrieve the south-west and north-east coordinates of this overlay

// in LatLngs and convert them to pixel coordinates.

// We'll use these coordinates to resize the div.

var sw = overlayProjection.fromLatLngToDivPixel(this.bounds_.getSouthWest());

var ne = overlayProjection.fromLatLngToDivPixel(this.bounds_.getNorthEast());

// Resize the image's div to fit the indicated dimensions.

var div = this.div_;

div.style.left = sw.x + 'px';

div.style.top = ne.y + 'px';

div.style.width = (ne.x - sw.x) + 'px';

div.style.height = (sw.y - ne.y) + 'px';

删除自定义覆盖

我们还添加了一种onRemove()方法,可以从地图上干净地删除叠加层。

// The onRemove() method will be called automatically from the API if

// we ever set the overlay's map property to 'null'.

USGSOverlay.prototype.onRemove = function() {

this.div_.parentNode.removeChild(this.div_);

隐藏和显示自定义叠加层

如果您希望隐藏或显示叠加层,而不是简单地创建或删除它,则可以实现自己的hide()和 show()方法来调整叠加层的可见性。另外,您可以将叠加层与地图的DOM分离,尽管此操作的成本稍高。请注意,如果您随后将叠加层重新附加到地图的DOM,它将重新调用叠加层的onAdd()方法。

以下示例 为叠加层的原型添加hide()和show()方法,以切换容器的可见性

。此外,我们添加了一种 toggleDOM()方法,用于将叠加层附加到地图或从地图上分离。

// Set the visibility to 'hidden' or 'visible'.

USGSOverlay.prototype.hide = function() {

if (this.div_) {

// The visibility property must be a string enclosed in quotes.
this.div_.style.visibility = 'hidden';           

USGSOverlay.prototype.show = function() {

this.div_.style.visibility = 'visible';           

USGSOverlay.prototype.toggle = function() {

if (this.div_.style.visibility === 'hidden') {
  this.show();
} else {
  this.hide();
}           

// Detach the map from the DOM via toggleDOM().

// Note that if we later reattach the map, it will be visible again,

// because the containing

is recreated in the overlay's onAdd() method.

USGSOverlay.prototype.toggleDOM = function() {

if (this.getMap()) {

// Note: setMap(null) calls OverlayView.onRemove()
this.setMap(null);           

} else {

this.setMap(this.map_);           

注意用户界面:

<div id="floating-panel">
  <input type="button" value="Toggle visibility" onclick="overlay.toggle();"></input>
  <input type="button" value="Toggle DOM attachment" onclick="overlay.toggleDOM();"></input>
</div>
           

查看示例。

继续阅读