在Python中使用ArcObjects對象
【本文環境】ArcGIS 10,Python 2.6
在ArcGIS 10以後,VBA將退出ArcGIS產品中,由此可想而知,將來Python在ArcGIS產品中的地位將會十分重要。雖然在ArcGIS中Python已經存在了很長一段時間,但是,一般常用的可能還是將模型匯出為Python指令碼,然後用以和他人交換或者使用作業系統定時任務等方式供其它程式調用。而本文需要描述的是,如何通過編寫Python指令碼,並在指令碼中使用ArcObjects對象,來充分發揮Python膠水語言的特點,在其它程式和ArcGIS之間構造一個互動的橋樑。
我們都知道ArcGIS中的ArcObjects都是COM對象,在Python中調用COM對象需要一個開源的類庫:comtypes,我們可以從sourceforge上下載並安裝它:
http://sourceforge.net/projects/comtypes/
在Windows下的安裝介面是這個樣子的:
在這步完成以後,所有對ArcGIS的調用就都是在Python環境下處理的問題了。讓我們首先來看如何在Python中載入ArcObjects的組件庫。
我這裡寫了一個方法,用以可以方便地載入ArcGIS的OLB檔案:
def GetAoModule(moduleName):
import comtypes
from comtypes.client import GetModule
GetModule('C:/Program Files (x86)/ArcGIS/Desktop10.0/com/' + moduleName)
這樣,在我想使用AO中的幾何對象時,只需要通過如下的代碼把esriGeometry這個物件程式庫載入上即可:GetAoModule('esriGeometry.olb')在這裡我們可以看到我們剛才安裝的comtypes的身影,我們依靠它才可以載入ArcGIS的物件程式庫。同樣,在這裡我們還需要依靠comtypes幫我們建立ArcObjects對象(COM對象),為了方便我這裡還定義了一個方法:
def AoObj(MyClass, MyInterface):
from comtypes.client import CreateObject
try:
obj = CreateObject(MyClass, interface=MyInterface)
return obj
except:
return None這樣,如果我想要在Python中建立一個ArcObjects對象,比如Point,我們就可以使用如下的方法:GetAoModule('esriGeometry.olb')
import comtypes.gen.esriSystem as esriSystem
pt = AoObj(esriSystem.Point, esriSystem.IPoint)現在,我們已經可以建立ArcObjects對象了,但是,這裡還有一個重要的問題需要解決,那就是如何進行對象介面類型轉化。比如我得到了一個對象的IWorkspace介面,但是我需要調用的是這個對象的IFeatureWorkspace介面的方法,這個時候需要一個轉化,在Python中我準備了另外一個方法去做這件事情:
def AoCType(obj, interface):
try:
newobj = obj.QueryInterface(interface)
return newobj
except:
return None這樣,如果我想將一個IWorkspace介面的對象轉到IFeatureWorkspace介面時,就可以這樣操刀:GetAoModule('esriGeoDatabase.olb')
import comtypes.gen.esriGeoDatabase as esriGeoDatabase
fw = AoCType(w, esriGeoDatabase.IFeatureWorkspace)通過上面的GetAoModule、AoObj和AoCType這3個方法,我們就可以方便地使用ArcObjects對象了。下面,讓我們通過一個從ArcSDE資料庫查詢要素的例子來再次熟悉一下Python中ArcObjects對象的使用:
GetAoModule('esriSystem.olb')
GetAoModule('esriDataSourcesGDB.olb')
GetAoModule('esriGeoDatabase.olb')
import comtypes.gen.esriSystem as esriSystem
aoInit = AoObj(esriSystem.AoInitialize, esriSystem.IAoInitialize)
pCode = esriSystem.esriLicenseProductCodeArcInfo
status = aoInit.IsProductCodeAvailable(pCode)
if status == esriSystem.esriLicenseAvailable:
aoInit.Initialize(pCode)
props = AoObj(esriSystem.PropertySet, esriSystem.IPropertySet)
props.SetProperty("server", "localhost")
props.SetProperty("instance", "5151")
props.SetProperty("user", "sde")
props.SetProperty("password", "sde")
props.SetProperty("version", "SDE.DEFAULT")
import comtypes.gen.esriDataSourcesGDB as esriDataSourcesGDB
import comtypes.gen.esriGeoDatabase as esriGeoDatabase
wf = AoObj(esriDataSourcesGDB.SdeWorkspaceFactory, esriGeoDatabase.IWorkspaceFactory)
w = wf.Open(props, False)
fw = AoCType(w, esriGeoDatabase.IFeatureWorkspace)
fc = fw.OpenFeatureClass("sde.sde.cities")
c = fc.Search(None, False)
f = c.NextFeature()
while (f != None):
print(str(f.ObjectID))
f = c.NextFeature()
本文來自CSDN部落格,轉載請標明出處:http://blog.csdn.net/warrenwyf/archive/2010/11/28/6040311.aspx