symbian系統開發培訓_第1頁
symbian系統開發培訓_第2頁
symbian系統開發培訓_第3頁
symbian系統開發培訓_第4頁
symbian系統開發培訓_第5頁
已閱讀5頁,還剩73頁未讀 繼續免費閱讀

下載本文檔

版權說明:本文檔由用戶提供并上傳,收益歸屬內容提供方,若內容存在侵權,請進行舉報或認領

文檔簡介

SymbianOS開發培訓InspurCommunicationInformationSystemsCo.,Ltd

第一頁,共七十八頁。SymbianOS概述

1998年6月,諾基亞(NOKIA)、摩托羅拉(MOTOROLA)、愛立信(ERICSSON)、三菱(MITSUBISHI)和Psion在英國倫敦共同投資成立Symbian公司。這個公司成立的目的是為了能夠設計并開發出一種可以在手機及其他類似的移動通訊終端產品上運行的開放性操作系統,以此來推動高端智能移動電話及類似的終端產品盡快進入大眾消費領域。之后有西門子(SIEMENS)、三星(SAMSUNG)、松下(Panasonic)、索尼愛立信(SonyEricsson)等手機廠商相繼入資,現如今,Symbian操作系統的智能手機已經占據了世界智能手機市場超過80%的份額。第二頁,共七十八頁。SymbianOS概述

Symbian是一個實時性、多任務的純32位操作系統,具有功耗低、內存占用少等特點,非常適合手機等移動設備使用,經過不斷完善,可以支持GPRS、藍牙、SyncML、以及3G技術。Symbian是一個標準化的開放式平臺,任何人都可以為支持Symbian的設備開發軟件。與微軟產品不同的是,Symbian將移動設備的通用技術,也就是操作系統的內核,與圖形用戶界面技術分開,能很好的適應不同方式輸入的平臺,也可以使廠商可以為自己的產品制作更加友好的操作界面,符合個性化的潮流第三頁,共七十八頁。SymbianOS概述

目前SymbianOS手機有三種開發SDK:NokiaSeries80:主要機型有Nokia9200系列NokiaSeries60:主要機型包括諾基亞7650、6600、西門子SX1等UIQ2、UIQ3:SonyEricssonP800,P900SonyEricssonP900第四頁,共七十八頁。開發平臺搭建安裝ActivePerl(x86和x64分別對應32位和64位cpu)jre(java的應用平臺)SymbianOSSDK(建議安裝在盤符根目錄下)(C++)開發工具第五頁,共七十八頁。手機軟件開發過程:開發平臺搭建第一步:安裝開發軟件,搭建開發環境(下面主要介紹series60sdk,其余類似)第二步:在模擬器上開發調試(以VC環境開發為例)第三步:生成sis文件,在手機上安裝運行第六頁,共七十八頁。幾種開發環境:開發平臺搭建VisualC++6.0BorlandC++Builder6CarbideC++第七頁,共七十八頁。開發平臺搭建Symbian工程aifdatagroupincsrcsis工程基本目錄結構:1.aif用來存放程序圖標2.data用來存放運行所需要的資源文件.rss。3.group中比較重要的幾個文件:bld.inf、*.mmp。4.inc和src存放工程頭文件和源代碼文件。5.sis用來存放程序打包所需要的pkg文件,打包后生成的安裝文件.sis也存放在此處。第八頁,共七十八頁。bld.inf聲明build的相關信息通常只包括這次build會引用到的mmp文件。例如:PRJ_MMPFILES

hello.mmp2..mmp文件保存工程編譯相關信息,主要內容如下

TARGEThello.app//目標名稱TARGETTYPEapp//目標類型UID0x100039CE0x07B9DE87//UID唯一系統標示符TARGETPATH\system\apps\hello//目標路徑SOURCEPATH..\src//源代碼存放位置SOURCEhelloApp.cpp//源代碼列表…

開發平臺搭建第九頁,共七十八頁。

SOURCEPATH..\data//資源文件路徑RESOURCEhello.rss//資源文件LANGSC//默認英語

USERINCLUDE.USERINCLUDE..\inc//頭文件路徑SYSTEMINCLUDE.\epoc32\include//系統包含文件目錄LIBRARYeuser.libapparc.libcone.libeikcore.libLIBRARYeikcoctl.libavkon.lib//庫文件3.UIDUID1-第一個UID(類型):

UID1用來設定該應用程序是一個執行程序(executablefile)還是一個數據文件(datafile).UIDvalueNumericvalue(Hex)MeaningKExecutableImageUid0x1000007A.exe可執行文件KDaynamicLibraryUid0x10000079.dll.app.ldd,.pdd文件KDirect0x10000037directKPermanent0x10000050permanent第十頁,共七十八頁。UID2-第二個UID(子類型):

UID2-具體含義取決于UID1的值:如果UID1是KExecutableImageUid,UID2不使用,所以UID2的值可以隨意取。如果UID1是KDynamicLibraryUid,UID2將會是:

