摘要:Google Map等網(wǎng)站為企業(yè)構(gòu)建基于地理信息的應(yīng)用提供了方便且經(jīng)濟(jì)的二次開(kāi)發(fā)平臺(tái),但其實(shí)現(xiàn)技術(shù)是基于Web的。本文討論在基于ArcGIS Engine的桌面應(yīng)用中利用Google Static Map服務(wù)實(shí)現(xiàn)背景地圖顯示的方法,這個(gè)方法也可以適用于與google map類(lèi)似的其它公共平臺(tái)。
關(guān)鍵詞:Google Static Map;ArcGIS Engine;墨卡托投影;瓦片
中圖分類(lèi)號(hào):TP311.1 文獻(xiàn)標(biāo)識(shí)碼:A
Implement of Background Map in ArcGIS Engine Application Based on Google Static Map
FANG Jun1, FU Yunhong2
(1.Software College, ChangeSha Social Work College, Changsha410004, China;
2. National Super—computer Center in Changsha,Changsha410082, China)
Abstract:Many websites such as Google Map provide convenient and economic secondary development environment for enterprise to build application based on GIS.But they are realized with web technology. In this paper, a method which uses Google Static Map Services to display background map in an desktop application based on ArcGIS Engine is discussed. This method can also used with other websites such as Sogou Map, Bing Map, etc.
Key words:Google Static Map; ArcGIS Engine; mercator projection; tile
1引言
目前,越來(lái)越多的信息系統(tǒng)都有對(duì)地理信息的需求,但由于地理信息的復(fù)雜性和海量特性,企業(yè)構(gòu)建自己的地理信息數(shù)據(jù)庫(kù)有一定難度,因此,越來(lái)越多地借助于開(kāi)放的地理信息系統(tǒng)平臺(tái)進(jìn)行二次開(kāi)發(fā),既可行又經(jīng)濟(jì)[1]。當(dāng)前,開(kāi)放的地理信息系統(tǒng)平臺(tái)主要有Google Map、Microsoft Bing Map、搜狗地圖等。這些平臺(tái)的開(kāi)發(fā)接口都是基于Web技術(shù)實(shí)現(xiàn)的,對(duì)于它們的應(yīng)用也主要采用B/S模式。然而,在很多桌面應(yīng)用中,同樣有對(duì)地理信息的應(yīng)用,如通信網(wǎng)優(yōu)軟件中基于城市道路、建筑分布的情況的數(shù)據(jù)分析與展示都離不開(kāi)地理信息的支持。但由于B/S和C/S技術(shù)的差異,要在桌面應(yīng)用中使用這些開(kāi)放平臺(tái)提供的各類(lèi)服務(wù),需要采用一些特殊的發(fā)方法。
本文討論在基于ArcGis Engine的桌面應(yīng)用中集成Google Static Map服務(wù)實(shí)現(xiàn)背景地圖顯示的方法。
2Google Static Map簡(jiǎn)介
Google Static Map服務(wù)是Google以靜態(tài)圖片提供的地圖服務(wù)[4]。只要按照Google提供的標(biāo)準(zhǔn)格式輸入http請(qǐng)求,就可以在網(wǎng)頁(yè)上得到相應(yīng)的地圖圖片。該服務(wù)是免費(fèi)的。分析這個(gè)服務(wù)返回的圖片,可以發(fā)現(xiàn)它是基于Google的瓦片地圖庫(kù)生成的圖片。下面是一個(gè)請(qǐng)求Google Static Map的例子[4]:http://maps.google.com/maps/api/staticmap?center=lonXlatzoom=14size=400x400sensor=1
其中,lon和lat是請(qǐng)求圖片中心點(diǎn)的經(jīng)緯度。
計(jì)算技術(shù)與自動(dòng)化2012年9月
第31卷第3期方俊等:基于ArcGIS Engine和Google靜態(tài)地圖服務(wù)的背景地圖實(shí)現(xiàn)
在基于地理信息的桌面應(yīng)用中,往往要以直觀的地圖圖片作為背景,特別是有些應(yīng)用需要以衛(wèi)星實(shí)景地圖作背景。Google Static Map服務(wù)提供了獲取這種地圖圖片的一種經(jīng)濟(jì)適用方式。下面將給出利用Google Static Map服務(wù)圖片作為桌面應(yīng)用背景圖片的方法。
3構(gòu)建地圖庫(kù)
從Google Static Map獲取圖片并作為背景在ArcGis Engine的地圖控件中顯示的步驟是:通過(guò)Http請(qǐng)求對(duì)象發(fā)送對(duì)圖片的請(qǐng)求,得到響應(yīng)后將其存為本地圖片文件,再將圖片文件加載到地圖控件中。為了提高性能,可以對(duì)請(qǐng)求過(guò)的圖片進(jìn)行本地緩存,以后再次請(qǐng)求同一位置的圖片時(shí)就不需重新從Google服務(wù)中下載,而直接使用緩存中的圖片。
Google Static Map最大只能支持640X640的圖片[4],因此,需要通過(guò)多圖拼接方式才能獲得較大范圍的圖片,相當(dāng)于把一張大地圖切片為小的圖片,然后把它們拼成一張大圖。基于Google的瓦片技術(shù)對(duì)圖片切片并緩存本地,在顯示時(shí)將多張小圖拼接在一起形成大圖。
3.1Google瓦片技術(shù)
Google地圖具有0~21縮放級(jí),0級(jí)比例尺最大,21級(jí)最小。0級(jí)將全球投影在一張256X256的圖片上,以后每放大一個(gè)級(jí)別就將原來(lái)級(jí)別中的每個(gè)256X256圖片放大成4張256X256的圖片[2]。如圖1。
圖1瓦片算法
3.2坐標(biāo)變換
很顯然,如需要顯示某塊區(qū)域的地圖,只需要獲取能覆蓋這塊區(qū)域的多塊瓦片即可,如圖2所示。實(shí)線小方塊表示下載的靜態(tài)地圖圖片,虛線大框表示用戶(hù)界面中顯示部分。要顯示虛線框中的地圖,必須獲取九個(gè)地圖圖片。
圖2顯示區(qū)域與瓦片的關(guān)系
為了獲取這些地圖圖片,需計(jì)算這些圖片的下載請(qǐng)求參數(shù)。在所有參數(shù)中,最重要的參數(shù)是size和center。size表示圖片尺寸,應(yīng)為256X256,center為圖片中心,這兩個(gè)參數(shù)決定一個(gè)圖片覆蓋的地理區(qū)域。為了使獲取的圖片與google的瓦片一致,需要計(jì)算要請(qǐng)求的圖片的中心。
要計(jì)算圖片中心,需了解Google Map相關(guān)的幾種坐標(biāo)系的概念。Google Map定義的坐標(biāo)系有大地坐標(biāo)系、投影坐標(biāo)系、像素坐標(biāo)系及瓦片坐標(biāo)系。Google采用的大地坐標(biāo)系標(biāo)準(zhǔn)為WGS84,以經(jīng)緯度為單位,經(jīng)墨卡托投影生成投影坐標(biāo)系,以米為單位。這兩個(gè)坐標(biāo)系都是以本初子午線和赤道的交點(diǎn)為原點(diǎn),橫軸往東為正,縱軸王上為正。兩種坐標(biāo)系可通過(guò)墨卡托投影公式進(jìn)行轉(zhuǎn)換。墨卡托投影公式如下[3]:
y=R*lntanπ4+φ2
x=R*θ
其中,R是地球半徑,為緯度,為經(jīng)度,x,y為墨卡托投影坐標(biāo)。
瓦片坐標(biāo)系是對(duì)同一縮放級(jí)下瓦片的編號(hào)。以西經(jīng)180度北緯85.05113為左上角,坐標(biāo)系橫軸往東為正,縱軸往南為正。
如前所述,每個(gè)瓦片是一個(gè)256X256的圖片,像素坐標(biāo)系就是將瓦片坐標(biāo)細(xì)化為像素位置的坐標(biāo)。
3.3算法
已知條件有兩個(gè):地圖縮放級(jí)別和虛框四個(gè)頂點(diǎn)的經(jīng)緯度。獲取如圖2所示的相關(guān)瓦片的參數(shù)的算法如下:
a)應(yīng)用墨卡托公式,通過(guò)經(jīng)緯度計(jì)算四個(gè)頂點(diǎn)的投影坐標(biāo)mx, my;
b)通過(guò)投影坐標(biāo)計(jì)算四個(gè)頂點(diǎn)像素坐標(biāo),計(jì)算如下:
已知常量:地球半徑r = 6378137米,地球周長(zhǎng)的一半為l = 20037508.342780244米, google Map最大緯度 = 85.05113度,初始級(jí)(0級(jí))分辨率(單像素表示的距離)s = 156543.033928041米。
設(shè)z為縮放級(jí)(0~21),Sz為該級(jí)別的分辨率,x, y為像素坐標(biāo),則:
Sz = s / 2z
x = (int)((mx + l) / Sz)
y = (int)((l— my) / Sz )
上述公式中用到分辨率的原因是圖片上的一個(gè)像素點(diǎn)表示的是地理上的一個(gè)區(qū)域。
c)由像素坐標(biāo)計(jì)算其所處的瓦片的坐標(biāo),公式如下:
設(shè)tx,ty為瓦片坐標(biāo),則
tx = (int)(x / 256), ty = (int)(y / 256);
d)計(jì)算瓦片中心經(jīng)緯度;
通過(guò)上述步驟計(jì)算出顯示區(qū)域虛框的四個(gè)頂點(diǎn)的瓦片坐標(biāo)后,即可得到虛框覆蓋區(qū)域的所有瓦片的坐標(biāo),利用瓦片坐標(biāo)可以算出每個(gè)瓦片的中心點(diǎn)的經(jīng)緯度,算法如下:
設(shè)瓦片坐標(biāo)為tx, ty,則瓦片的上下左右邊界的像素值為:
minX = tx * 256
maxX = minX + 256 – 1
minY = ty * 256
maxY = ty + 256 – 1
這樣可以得到瓦片中心的像素坐標(biāo)((minX + maxX) / 2, (minY + maxY) / 2),再利用與a、b步驟中相反的算法即可計(jì)算改中心點(diǎn)對(duì)應(yīng)的經(jīng)緯度。
通過(guò)上述算法得到覆蓋區(qū)域所有瓦片的中心經(jīng)緯度后,結(jié)合前面給出的請(qǐng)求格式,就可以瓦片的URL,利用這些URL,在程序中就可以下載所需靜態(tài)地圖圖片了。
4背景地圖在AE控件中的顯示
本節(jié)基于.net開(kāi)發(fā)環(huán)境下的C#語(yǔ)言描述。
在獲取顯示區(qū)域的圖片后,使用ArcGIS Engine的地圖控件MapControl將這些圖片顯示為背景地圖時(shí)還需要進(jìn)行一些特殊處理。因?yàn)椋诘貓D控件的刷新機(jī)制中,不同類(lèi)型的圖層的刷新次序不同,顯示圖片的圖層總是最后刷新[5],這樣就會(huì)造成圖片覆蓋其它圖層的效果。而背景地圖總是應(yīng)該顯示在其它圖層下面,因此,需要調(diào)整背景圖層的刷新時(shí)間,使它在其它圖層刷新之前刷新。解決方案如下:
擴(kuò)展圖層類(lèi)CompositeGraphicsLayerClass[5],生成一個(gè)新的圖層類(lèi)BackgroundLayerUseStaticMap,這個(gè)新類(lèi)中只要重寫(xiě)基類(lèi)中的SupportedDrawPhases方法,使它的刷新時(shí)間發(fā)生改變,代碼如下:
public override int SupportedDrawPhases
{
get
{
return (int)ESRI.ArcGIS.esriSystem.esriDrawPhase.esriDPGeography;
}
}
代碼中的esriDPGeography是ArcGIS定義的一種刷新階段,表示在刷新地理要素之前刷新本圖層。這是一個(gè)新的圖層類(lèi),在向這個(gè)圖層類(lèi)對(duì)象添加背景地圖元素時(shí),使用ArcGIS開(kāi)發(fā)環(huán)境提供的PngPictureElementClass或PngPictureElementClass就可顯示png或bmp圖片,并且圖層中的圖片在地理要素刷新前刷新。圖3是利用google static map實(shí)現(xiàn)的背景圖效果。
圖3基于google static map服務(wù)的背景地圖顯示效果
5結(jié)束語(yǔ)
本文給出基于ArcGIS Engine的桌面應(yīng)用中背景地圖的一種經(jīng)濟(jì)的實(shí)現(xiàn)方案,其中的地圖資源是以Google Map的靜態(tài)服務(wù)為例。目前,提供靜態(tài)地圖服務(wù)的網(wǎng)站還有很多,如sogo地圖、bing的瓦片服務(wù)等,采用本文的方案同樣可以實(shí)現(xiàn)。
參考文獻(xiàn)
[1]王芳.Google地圖開(kāi)發(fā)研究[J].計(jì)算機(jī)與數(shù)字工程,2010,38(3);146—149.
[2]高皓亮.基于Google Map的空間數(shù)據(jù)整合技術(shù)[EB/OL].中國(guó)科技論文在線,http://www.paper.edu.cn
[3]吳忠信.《地圖投影》[M],北京:測(cè)繪出版社,1980.
[4]Google Static Map API文檔[EB/OL],https://developers.google.com/maps/documentation/staticmaps/?hl=zh—CN
[5]ArcGIS開(kāi)發(fā)文檔,ArcObjects SDK for ArcGIS 10.