標籤:
在上一篇文章裡,我簡單扼要的給大家介紹了一下GDI的基礎知識,包括DC,HDC,GDI對象等等,總的來說都是些偏理論的知識,屬於概念的範疇。
今天這篇文章裡,我就要正式開始有點實際的東西了,我會教大家一些GDI的準系統代碼編寫,基本的技巧,當然還有如何避免基本的坑,哈哈,對的,基本的坑而不是進階的。
那麼我要如何說起呢,首先我要告訴大家如何建立DC,如何使用DC,如何設定DC的屬性(也就是GDI對象),如何在DC上繪製簡單的文字,繪製圖形,繪製圖片也就是位元影像。我還會附帶的說說GDI+,說說CImage這個繪圖超級方便的類(我在我過去的項目中大量的使用了這個類),還要說說圓角視窗的實現,包括用蒙板色的辦法和用層疊視窗的辦法。當然這麼多的內容在這樣一篇文章裡肯定是寫不完的,所以我將在後面的文章裡逐一介紹,有興趣的朋友可以等我一篇一篇婉婉道來。
首先來談談DC的使用
擷取DC的方式有好幾種,一般而言有如下幾種
CreateDC,查閱MSDN可知其參數如下:
HDC CreateDC(LPCTSTR lpszDriver, LPCTSTR lpszDevice, LPCTSTR lpszOutput,constDEVMODE* lpInitData)
這個函數的第一個參數lpszDriver,表示你要建立DC的裝置,也就是表示你想進行抽象的裝置,一般而言可以是顯示器或者印表機,因為用於列印的情況比較少,我們這裡只討論“DISPLAY”這個參數的情況。
當第一個參數為“DISPLAY”時,lpszDevice決定了你要在哪一個顯示裝置上進行繪製,如果你要在主顯示裝置上進行繪製,可以這樣調用CreateDC
CreateDC(TEXT("DISPLAY"),NULL,NULL,NULL)
這個函數的HDC類型返回值,就代表了這個顯示裝置,有了這個HDC,我們就可以在螢幕上進行繪製了。
下面再說另外一種擷取DC的方式GetDC
GetDC是基於視窗的,它只有一個HWND型別參數,代表了你想進行繪製的視窗,因為它的用法比較簡單,我這裡不做多說
說到這裡,是不是覺得這兩個函數還挺簡單,但是在使用CreateDC和GetDC建立的DC之後,GDI的對象和資源在使用完畢後都是需要釋放的,這裡有個常見的坑,我在網上很多的技術部落格上看到不少作者都犯了這個錯誤。
釋放DC有兩種函數
DeleteDC,ReleaseDC
那麼它二者有什麼區別呢?
查閱MSDN對二者的Remark可知
An application must not delete a DC whose handle was obtained bycalling the GetDC function. Instead, it mustcall the ReleaseDC function to free the DC.
An applicationcannot use the ReleaseDC functionto release a DC that was created by calling the CreateDC function; instead, it must usethe DeleteDC function. ReleaseDC mustbe called from the same thread that called GetDC.
換句話說:CreateDC與DeleteDC配對使用,而GetDC與ReleaseDC配對使用,二者不可替換,用錯了釋放方法,這是初學者,甚至很多有經驗的老鳥都會犯的錯誤。而且在最後,還需要有一點要注意的,RelaseDC必須在與GetDC相同的線程中進行調用。
看到這裡,大家可能覺得真的細節還是不少的,但這些正是區分一個Windows開發老手和菜鳥的標誌,所以對於我們這些Windows開發人員而言,需要注意得到地方的確很多,我們必須一絲不苟的摳每一個API的參數,含義以及坑,這大概也是一種樂趣吧。
Windows用戶端開發簡介(四)