如果UID1是KDirect或者KPermanent,那么UID2將是:UIDvalueNumericvalue(Hex)MeaningKSharedLibraryUid0x1000008D.dllKUidApp0x100039CE.appKLogicalDeviceDriverUid0x100000AFalogicaldecivedriver(.ldd)KPhysicalDeviceDriverUid0x100039D0aphysicaldevicedriver(.pdd)UIDvalueNumericvalue(Hex)MeaningKUidAppDllDoc0x10003A12indicatesthisisacreatedbyan.apptostoreuserdata(i.e,adocument)KUidAppInfoFile0x10003A38IndicatesthisisanAIFfile(atypeof)第十一頁,共七十八頁。UID3-第三個UID(子子類型):

每個獨立的應用程序有一個唯一的UID3值,它也被用作安全ID(secureID),對于UIKON應用程序而言,用于關聯數據文件和程序:1.

對于dll和exe文件,它辯識特定的二進制(itidentifiedtheparticularbinary)。2.

對于.app(UIKON應用程序),它辯識特定的應用程序(itidentifiedtheparticularapplicationprogram).3.

對于由.apps創建的文件存儲(),它辯識和該文件相關的應用程序(itidentifiestheapplicationprogramassociatedwiththisfile).4.

對于其他文件存儲(),它沒有典型的用途(但是你可以自定義它的用途)

第十二頁,共七十八頁。Symbian命名約定

Symbian大致分了四種類C:C前綴表示類從CBase派生并應該基于堆構造。T:T前綴表示一個簡單類,這種類不擁有任何額外的資源。如Tint、TReal等基本數據類型。R:R前綴表示一個資源類,它包含其它位置擁有資源的句柄。M:M前綴表示一個接口類,它定義了接口但需要派生類實現。結構(struct)類型作為T類對待,因為它也不擁有任何額外的資源,它的前綴通常是T(但也有一些以S開頭)。enumTColors{ERed,//盡量用E開頭,盡量用枚舉EGreen}成員變量的名字以i開頭,參數名以a開頭classTMyClass{

TIntiMyValue;

voidMyAddFunc(TIntaArg1,TIntaArg2);

voidMyAddFunc(TIntaArg1,TIntaArg2);voidMyAddFuncL(TIntaArg1,TIntaArg2);-------->后綴L的約定是該函數可能產生異常退出;voidMyAddFuncLC(TIntaArg1,TIntaArg2);

---------->后綴LC的約定表示成功完成之后,返回值會被壓入清理棧中;(棧不保存)};

Symbian編程規范和基本框架第十三頁,共七十八頁。Symbian命名約定常量應加前綴KconstCIntKMyconstant;宏全部為大寫#defineMY_HARDCODED_VALUE(25)

Symbian四個主要的應用軟件框架類

針對右圖Graphics,UI程序應該具備的基本功能類:視圖(View)、文檔(Document)、應用程序(Application)、應用程序UI(ApplicationUI)。所有的S60UI應用程序都具有一些基本功能:

提供一個用戶界面,用于顯示信息并允許用戶進行交互。

響應各種用戶啟動的事件,比如用戶選擇一個菜單項。

響應系統啟動的不同事件,比如導致屏幕重繪的window服務器事件。

能夠保存和恢復應用程序數據。可以唯一性的向框架標志自身。向框架提供有關應用程序的描述性信息,比如圖標和標題等。Symbian編程規范和基本框架第十四頁,共七十八頁。Symbian四個主要的應用軟件框架類一個程序只能有一個文檔,可以有多個視圖。必須創建下面的每個方法,才能提供最小的S60應用程序:

所有S60UI都實現一個全局函數E32DLL(),當應用程序啟動時,框架將首先調用該函數,該函數也稱為DLL入口點,應用程序必須存在該函數。

框架調用Ne(),創建Application類,其基類是CAknApplication.Application類創建應用程序類的Document對象,并返回它的指針,以后框架使用該指針完成應用程序的創建。

由框架調用AppDllUid()返回應用程序的UID。該函數必須返回在.mmp文件中指定的值。Document基類是CAknDocument.

Document對象通過CreateAppUiL創建獲取AppUi類的指針。AppUi類的基類是CAknAppUi或者

CAknVie,它是用來處理應用程序事件,如操作菜單,操作視圖,切換視圖等等。View是控制類(c類),在屏幕上顯示數據,用戶與界面交互,傳遞命令給AppUi。Symbian編程規范和基本框架第十五頁,共七十八頁。Symbian處理內存泄漏的手段1.Trap和TrapD處理異常

TInterr;

Trap(err,CreateObject());//需要先定義err變量TrapD(err,CreateObject());//不需要定義err變量2.CleanupStack

它是處理內存泄漏的又一重要手段CFoo*p=new(ELeave)CFoo();CleanupStack::PushL(p)p->SomeFunctionL();//可能異常退出,使得deletep得不到調用CleanupStack::Pop();

deletep;Symbian二階段構造在Symbian中,如果在一個類的構造函數中需要執行某些比如申請內存等操作,那么有可能會Leave。如果Leave的話,這個時候這個類的析構函數是不會被調用,因為還沒有初始化完,也就沒法把自己加入CleanupStack,那么那些申請了的內存可能會因為沒有變量引用而造成內存泄漏。因此在Symbian中類的構造函數中不能有可能會Leave的代碼。

Symbian編程規范和基本框架第十六頁,共七十八頁。Symbian二階段構造初始化一個類確實需要執行某些可能會Leave的函數,這就是Symbian中要求的兩階段初始化了。第一階段,也就是在構造函數中執行一些不會Leave的初始化工作。然后是第二階段,把這個實例推進CleanupStack,再執行第二階段的可能會Leave的代碼。當然,在析構函數中,要能夠處理部分初始化的情況,也就是實例沒有初始化成功,也能釋放那些已經申請的內存或資源。

