Symbian學(xué)習(xí)筆記(20)——關(guān)于皮膚的小結(jié)
最基本的一招就是在AppUi中的ConstructL()中加一句話搞定。如下:
- void CTestMIMAppUi::ConstructL() {<BR> BaseConstructL(CAknAppUi::EAknEnableSkin);<BR>//add your code here...<BR>}<BR>
用上面這句話基本上能讓大部分控件的透明化,顯示出系統(tǒng)的皮膚。
但是,有時(shí)我們會(huì)發(fā)現(xiàn)部分控件(比如那個(gè)CEikEdwin)仍顯示的一個(gè)難看的白底,此時(shí),我們需要做一些額外的工作了。
修改Container的頭文件,增加一個(gè)成員變量:
- CAknsBasicBackgroundControlContext* iBgContext;
然后在對(duì)應(yīng)的ConstructL函數(shù)中初始它:
- iBgContext = CAknsBasicBackgroundControlContext::NewL(KAknsIIDQsnBgAreaMainIdle,aRect,ETrue);
這兒的KAknsIIDQsBgAreaMainIdle你可以選擇其它的,不礙事的。
然后,因?yàn)镃EidEdwin有一個(gè)很方便的成員方法SetSkinBackgroundControlContextL,所以接下來(lái)的代碼就簡(jiǎn)單了:
- iEdWin=new(ELeave)CEikEdwin;<BR> CleanupStack::PushL(iEdWin);<BR> iEdWin->SetContainerWindowL(*this); <BR> iEdWin->ConstructL();<BR> iEdWin->SetSkinBackgroundControlContextL(iBgContext);<BR> iEdWin->SetExtentToWholeScreen();<BR> iEdWin->SetFocus(ETrue);<BR> iEdWin->ActivateL();<BR> CleanupStack::Pop(iEdWin);
這樣就可以了。別忘了,在析構(gòu)時(shí)delete它。
2.終極方法顯示系統(tǒng)皮膚
再進(jìn)一步,如果控件沒(méi)有這么方便的成員讓我們?nèi)ピO(shè)置它的背景,也有辦法(參考http://www.newlc.com/Enable-Skin-support-in-your.html)。
很好辦,先在H文件中增加一個(gè)MopSupplyObject的聲明:
- TTypeUid::Ptr MopSupplyObject(TTypeUid aId);
然后實(shí)現(xiàn)中,ContructL中就不用iEdWin->SetSkinBackgroundControlContextL了,而是在三個(gè)函數(shù)中分別處理:
- void CTestMIMEdtContainer::Draw(const TRect& aRect) const {<BR> CWindowGc& gc = SystemGc();<BR><BR> MAknsSkinInstance* skin = AknsUtils::SkinInstance();<BR> MAknsControlContext* cc = AknsDrawUtils::ControlContext( this );<BR> AknsDrawUtils::Background( skin, cc, this, gc, aRect );<BR>}<BR><BR>void CTestMIMEdtContainer::SizeChanged() {<BR> if(iBgContext)<BR> {<BR> iBgContext->SetRect(Rect());<BR> if ( &Window() )<BR> {<BR> iBgContext->SetParentPos( PositionRelativeToScreen() );<BR> }<BR> } <BR> DrawNow();<BR>}<BR>TTypeUid::Ptr CTestMIMEdtContainer::MopSupplyObject(TTypeUid aId)<BR>{<BR> if (iBgContext )<BR> {<BR> return MAknsControlContext::SupplyMopObject( aId, iBgContext );<BR> }<BR> return CCoeControl::MopSupplyObject(aId);<BR>}
void CTestMIMEdtContainer::Draw(const TRect& aRect) const {
CWindowGc& gc = SystemGc();
MAknsSkinInstance* skin = AknsUtils::SkinInstance();
MAknsControlContext* cc = AknsDrawUtils::ControlContext( this );
AknsDrawUtils::Background( skin, cc, this, gc, aRect );
}
void CTestMIMEdtContainer::SizeChanged() {
if(iBgContext)
{
iBgContext->SetRect(Rect());
if ( &Window() )
{
iBgContext->SetParentPos( PositionRelativeToScreen() );
}
}
DrawNow();
}
TTypeUid::Ptr CTestMIMEdtContainer::MopSupplyObject(TTypeUid aId)
{
if (iBgContext )
{
return MAknsControlContext::SupplyMopObject( aId, iBgContext );
}
return CCoeControl::MopSupplyObject(aId);
}
這樣也可以讓控件透明顯示出系統(tǒng)皮膚。
3.顯示自定義皮膚
來(lái)說(shuō)自定義皮膚的顯示,關(guān)鍵在于那個(gè)iBgContext成員如何弄出來(lái),前面的NewL()的第一個(gè)參數(shù)是系統(tǒng)定義的東西,現(xiàn)在我們需要自定義了。
同樣,先修改一個(gè)H文件,增加一個(gè)成員:
- TAknsItemID aSkinItem;
然后實(shí)現(xiàn)文件中的ContructL函數(shù)中,我們要從MIF文件中取圖片弄成背景:
- TFileName iMFileName;<BR> iMFileName.Copy(KMifFileName);<BR> CompleteWithAppPath(iMFileName);<BR> <BR> aSkinItem.iMinor = 0xE2139689;<BR> aSkinItem.iMajor = 1 ;<BR><BR> CAknsItemDef* mainBgItemDef = AknsUtils::CreateBitmapItemDefL(aSkinItem, iMFileName, EMbmTestmimGrid);<BR> AknsUtils::SkinInstance()->SetLocalItemDefL( mainBgItemDef ); <BR> iBgContext = CAknsBasicBackgroundControlContext::NewL(aSkinItem,aRect,ETrue );
這兒的KMifFileName是定義的資源MIF文件(與其它例子中加載資源圖像的方法類似)。
【編輯推薦】