自定義地圖示例:天地圖(二)
有了天地圖地圖圖片的URL生成規則,就可以開始實行對自定義地圖型別天地圖的支援。
引路蜂地圖包中類MapType,介面ICustomMapType主要用來支援自定義地圖。在類MapType中定義了 GENERIC_MAPTYPE_1 ,GENERIC_MAPTYPE_2 … GENERIC_MAPTYPE_7 用於支援自定義地圖,其中型別 GENERIC_MAPTYPE_7 由兩層組成(GENERIC_MAPTYPE_6和GENERIC_MAPTYPE_7),也就是說在繪製地圖型別GENERIC_MAPTYPE_7時,現繪製GENERIC_MAPTYPE_6,在其上再繪製GENERIC_MAPTYPE_7,兩層疊加而成。多於兩層的地圖圖片很少見。
跟據天地圖的特點,採用GENERIC_MAPTYPE_7作為其地圖型別,1-10由兩層地圖組成,一層影象,一層標註。11層以上也可以看作兩層,另一層為空層。
介面ICustomMapType只定義了一個方法:地圖圖片產生規則定義。
public String getTileURL(int mtype, int x, int y, int zoomLevel);
由於目前在寫Android示例,就使用Android為例,其它平臺類似,在專案GISEngineTutorial中新增CustomMap Activity。
package com.pstreets.gisengine.demo; import com.mapdigit.gis.raster.ICustomMapType; import com.mapdigit.gis.raster.MapType; import com.mapdigit.gis.geometry.GeoLatLng; import com.pstreets.gisengine.R; import com.pstreets.gisengine.SharedMapInstance; import android.app.Activity; import android.os.Bundle; import android.view.Menu; import android.view.MenuInflater; import android.view.MenuItem; public class CustomMap extends Activity { @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.main); } @Override public void onStart() { super.onStart(); MapType.setCustomMapTileUrl(new TiandiMapType()); GeoLatLng center = new GeoLatLng(32.0616667, 118.7777778); SharedMapInstance.map.setCenter(center, 13, MapType.GENERIC_MAPTYPE_7); } @Override public boolean onCreateOptionsMenu(Menu menu) { MenuInflater inflater = getMenuInflater(); inflater.inflate(R.menu.mapzoom_menu, menu); return true; } @Override public boolean onOptionsItemSelected(MenuItem item) { // Handle item selection switch (item.getItemId()) { case R.id.zoomin: SharedMapInstance.map.zoomIn(); return true; case R.id.zoomout: SharedMapInstance.map.zoomOut(); return true; default: return super.onOptionsItemSelected(item); } } } class TiandiMapType implements ICustomMapType { private static int serverIndex=1; public String getTileURL(int mtype, int x, int y, int zoomLevel) { String returnURL=""; serverIndex+=1; serverIndex%=6; int maxTiles=(int)Math.pow(2, zoomLevel); switch(mtype){ case MapType.GENERIC_MAPTYPE_6: if(zoomLevel<11){ returnURL= "http://tile" + serverIndex +".tianditu.com/DataServer?T=A0512_EMap"; returnURL+="&X="+x+"&Y="+y+"&L="+zoomLevel; }else if(zoomLevel<13){ returnURL= "http://tile" + serverIndex +".tianditu.com/DataServer?T=B0627_EMap1112"; returnURL+="&X="+x+"&Y="+y+"&L="+zoomLevel; }else{ returnURL= "http://tile" + serverIndex +".tianditu.com/DataServer?T=siwei0608"; returnURL+="&X="+x+"&Y="+y+"&L="+zoomLevel; } break; case MapType.GENERIC_MAPTYPE_7: if(zoomLevel<11){ returnURL= "http://tile" + serverIndex +".tianditu.com/DataServer?T=AB0512_Anno"; returnURL+="&X="+x+"&Y="+y+"&L="+zoomLevel; }else{ returnURL=MapType.EMPTY_TILE_URL; } break; } return returnURL; } }
看起來還是不錯,但仔細分析一下,天地圖的分片方法和Google地圖分片方法不盡相同,在同一縮放級別下,天地圖比Google地圖在高度方向要矮一半,具體來說,將兩種地圖都設成最小級(顯示全世界地圖),天地圖大小為512X256,而Google地圖為512X512。這造成的結果就是需要對天地圖經緯度座標進行調整。如何調整將在以後詳細說明。但這不影響自定義地圖示例方法,如果自定義地圖分片方法和Google地圖一樣,則不需要調整經緯度座標。要注意的是這裡的調整經緯度座標和座標偏移是不同的概念。這裡經緯度座標調整是因為天地圖和Google地圖座標投影方法不同,而座標偏移指的是人為新增的偏移。