CGraphicsAppView::CGraphicsAppView(){}CGraphicsAppView*CGraphicsAppView::NewL(constTRect&aRect){CGraphicsAppView*self=NewLC(aRect);CleanupStack::Pop(self);returnself;}CGraphicsAppView*CGraphicsAppView::NewLC(constTRect&aRect){CGraphicsAppView*self=new(ELeave)CGraphicsAppView;CleanupStack::PushL(self);self->ConstructL(aRect);returnself;}voidCGraphicsAppView::ConstructL(constTRect&aRect){CreateWindowL();SetRect(aRect);}Symbian編程規范和基本框架第十七頁,共七十八頁。描述符描述符是用來存儲文本和二進制的基本類抽象類(Abstract):(TDes、TDesC、TDes8、TDesC8),描述符的基類,僅提供接口和基本功能,不能被實例化,一般只用作函數的參數。文字常量(Literal):(TlitC、_LIT()),用于存儲文字字符串(literalstring),即C中字符串常量,通常使用_LIT()這種方式,也有_L(),_L8()這種方式。棧類(Buffer):(TBuf、TBufC、TBuf8、TBufC8),數據存儲于棧上,最基本的描述符變量類型,大小在編譯時確定,包含描述符本身數據,使用最為普遍,具體方法如下堆類(Heap):(HBufC、HBufC8),數據存儲于堆上,大小在運行時確定,也就是用來處理動態申請的描述符類。在C/C++中用過動態內存的都知道,動態內存是啥回事,這里堆類描述符用的時候,也是差不多,由于堆描述符沒有構造函數,所以只能聲明為指針類型,通過堆描述符類內靜態函數NewL方法申請內存,具體方法如下HBufC*errorTitleCode=HBufC::NewLC(50);HbufC*unUseCode=NULL;指針類(Pointer):(TPtr、TPtrC、TPtr8、TPtrC8),本身不包含描述符數據,但是包含長度數據,而且還包含一個指向位于描述符之外數據的指針。Symbian基本語法第十八頁,共七十八頁。描述符關系簡圖

Symbian基本語法第十九頁,共七十八頁。描述符的使用文字描述符常量

_LIT(KMyFile,“c:\System\Apps\MyApp\My”);它可以在任何使用TDesC&的地方使用。//常用的通知函數NEikonEnvironment::MessageBox(_L("Error:initfound!"));//數字轉字符串TBuf16<20>buf;//TIntiNum=20;buf.Format(_L("%d"),iNum

);棧描述符棧類描述符聲明時必須指定描述符的最大長度,否則無法聲明和定義,舉例如下://直接從字符串中構造_LIT(Ktext,"TestText");TBufC<10>Buf(Ktext);//或從字符串賦值TBufC<10>Buf2;Buf2=Ktext;//從已有的對象中生成新的TBufCTBufC<10>Buf3(Buf2);Symbian基本語法第二十頁,共七十八頁。描述符的使用棧描述符

盡管這里的對象表示數據是不能被修改的(因為有個后綴C代表了常量的意思),但仍然有兩種方式可以用來修改數據內容:這里的數據可以用賦值的方式替換掉;使用Des()函數構造出一個TPtr對象,這樣就可以用它來修改數據。_LIT(Ktext,"TestText");

