很多應用中都需要用到地圖聯動、多屏對比、二三維分屏、大屏顯示,有圖形可視化的地方就有事件響應觸發:鼠標按下、移動、鼠標滾輪,由此觸發了地圖上座標或範圍的變化,將這些變化發送給另一個地圖並響應這些變化,即完成地圖聯動。
下面以二維地圖分屏和二三維地圖分屏分別說明實現思路(以ArcGIS開發為例,其他思路可參考)。
1、二維地圖分屏對比(地圖空間參考一般會一致)
1)頁面佈局,將網頁佈局設計成1~N個DIV;
2)事件監聽,對鼠標在地圖上的事件進行監聽,一個地圖事件觸發後,其他地圖響應。
※※※ MouseDown、MouseOver、MouseWheel,3個主要事件響應,對應地圖上pan-end、mouse-move、zoom-end,地圖聯動變化核心:【map.setExtent(evt.extent)】,參考代碼如下:
<code> //放大聯動
this._activeMapEventHandlers.push(this.activeMap.on("zoom-end", function (evt) {
self._maps.forEach(function (map) {
if (map != self.activeMap) {
map.setExtent(evt.extent);
}
});
}));
//平移聯動
this._activeMapEventHandlers.push(this.activeMap.on("pan-end", function (evt) {
self._maps.forEach(function (map) {
if (map != self.activeMap) {
map.setExtent(evt.extent);
}
});
}));
//鼠標聯動
this._activeMapEventHandlers.push(this.activeMap.on("mouse-move", function (evt) {
self._maps.forEach(function (map) {
var idx = self._maps.indexOf(map);
var graphicLayer = map.getLayer("layer")
var graphic = self._mouseGraphics[idx];
if (map != self.activeMap) {
graphicLayer.show();
graphic.setGeometry(evt.mapPoint);
} else {
graphicLayer.hide();
}
});
}));/<code>
2、二三維分屏聯動對比
與二維相比,三維在地圖空間參考上具有差異性,三維地圖一般是WGS84、WGS84魔卡託,還有諸如國內火星座標系(CGCS2000)等,會導致投影座標存在投影轉換,二維平面座標就是XY(另加Scale),三維立體座標擁有XYZ(另加Scale),以及XYZ上的旋傾角,遵循右手笛卡爾座標系,見下圖:
pitch是圍繞X軸旋轉,也叫做俯仰角;yaw是圍繞Y軸旋轉,也叫偏航角;roll是圍繞Z軸旋轉,也叫翻滾角。
由此可見,二三維聯動的核心:二維的中心(X,Y)+Scale(縮放係數),三維的“七參數”:(X,Y,Z,Pitch,Yaw,Roll,Scale(縮放係數)),轉換投影變動就能實現。
ArcGIS JS二三維聯動同步具體設計實現與二維類似,給出核心同步代碼參考:
<code>var synchronizeView = function(view, others) {
others = Array.isArray(others) ? others : [others];
var viewpointWatchHandle;
var viewStationaryHandle;
var otherInteractHandlers;
var scheduleId;
var clear = function() {
if (otherInteractHandlers) {
otherInteractHandlers.forEach(function(handle) {
handle.remove();
});
}
viewpointWatchHandle && viewpointWatchHandle.remove();
viewStationaryHandle && viewStationaryHandle.remove();
scheduleId && clearTimeout(scheduleId);
otherInteractHandlers = viewpointWatchHandle =
viewStationaryHandle = scheduleId = null;
};
//鼠標事件監聽、動畫交互
var interactWatcher = view.watch('interacting,animation',
function(newValue) {
if (!newValue) {
return;
}
if (viewpointWatchHandle || scheduleId) {
return;
}
//同步聯動視圖(每個地圖的View),viewpoint:Camera,rotation,scale
scheduleId = setTimeout(function() {
scheduleId = null;
viewpointWatchHandle = view.watch('viewpoint',
function(newValue) {
others.forEach(function(otherView) {
otherView.viewpoint = newValue;
});
});
}, 0);
//視圖交互響應
otherInteractHandlers = others.map(function(otherView) {
return watchUtils.watch(otherView,
'interacting,animation',
function(
value) {
if (value) {
clear();
}
});
});
viewStationaryHandle = watchUtils.whenTrue(view,
'stationary', clear);
});
return {
remove: function() {
this.remove = function() {};
clear();
interactWatcher.remove();
}
}
};/<code>
以上介紹了地圖開發中常用到的分屏對比實現思路,僅供參考。
閱讀更多 GIS行雲流水 的文章