天天看點

【大話QT之六】QT皮膚系統的動态切換

應用需求:

        提供皮膚切換選項,在不重新開機應用程式的情況下實作皮膚的動态切換。

理論基礎:

        1) 圖檔資源是如何被利用的

            這裡先簡要說明一下實作原理,皮膚的動态切換其關鍵在于圖檔資源的加載方式。qt中每個應用程式啟動後都會維護屬于自己的資源子庫,所有的圖檔以及ui資源都實作編譯到rcc檔案中,而rcc檔案是整合了所有資源的二進制檔案,這種方式屬于動态加載。

             圖檔是一種資源,在qt中,對于資源的使用有以下幾點:

             1>  一般來說:資源在記憶體中是用資源對象樹來表示的,該樹在程式啟動時建立。

             2>    對于資源而言:都是需要先将其加入到這棵樹中才能加載到記憶體中并被程式使用。

             3>    将一個圖檔資源動态加載到資源的對象樹中是用函數:qresource::registerresource()來實作的,即先将資源向這顆資源對象樹進行注冊,這樣才可以在程式中使用該資源葉子。資源一旦注冊到資源子樹中它就會占用記憶體。

             4>    當不再需要使用某個資源圖檔時,我們不希望它繼續占用記憶體,此時需要用qresource::unregisterresource()來進行反注冊。此函數的作用就是在資源對象樹中周遊找到代表該資源的節點,然後delete釋放它。

             總的來說就是:一個程式所用到的資源都是放到一棵資源對象樹中的,當程式啟動時該樹便會自動建立,而當我們使用某個資源時都需要實作将其向該樹進行注冊,當不需要時則需要進行反注冊。

        2) 圖檔資源使用的三種方式

        1>  在程式運作時加載圖檔

               這是最簡單的一種使用方法,例如:image = newqimage(“1.png”),這種方法在程式運作時再去加載圖檔,需要在對應目錄下事先放置好圖檔,這樣做的優點是程式 運作時不需要的檔案不會加載,節省了記憶體,但是這種方式是i/o讀取,是以速度會相對慢一些。

         2>  将圖檔編譯進工程

               這種方式是在pro檔案下添加一行:resources = test.qrc ; qrc檔案中添加了對圖檔資源的引用,它的格式如下:

【大話QT之六】QT皮膚系統的動态切換

               這樣程式在釋出時不需要在目錄下放置圖檔,利用該qrc檔案在編譯的時候會自動生成qrc_test.cpp檔案,裡面主要是利用三個數組來存放圖檔的二進制資料。

當使用qrc資源檔案時,系統會自動将所有的圖檔資源都向程式的資源對象樹進行注冊,并且當程式結束時再進行反注冊。使用這種方式,由于圖檔資源一直在記憶體中,避免了i/o操作,加快了讀取速度,但是卻是以消耗記憶體為代價的。

         3>  手動進行注冊

               上面利用qrc檔案是程式運作時一次性将圖檔資源全部加載到資源對象樹中,直到程式運作結束才會反注冊。而最佳的實作方式是:需要用到時,将資源加載進來,不需要的時候可以對資源進行反注冊,進而可以節省記憶體。

               這種方法的主要步驟為:

               1)    利用qrc和qss檔案生成rcc二進制資源檔案:rcc.exe –binary test.qrc –o test.rcc

               2)    在需要的時候将該資源向程式的資源對象樹進行注冊使用。

               3)    在不需要時進行反注冊。

皮膚插件系統的實作:

         皮膚插件系統實作的基本邏輯圖如下:

【大話QT之六】QT皮膚系統的動态切換

        其實作原理就是根據上面的三種方式,手動進行rcc檔案的注冊與反注冊。這裡需要強調的一點是:每個子產品都有自己的一套:qrc、qss以及他們生成的rcc檔案,因為我們利用rcc檔案就是避免它一次性将所有的資源注冊上(如果每套皮膚隻用一個rcc檔案将所有的資源都注冊上,在記憶體方面沒有優勢,隻是提供了可以進行皮膚動态切換的可能,gf2中的每套皮膚就隻有一個rcc檔案),需要時注冊,不需要時反注冊,是以我們需要手動地控制哪個子產品合适注冊、何時反注冊。比如:程式啟動先注冊login子產品的資源檔案,當登入成功後,登入界面就消失了,然後主面闆開始出現,這個時候我們就可以将登入子產品注冊的資源檔案進行反注冊。如果主界面邏輯中還有一個按鈕是顯示所有檔案同步資訊的,當我們點選時,檔案資訊子產品注冊上,關閉視窗時,檔案資訊子產品資源反注冊,而此時主面闆子產品資源一直都是注冊着的。采用這種方式,可能會花費一些精力還處理不同子產品資源的注冊與反注冊。

總結:

         這裡的關鍵還是要了解動态方式使用rcc檔案,它是插件系統得以實作的基礎,本質就是向資源對象樹中的注冊與反注冊。注意:這裡充分利用了配置檔案的優點,還是基于插件的體系。由于界面具體的樣式還沒有細調,這裡就不上圖了,不過已經可以實作皮膚的動态切換了。聯想到其它,所有皮膚切換的實作原理都基本相似吧,自己的知識盲區中又少了一塊,加油!!五一來臨。

繼續閱讀