所周知,j2me平台受限於各廠商對KVM的實現不同。此外,由於不同終端性能的差別,j2me開發中的 機型適配是相當繁瑣的工作。當然,對於該難題,有很多種解決方案。例如,可以使用j2mepolish,請參考本人以前發表的文章《使用J2MEPolish的build和preprocess功能》。本文主要討論如何使用antenna來解決這個問題。
Antenna介紹
Antenna是基於ant的j2me開發工具。可以使用antenna對J2ME程序進行 編譯、校驗、打包、混淆等,甚至可以通過antenna所定義的task,運行已經打包完成的jar;還可以將打包完成jad和jar部署到OTA服務器上。
以上功能,只是對ant的擴展,在我以前的文章《使用Ant對j2me程序打包》也討論。其實,以上所說的功能,直接使用ant也能實現,只是antenna對這些task進行了擴展,使得對j2me程序的打包過程更加的傻瓜話罷了。貌似,話說到這裡有些自相矛盾了,既然這些功能ant都能實現,還介紹antenna干嘛呢?其實,本人最推崇antenna的,不僅是它對j2me打包過程的簡化,而且特別贊賞它對預處理的支持。除此之外,antenna的預處理,結合了J2MEpolish所提供的device.XML數據庫,就是說,我們也可以像在J2MEpolish中那樣,對源程序進行相關的處理,以達到多機型時配的要求。
Antenna中的預處理
中的預處理原來與J2MEpolish等支持預處理的軟件一致,都是在編譯之前,對代碼中定義的預處理腳本進行處理,並生成符合腳本定義規則的代碼。在antenna中,通過“wtkpreprocess”task來進行預處理。關於預處理腳本的定義,請參考antenna自帶doc中的wtkpreprocess.Html。此外,本文討論的preprocessor是指新版的preprocessor,即version=2,原來的預處理機制不在本文討論范圍之內。下面舉例說明,如何通過在代碼中定義腳本獲取終端相關信息,類似於《使用J2MEPolish的build和preprocess功能》一文中的例子,感興趣的朋友可以結合起來學習。
Task定義如下:
XML 代碼
<wtkpreprocessverbose="true"version="2"srcdir="${dir.src}"destdir="${dir.dist}"
device="Nokia/6600"printsymbols="true"/>
其中,device為制定的機型型號,而printsymbols用於標示,是否在處理過程,將所有的標記打印出來。出於學習和調試目的,最好設置為true
源代碼片斷:
Java 代碼
publicclassMyCanvas
//#if'nokia-ui'@JavaPackage
//#extendscom.nokia.mid.ui.FullCanvas
//#else
extendsCanvas
//#endif
{
//#ifdefkey.LeftSoftKey
//#expandpublicfinalstaticintKEY_SOFT_LEFT=%key.LeftSoftKey%;
//#else
publicfinalstaticintKEY_SOFT_LEFT=6;
//#endif
//#ifdefkey.RightSoftKey
//#expandpublicfinalstaticintKEY_SOFT_RIGHT=%key.RightSoftKey%;
//#else
publicfinalstaticintKEY_SOFT_RIGHT=7;
//#endif
intscreenWidth=getWidth();
intscreenHeight=getHeight();
publicMyCanvas()
{
// #if!('nokia-ui'@JavaPackage)
//#setFullScreenMode(true);
//#endif
}
protectedvoidpaint(Graphicsg)
{
//#ifdefScreenSize
//#expandStringscreensize="%ScreenSize%";
//#else
Stringscreensize="128x128";
//#endif
g.setColor(0);
g.fillRect(0,0,screenWidth,screenHeight);
g.setColor(255,255,255);
g.drawString(screensize,screenWidth/2,screenHeight/2,0);
}
}
如此一來,就可以通過antenna中的預處理機制,解決多機型之間,鍵值不同,屏幕大小不同,擴展API不同等問題。
注意,device.xml中,有些數據並沒有安全定義。例如,各終端的導航鍵值就沒有定義。可自行添加到device.xml中,然後覆蓋原來的antenna包中的device.XML即可。
目錄結構定義
在打包過程中,對整個工程的目錄設置如下,具體體現在build.XML中
src ——源碼目錄
res——資源目錄
build
—— 編譯後的class文件以及從res復制過來的資源文件——jar和jad文件
dist——預處理後的Java文件
Ant腳本
按照以上分析,build.XML文件定義如下:
XML 代碼
<targetname="init"description="變量定義">
<echomessage="Definevariable"/>
<!--相關變量定義-->
<propertyname="basedir"value="."/>
<propertyname="midlet.version"value="1.0"/>
<propertyname="jad.filename"value="AntennaApp"/>
<propertyname="jar.filename"value="${jad.filename}"/>
<propertyname="wtk.proguard.home"value="E:Develpmentproguard3.9"/>
<!--目錄結構定義-->
<propertyname="dir.src"value="src"/>
<propertyname="dir.res"value="res"/>
<propertyname="dir.output"value="${basedir}/build"/>
<propertyname="dir.dist"value="${basedir}/dist"/>
<propertyname="dir.classes"value="${dir.output}/classes"/>
<propertyname="dir.deployed"value="${dir.output}/deployed"/>
<propertyname="wtk.home"value="E:DevelpmentSDKWTK25"/>
<propertyname="wtk.cldc.version"value="1.0"/>
<propertyname="wtk.midp.version"value="2.0"/>
<propertyname="wtk.wma.enabled"value="false"/>
<propertyname="wtk.debug"value="false"/>
<propertyname="wtk.obfuscate"value="true"/>
<!--JAD相關屬性定義-->
<propertyname="jad.midlet-name"value="AntennaApp"/>
<propertyname="jad.midlet-vender"value="org"/>
<propertyname="jad.midlet-version"value="1.0.0"/>
<!--Midlet相關定義-->
<propertyname="jad.midlet-class"value="MyMIDlet"/>
<propertyname="jad.midlet-icon"value=""/>
<!--發布-->
<propertyname="deploy.target"value="http://localhost:8080/deployer"/>
<propertyname="deploy.login"value="admin"/>
<propertyname="deploy.passWord"value="admin"/>
<!--</span-->target>
<targetname="clean"depends="init"description="初始化環境">
<echomessage="Cleandir"/>
<deletedir="${dir.output}"/>
<!--</span-->target>
<targetname="preprocess"depends="init,clean"description="預處理">
<echomessage="preprocess"/>
<mkdirdir="${dir.dist}"/>
<wtkpreprocessverbose="true"version="2"srcdir="${dir.src}"destdir="${dir.dist}"device="Nokia/6600"printsymbols="true"/>
<!--</span-->target>
<targetname="compile"depends="preprocess"description="編譯">
<echo>Startingcompile<!--</span-->echo>
<mkdirdir="${dir.classes}"/>
<echo>buildfromallthe${dir.src}to${dir.classes}<!--</span-->echo>
<wtkbuildsrcdir="${dir.dist}"destdir="${dir.classes}"target="1.1"source="1.2"preverify="false"debug="${wtk.debug}"listfiles="no"classpath="E:Develpmentwtk100lib
okiaui.zip">
<!--</span-->wtkbuild>
<!--</span-->target>
<targetname="build"depends="compile"description="生成">
<echomessage="Packaginglibrary"/>
<copytodir="${dir.classes}/res">
<filesetdir="${dir.res}"includes="*.png"/>
<filesetdir="${dir.res}"includes="*.propertIEs"/>
<filesetdir="${dir.res}"includes="*.midi"/>
<!--</span-->copy>
<mkdirdir="${dir.deployed}"/>
<wtkjadjadfile="${dir.deployed}/${jad.filename}.jad"
jarfile="${dir.deployed}/${jar.filename}.jar"
name="${jad.midlet-name}"
vendor="${jad.midlet-vender}"
version="${jad.midlet-version}">
<midletname="${jad.midlet-name}"
class="${jad.midlet-class}"
icon="${jad.midlet-icon}"/>
<attributename="MIDlet-Icon" value="${jad.midlet-icon}"/>
<attributename="MIDlet-Permissions" value="${jad.midlet-permissions}"/>
<attributename="MicroEdition-Configuration" value="CLDC-1.0"/>
<attributename="MicroEdition-Profile" value="MIDP-2.0"/>
<!--</span-->wtkjad>
<wtkpackagejarfile="${dir.deployed}/${jar.filename}.jar"
jadfile="${dir.deployed}/${jad.filename}.jad"
obfuscate="${wtk.obfuscate}"
preverify="true"classpath="E:Develpmentwtk100lib
okiaui.zip">
<filesetdir="${dir.classes}"/>
<!--</span-->wtkpackage>
<!--</span-->target>
注意:如果是在Eclipse中使用ant 來運行build.XML,請注意ant_home路徑的設置,且確認ant_homein目錄下存在antenna包。
軟件版本
apache-ant-1.7.0
antenna-bin-0.9.15-beta.jar
jdk1.5
eclipse3.2