_LIT(Ktext1,"TestText”);_LIT(KXtraText,"New:");TBufC<10>Buf1(Ktext);//Buf1長度為9內容“TestText”TBufC<10>Buf2(Ktext1);//Buf2長度為10內容“Test1Text”//通過賦值的方式改變數據Buf2=Buf1;//Buf2長度變為9內容“TestText”//通過使用Des()生成指針改變TBufC的數據TPtrPointer=Buf1.Des();//刪除后四個字符Pointer.Delete(Pointer.Length()-4,4);//Buf1長度變為5內容“Test”

//增加新的數據Pointer.Append(KXtraText);//Buf1長度為9內容為“TestNew:”//也可以使用下列方式改變數據

TBufC<10>Buf3(NewText);Pointer.Copy(Buf3);//Buf1長度為4,內容為New1//或直接從字符串里獲得數據Pointer.Copy(NewText1);//Buf1長度為4,內容為New2Symbian基本語法第二十一頁,共七十八頁。描述符的使用棧描述符可修改的描述符TBuf,TBuf8就不用通過那么復雜的方法來實現修改,它直接可以用Copy、Delete等方法,但是無論可修改的還是不可修改的,一旦指定最大的數據長度后,最大長度就不能進行修改了修改的只是數據內容,而數據內容修改的受限條件是不能超過聲明或定義時的最大長度。堆描述符堆描述符HBufC,HbufC8雖然都是不可修改類型的,但是它仍然具有構造和修改,與棧描述符不同的是:首先對內存需要顯示釋放,其次是堆描述符沒有最大長度的限制,任何時候都可以用ReAlloc()函數重新申請分配。有兩種方式來生成一個堆描述符示例:

//第一種方式用New(),NewL(),或NewLC()

HBufC*Buf=HBufC::NewL(15);

//第二種方式是采用Alloc(),AllocL()或AllcLC()來處理_LIT(KText,"TestText");

TBufC<10>

CBuf=KText;

HBufC*Buf1=CBuf.AllocL();

CleanupStack::PushL(Buf1);堆描述符的修改方式:

//1.賦值方式改變其數據的方法

_LIT(KText1,"Text1");

*Buf1=KText1;

Symbian基本語法第二十二頁,共七十八頁。描述符的使用堆描述符堆描述符的修改方式://2.通過可修改指針來改變數據的方式

TPtrPointer=Buf1->Des();

Pointer.Delete(Pointer.Length()-2,2);

//刪除數據

_LIT(KNew,"New:");

Pointer.Append(KNew);

//添加數據重新申請內存Buf1=Buf1->ReAllocL(KText().Length()+KNew().Length());CleanupStack::PushL(Buf1);釋放內存

deleteBuf;

Buf=NULL;指針描述符不可修改的指針TPtrC可用TBuf和TBufC構造出TPtrC對象

_LIT(KText,"TestCode");

TBufC<10>Buf(KText);

//或者為TBuf<10>Buf(KText);

TPtrC

Ptr(Buf);//使用構造函數初始化

TPtrC

Ptr1;

Ptr1.Set(Buf);//利用set函數初始化Symbian基本語法第二十三頁,共七十八頁。描述符的使用指針描述符不可修改的指針TPtrC

用TText*構造TPtrC

constTText*text=_S("HelloWorld\n");

TPtrCptr(text);

//或者

TPtrCPtr2;

Ptr2.Set(text);

//如果要存儲TText的一部分數據,我們使用下列方法

TPtrC

ptr4(text,5);

從另一個TPtrC中構造TPtrC

constTText*text1=_S("HelloWorld\n");

TPtrCPtr3(text1);

//從一個TPtrC中獲得另一個TPtrC

TPtrCp1(Ptr3);

//或

TPtrCp2;

p2.Set(Ptr3);可修改的TPtr同不可修改的指針描述符構造方法基本類似,區別在于,不可修改的指針描述符TPtrC的函數始終是不可修改的,因此沒有Insert,Delete等函數,并且沒有Des()函數,但有Alloc(),Compare(),Find(),Mid(),Size()等函數。Symbian基本語法第二十四頁,共七十八頁。動態數組

在傳統c/c++中經常會使用數組來存儲序列,它是具有相同數據類型的數據元素的集合,通過數組可以很方便的實現數據元素的訪問等相關操作。動態數組是一個類的模板,可以接受各種各樣的數據類型,SymbianOS主要提供了3類動態數組:

RArray<classT>,RPointerArray<classT>,CArray<classT>活動對象

在symbianos中活動對象是一種非搶先式多任務處理的機制,是symbianos中一個十分重要的概念。可用于替代SymbianOS中的多線程。使用活動對象可獲得的好處是:在同一個線程中運行的活動對象之間進行切換的代價要比線程上下文的切換代價低,這使得對于各種資源比較緊張的SymbianOS來說,使得活動對象更適合事件驅動多任務。

概念:一個活動對象必須派生自基類CActiveclassCActive:publicCBase{

public:

enumTpriority

{

EPriorityIdle=-100;

EPriorityLow=-20;

EPriorityStandard=0;

EPriorityUserInput=10;

EPriorityHigh=20;

}

Symbian基本語法第二十五頁,共七十八頁。活動對象

public:

IMPORT_C~CActive();

IMPORT_CvoidCancel();//刪除未完成請求的函數

……

IMPORT_CvoidSetPriority(TIntaPriority);

InlineTBoolIsActive()const;

……

protected:

IMPORT_CCActive(TIntaPriority);

IMPORT_CvoidSetActive();

virtualvoidDoCancel()=0;//兩個純虛函數,繼承類必須實現它們

virtualvoidRunL()=0;//處理函數

IMPORT_CvirtualTIntRunError(TIntaError);

public:

TrequestStatusiStatus;//代表請求狀態

…….

private:

TBooliActive;

…….

}構造時也會有一個優先級值來決定它們如何被調度Cancel和DoCancel用來取消發出的請求,Docancel是一個純虛函數,需要由派生類實現。Cancel的功能就是調用DoCancel,如果用戶取消當前請求調用Cancel而不是DoCancel,但在代碼中要實現DocancelSymbian基本語法第二十六頁,共七十八頁。活動對象IsActive確定活動對象是否處于活動狀態SetActive激活活動對象,一般在調用請求后緊接著調用它。RunL異步事件處理函數,當一個請求完成時,活動對象調度器會調用這個函數,進行下一步處理RunError當RunL函數出現異常時會出現RunError函數,它也是純虛函數,需要派生類實現。

具體例子見文檔。文件管理symbian系統采用了C/S(客戶端/服務器)的架構。對于文件操作,系統有一個文件系統管理的服務器。程序通過聯結這個文件管理服務器來進行文件。在symbianos中,Flash(閃存)通常被定義在c盤,symbian智能手機中還有一個ROM存儲器通常被映射在z盤,用戶的許多文件也存放在z盤。其他可移動存儲(如存儲卡)則映射在d,e等盤符。symbian開發環境下各盤符對應的映射關系:客戶機c:盤對應開發平臺中sdk的\epoc32\wins\c目錄客戶機d:盤對應開發平臺中sdk的\epoc32\wins\d目錄客戶機z:盤對應開發平臺中sdk的\epoc32\release\wins\urel\z目錄或者\epoc32\release\wins\urel\z文件命名規則一個完整的symbianos文件應該包含以下四個部分1.驅動器名,即盤符2.路徑,從根目錄到或當前會話目錄起到文件經過的所有目錄路徑3.文件名,遵循c/c++命名規范4.文件擴展名例如:c:\my就是合法的文件名,一個完整的文件名不能超過255個字符。Symbian基本語法第二十七頁,共七十八頁。文件管理文件訪問流程1.應用程序要進行文件讀寫之前,必須建立應用程序與文件服務器的連接,這種連接也稱會話(session),Sysmbianos中提供RFs類來實現這個功能,該類提供了Connect()和Close()函數來建立和關閉連接。RFsfsSession;//建立RFs類的對象User::LeaveIfError(fsSession.Connect());//建立連接,為防止出現異常放User::LeaveIfError中

fsSession.Close();//用完關閉連接2.文件服務器可以實現文件的讀、寫、刪、建,通過R(RFsaFs,constTDesC&aName,TUnita)打開文件。通過Write()和Read()可以實現文件的寫和讀。R()用于建立新文件。刪除文件可以使用RFs的Delete()。3.另一種比較重要的文件讀寫方式----流(Stream)文件輸出流RWriteStream和文件輸入流RReadStream文件輸出六主要使用RWriteStream的派生類R將數據外化為流,它需要先打開一個文件,打開文件的兩種方式:OpenL:當文件不存在會產生異常,所以必須保證文件存在Replace:文件存在刪除并重建新的,不存在就創建,因每次都創建文件,會帶來額外開銷。例子:

Rwriter; writer.PushL();//writeroncleanupstack User::LeaveIfError(writer.Replace(iCoeEnv->FsSession(),*i,E)); writer<<*iText; //writethetext writer.CommitL(); CleanupStack::PopAndDestroy();//釋放資源從存儲中讀取數據的方法就是將以上的過程反向Symbian基本應用第二十八頁,共七十八頁。數據庫管理

Symbian系統的DBMS提供了創建與維持數據庫的功能,通過本地調用和SQL調用,其可以對數據庫進行安全可靠的數據訪問。這種調用支持事務/回滾機制用以保證所有數據被寫入或數據為空的情形獲得支持。DBMS的管理結構和元素任何Symbian系統的DBMS都采用層次性的結構—最底層是保存數據庫的文件倉庫。Symbian操作系統的DBMS是一個功能強大,或為輕量集的數據庫關系系統實現。它支持普通的添加/查找/檢索/更新/刪除功能,同時它還支持基本的結構化查詢語言(StructuredQueryLanguage:SQL),數據定義語言(DataDefinitionLanguage:DDL)和數據建模語言(DataModelingLanguage:DML)語句處理。永久文件存儲系統和流Symbian系統的DBMS依賴于文件服務器提供的資源,Symbian系統所的永久文件存儲和流能提供系統所需要的底層存儲功能。永久文件系統通過使用CPermanent來獲得,它是一個源自C的具體類。這些類在文件存儲API中定義,可為DBMS提供組建模塊。創建數據庫(1)RDbStoreDatabase:通過文件存儲打開的數據庫,提供了進行數據庫操作的API,獨占使用數據庫,不可共享使用。(2)RDbNamedDatabase:通過文件名打開的數據庫,同樣提供API。使用C/S模式,可以共享使用(3)CDbColSet:數據庫字段的集合,可用于在數據庫中創建表格。(4)使用到的庫和頭文件:ws32.libedbms.libd32dbms.hf32file.hs32file.h創建步驟:(1)數據庫類的聲明:將RFs和RDbStoreDatabase聲明為數據成員。classCMiapSampleDatabase:publicCBase

{

Symbian基本應用第二十九頁,共七十八頁。數據庫管理public:

//SomeFunctions

private:

RFsiFsSession;

RDbStoreDatabaseiDb;};

(2)創建數據庫:

首先打開一個文件流存儲(),通過調用RDbStoreDatabase::CreateL(CStreamStore*aStore)來創建數據庫。最后將文件流提交。

_LIT(K,"C:\\DataBase.db");

C*=CPermanent(iFsSession,K,E);

CleanupStack::PushL();

>SetTypeL(>Layout());

TStreamIdid=iDb.CreateL();

>SetRootL(id);

>CommitL();

CleanupStack::PopAndDestroy();

iOpen=ETrue;

iDb.Close();Symbian基本應用第三十頁,共七十八頁。數據庫管理(3)創建表格:

通過文件流存儲打開數據庫:

_LIT(K,"C:\\DataBase.db");

C*=CPermanent(iFsSession,K,E);

>SetTypeL(>Layout());

iDb.OpenL(,>Root());

添加字段:

_LIT(KId,"Id");

_LIT(KText,"Text");

_LIT(KTableName,"Table");

TDbColIdCol(KId,EDbColText);

TDbColTextCol(KText,EDbColText);

CDbColSet*ColSet=CDbColSet::NewLC();

ColSet->AddL(IdCol);

ColSet->AddL(TextCol);

創建表格:

User::LeaveIfError(iDb.CreateTable(KTableName,*ColSet)); 釋放不使用的內存:

CleanupStack::PopAndDestroy(ColSet);

CleanupStack::PopAndDestroy();Symbian基本應用第三十一頁,共七十八頁。數據庫管理(4)創建索引:

TDbKeyColIdKey(KId);

CDbKey*key=CDbKey::NewLC();

key->AddL(IdKey);

User::LeaveIfError(iDb.CreateIndex(KTableName,KTableName,*key));

CleanupStack::PopAndDestroy(key);

首先創建一個索引對象,將其添加到索引集合中,通過調用RDbStoreDatabase::CreateIndex(constTDesC&aName,constTDesC&aTable,constCDbKey&aKey)創建表格,最后清除不使用的內存。(5)插入記錄:

_LIT(KIdText,"100001");首先打開數據庫。打開表:

RDbTabletable;

CleanupClosePushL(table);

User::LeaveIfError(table.Open(iDb,aTableName,table.EUpdatable));

獲取字段集合:

CDbColSet*ColSet=table.ColSetL();

CleanupStack::PushL(ColSet);

添加記錄:

table.Reset();

table.InsertL();

table.SetColL(ColSet->ColNo(KId),KIdText);

table.PutL();

CleanupStack::PopAndDestroy(2);//清除內存:注意:每插入一條記錄,就必須調用table.InsertL(),設置完值后,必須調用table.PutL()提交。Symbian基本應用第三十二頁,共七十八頁。(6)查詢記錄:

首先打開數據庫和表。

TPtrCptrc;

for(table.FirstL();table.AtRow();table.NextL())

{

table.GetL();

ptrc.Set(table.ColDes(colSet->ColNo(KId)));

}

table.FirstL()將焦點設置為第一條記錄,table.AtRow()驗證下一條記錄是否存在,table.NextL()將焦點移動到下一條記錄。

每查詢一條記錄,必須調用table.GetL();

使用TPtrC::Set()將查詢結果寫進描述符。(7)執行SQL語句:

首先打開數據庫。 TBuf<256>SQL;

SQL.Append(_L("http://SomeSQL"));

RDbUpdateDbUpdate;

TIntincStat=DbUpdate.Execute(iDb,SQL,EDbCompareNormal);

incStat=DbUpdate.Next();

while(incStat==1)

{

incStat=DbUpdate.Next();

}

DbUpdate.Close();Symbian基本應用第三十三頁,共七十八頁。

SymbianGUI編程60系列用戶界面顯示器規范如下:分辨率:176像素(寬)×208像素(高)正方形像素物理尺寸:約35mm(寬),41mm(高), 對應約0.2mm的象素點距。顏色數(4096色或更多)第三十四頁,共七十八頁。

SymbianGUI編程第三十五頁,共七十八頁。SymbianGUI編程顯示器按照一定的層次結構進行布局。布局由被稱為窗口(windows)和窗格(panes)的組件構建。屏幕(Screen)是最頂層的顯示組件,對應于物理屏幕的整個象素區域。窗口(Window)屏幕(screen)是窗口的唯一父組件。一般情況下一個窗口會充滿整個屏幕,但有時也存在一些小窗口(臨時性的),它們只占據屏幕的一部分,環繞其周圍的部分是可見的。每個應用程序都在自己的窗口中運行。應用程序也可以調用其它的臨時窗口。

窗格(Pane)窗格是窗口(window)的子組件。一個窗口可以包含多個窗格,而每個窗格又可以包含多個子窗格,如此等等。不含有子組件的底層組件被稱為元素(element)。

應用窗口應用窗口是覆蓋整個屏幕的主窗口。通常它并不直接用于顯示,而是作為各種窗格的父組件。一個典型的應用窗口由下幾種窗格組成:-狀態窗格-主窗格-控制窗格第三十六頁,共七十八頁。SymbianGUI編程第三十七頁,共七十八頁。GUI應用程序的基本組成部分Application負責啟動方面的工作Document負責永久保持的工作AppUI負責接受并處理用戶的命令AppView負責圖形顯示的工作Model可選:負責處理數據第三十八頁,共七十八頁。view架構view是一個執行特定任務的一屏同一時刻,view管理系統只允許一個view處于激活狀態每個view都有一個ID每個view必須到viewserver上去登記調用ActiveViewL()還能夠激活其它應用程序的views在view之間能夠傳遞消息classCMyView:publicCAknView第三十九頁,共七十八頁。CCoeControl框架主要內容簡單控件CCoeControl概述控件的初始化控件的重繪用戶輸入處理(按鍵事件)復合控件常用控件對話框表格資源菜單軟鍵熱鍵第四十頁,共七十八頁。CCoeControl框架WINDOWSserver第四十一頁,共七十八頁。CCoeControl框架WINDOWSserver第四十二頁,共七十八頁。CoeControl可以作為視圖的基類傳統的EIKON視圖架構-containerdialog負責應用程序視圖區域的顯示工作一個應用程序的界面分為三部分標題欄軟鍵區域應用程序視圖區域(右圖的黑框部分)使用CGraphicsContext進行畫圖在UI平臺能力范圍內工作(如:60系列)系統提供的常用控件有按鈕編輯器文本標簽列表框可以內嵌其它控件(又稱定制控件,或者復合控件)第四十三頁,共七十八頁。CoeControl所有對屏幕的操作都是在控件上進行控件從CCoeControl繼承而來控件是屏幕上的一個矩形區域控件占據窗口的全部或者部分應用程序的視圖使用至少一個控件控件可以處理用戶的輸入事件鍵盤事件鼠標事件第四十四頁,共七十八頁。CoeControl是所有控件的基類被派生類直接調用的函數SetRect()CreateWindowL()被派生類重載的函數OfferKeyEventL()Draw()所擁有的函數可以分為以下三類初始化Drawing用戶輸入處理第四十五頁,共七十八頁。初始化classCAbcContainer:publicCCoeControl{public://ConstructorsanddestructorvoidConstructL(constTRect&aRect); ~CAbcContainer();private://FunctionsfrombaseclassesvoidSizeChanged(); voidDraw(constTRect&aRect)const; };voidCAbcContainer::ConstructL(constTRect&aRect){CreateWindowL(); SetRect(aRect);ActivateL();}第四十六頁,共七十八頁。初始化classCAbcContainer:publicCCoeControl{public://ConstructorsanddestructorvoidConstructL(constTRect&aRect); ~CAbcContainer();private://FunctionsfrombaseclassesvoidSizeChanged(); voidDraw(constTRect&aRect)const; };voidCAbcContainer::ConstructL(constTRect&aRect){CreateWindowL(); SetRect(aRect);ActivateL();}第四十七頁,共七十八頁。DrawingvirtualvoidDraw(constTRect&aRect)const;負責產生控件的圖形化外觀重要提示基類中的該函數為空,在派生類中如果不實現該函數的話控件將不可見該方法由應用程序框架調用,不要自己調用該函數方法是const,意味著你在Draw()中不能更改任何成員變量,或者調用任何不是const的函數。該函數不允許leave,因此你必須用TRAP封裝可能leave的函數第四十八頁,共七十八頁。Draw()voidCAbcContainer::Draw(constTRect&aRect)const{CWindowGc&gc=SystemGc();gc.SetPenStyle(CGraphicsContext::ENullPen);gc.SetBrushColor(KRgbDarkBlue);gc.SetBrushStyle(CGraphicsContext::ESolidBrush);gc.DrawRect(aRect);//gc.Clear()}第四十九頁,共七十八頁。圖形設備接口GDI抽象類CGraphicsContext(圖形上下文)定義了一致的接口派生類CWindowGc和CFbsBitGc具體實現了這些接口可以直接使用CFbsBitGc繪圖,但不推薦:第五十頁,共七十八頁。推薦的繪圖方式建議在程序中使用CWindowGc提供的接口第五十一頁,共七十八頁。圖形上下文 CWindowGc&SystemGc()const用來獲取當前的圖形上下文提供了許多有用的繪圖函數畫點、線、橢圓、矩形、位圖等等改變畫筆/畫刷的顏色和風格改變字體設置裁剪區域,原點在某一時刻CWindowGc只能由一個窗口激活voidActivate(RDrawableWindow&aWindow)voidDeactivate()第五十二頁,共七十八頁。控件的重繪(redraw) 更新在屏幕上的顯示兩種類型系統發起的windowserver我們“必須”重繪控件應用程序發起的內部狀態改變我們“想要”重繪控件第五十三頁,共七十八頁。系統發起的重繪 當windowserver檢測到可能使一個區域無效的事件對話框/菜單不再需要時啟動一個GUI程序時發送redraw消息給擁有窗口的應用程序應用程序通過CONE發送消息給相關的控件調用控件的Draw()函數第五十四頁,共七十八頁。應用發起的重繪 通常是某個內部狀態改變的結果實現方法有以下幾種:Invalidate控件窗口的某部分,讓windowserver發送一個redraw消息請求CONE立即重繪整個控件立即重繪控件的某個部分所有的實現方法最終都是調用Draw()函數第五十五頁,共七十八頁。redraw的類型 立即重繪整個控件CCoeControl::DrawNow()在程序初始化時采用一旦有機會就重繪整個窗口:voidCCoeControl::DrawDeferred()const部分窗口:voidRWindow::Invalidate(constTRect&)立即重繪已知無效的部分voidCSemView::DrawSunNow()const{Window().Invalidate(iSunArea);ActivateGc();Window().BeginRedraw(iSunArea);DrawSun();Window().EndRedraw();DeactivateGc();}第五十六頁,共七十八頁。更多Draw()的信息參數aRect指定重繪的區域相對于控件的原點(左上角)對于簡單控件,通常重繪整個控件對于復合控件,只重繪部分控件防止屏幕閃爍只重繪位于無效區域的部分不要短時間內多次重繪某個區域盡量避免大面積的重繪第五十七頁,共七十八頁。處理按鍵事件控件能夠檢測并處理按鍵事件按鍵事件的處理是獨立于資源文件定義的熱鍵處理之外的UI框架已經實現了大部分的按鍵處理典型應用導航鍵選擇鍵第五十八頁,共七十八頁。CONE控件堆棧按鍵事件由系統通告給對其感興趣的控件在一個特殊的數據結構(CONE控件堆棧)中登記感興趣的控件系統給控件發送OfferKeyEventL事件CONE控件堆棧中的控件被一一通告事件的發生,直至某個控件宣稱接收了該事件控件按優先級被通告事件的發生控件必須告知系統是否接收了該事件如果沒有任何控件宣稱接收一個事件,則最后將由AppUi在它的CMyAppUi::HandleKeyEventL()中處理該事件第五十九頁,共七十八頁。AppUi對按鍵事件的處理在CONE控件堆棧中登記控件voidCtestAppUi::ConstructL(){BaseConstructL();iAppContainer=new(ELeave)CtestContainer;iAppContainer->SetMopParent(this);iAppContainer->ConstructL(ClientRect());AddToStackL(iAppContainer);iAppContainer2=new(ELeave)CtestContainer2;iAppContainer2->SetMopParent(this);iAppContainer2->ConstructL(ClientRect());AddToStackL(iAppContainer2);}在析構的時候將控件從CONE控件堆棧中注銷CtestAppUi::~CtestAppUi(){if(iAppContainer){RemoveFromStack(iAppContainer);deleteiAppContainer;}}第六十頁,共七十八頁。CCoeControl對按鍵事件的處理TKeyResponseOfferKeyEventL(constTKeyEvent&aEvent,TEventCodeaType)TKeyResponseCMyGameView::OfferKeyEventL(constTKeyEvent&aKeyEvent,TEventCodeaType){switch(aType){caseEEventKey:if(aKeyEvent.iScanCode==EStdKeyNkp5||aKeyEvent.iScanCode==EStdKeyDevice3){ iMyGameEngine->Fire();returnEKeyWasConsumed;}break;caseEEventKeyDown:…caseEEventKeyUp:…}returnEKeyWasNotConsumed;}第六十一頁,共七十八頁。點擊事件的處理60系列并不支持筆寫輸入但模擬器支持筆的點擊voidHandlePointerEventL(constTPointerEvent&)第六十二頁,共七十八頁。復合控件compoundcontrol包含其它控件的控件有時也稱container,容器為什么要用復合控件共享主控件的現有窗口重用控件系統控件(CEikLabel)自己的控件(CMyInfoControl)可以選擇性地重繪子控件第六十三頁,共七十八頁。容器(主控件)的責任創建窗口只為主控件創建窗口子控件重用該窗口創建和刪除子控件在主控件中定義成員變量在析構函數中刪除子控件擺放子控件設置自己的大小擺放子控件第六十四頁,共七十八頁。CCoeControl&Windows創建一個新窗口CreateWindowL()為主控件所擁有為子控件所共享重用現有的窗口SetContainerWindowL(constCCoeControl&aContainer)子控件調用該函數減少與windowserver的c/s交互}第六十五頁,共七十八頁。創建子控件在容器的第二階段構造函數中創建子控件,并讓它們重用容器的窗口voidCtestContainer::ConstructL(constTRect&aRect){CreateWindowL();//創建主窗口iLabel=new(ELeave)CEikLabel;iLabel->SetContainerWindowL(*this);iLabel->SetTextL(_L("ExampleView"));iToDoLabel=new(ELeave)CEikLabel;iToDoLabel->SetContainerWindowL(*this);iToDoLabel->SetTextL(_L("AddYourcontrols\nhere"));SetRect(aRect);ActivateL();}第六十六頁,共七十八頁。通告給CONE相應的信息告訴CONE擁有的子控件的數目TIntCtestContainer::CountComponentControls()const缺省的實現返回0返回子控件的指針CCoeControl*CtestContainer::ComponentControl(TIntaIndex)const用來依次對所有的子控件執行操作第一個控件的index為0,順序通常不是很重要如果忘記重載上述兩個函數,則子控件依然存在,但無法顯示,因為CONE不知道我們的容器有幾個子控件第六十七頁,共七十八頁。復合控件的繪圖重繪容器時也重繪了子控件首先調用容器的Draw()然后調用子控件的Draw()CONE利用CountComponentControls()和ComponentControl(TIntaIndex)依次調用自控件的Draw()防止閃爍如果子控件覆蓋了整個容器的區域,則無須為容器提供Draw(),否則會重繪兩次同一區域,產生閃爍只重繪沒有被子控件覆蓋的區域設置裁剪區域voidSetClippingRect(constTRect&aRect)TintSetClippingRegion(constTRegion&aClippingRegion)TRegionFix<10>clippingRegion;clippingRegion.Clear();clippingRegion.AddRect(Rect());clippingRegion.SubRect(iSubControl1);//裁剪掉該子控件占用的區域clippingRegion.SubRect(iSubControl2);第六十八頁,共七十八頁。轉發按鍵事件只有容器被壓入CONE控件堆棧由AppUi來將其壓棧必須轉發按鍵事件給子控件具體實現TKeyResponseCMainControl::OfferKeyEvent(..){ if(aType!=EEventKey)return; returniSubContro

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯系上傳者。文件的所有權益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網頁內容里面會有圖紙預覽,若沒有圖紙預覽就沒有圖紙。
  • 4. 未經權益所有人同意不得將文件中的內容挪作商業或盈利用途。
  • 5. 人人文庫網僅提供信息存儲空間,僅對用戶上傳內容的表現方式做保護處理,對用戶上傳分享的文檔內容本身不做任何修改或編輯,并不能對任何下載內容負責。
  • 6. 下載文件中如有侵權或不適當內容,請與我們聯系,我們立即糾正。
  • 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

評論

0/150

提交評論