久久国产成人av_抖音国产毛片_a片网站免费观看_A片无码播放手机在线观看,色五月在线观看,亚洲精品m在线观看,女人自慰的免费网址,悠悠在线观看精品视频,一级日本片免费的,亚洲精品久,国产精品成人久久久久久久

分享

DIB處理程式庫

 alal51 2010-08-12
 

DIB處理程式庫
 

就是現(xiàn)在-經(jīng)過我們長時間地學習GDI點陣圖物件,、裝置無關(guān)點陣圖、DIB區(qū)塊和Windows調(diào)色盤管理器之後-我們才做好了開發(fā)一套有助於處理點陣圖的函式的準備,。

前面的PACKEDIB檔案展示了一種可能的方法:記憶體中的packed DIB只用指向它的指標表示,。程式所的有關(guān)DIB的全部資訊都可以從存取表頭資訊結(jié)構(gòu)的函式獲得。然而,,實際上到「get pixel」和「set pixel」常式時,,這種方法就會產(chǎn)生嚴重的執(zhí)行問題。圖像處理任務(wù)當然需要存取點陣圖位元,,並且這些函式也應(yīng)該盡可能地快,。

可能的C++的解決方式中包括建立DIB類別,這時指向packed DIB的指標正好是一個成員變數(shù),。其他成員變數(shù)和成員函式有助於更快地執(zhí)行獲得和設(shè)定DIB中的圖素的常式,。不過,因為我在第一章已經(jīng)指出,,對於本書您只需要瞭解C,,使用C++將是其他書的範圍,。

當然,用C++能做的事情用C也能做,。一個好的例子就是許多Windows函式都使用代號,。除了將代號當作數(shù)值以外,應(yīng)用程式對它還瞭解什麼呢,?程式知道代號引用特殊的函式物件,,還知道函式用於處理現(xiàn)存的物件。顯然,,作業(yè)系統(tǒng)按某種方式用代號來引用物件的內(nèi)部資訊,。代號可以與結(jié)構(gòu)指標一樣簡單。

例如,,假設(shè)有一個函式集,,這些函式都使用一個稱為HDIB的代號。HDIB是什麼呢,?它可能在某個表頭檔案中定義如下:

typedef void * HDIB ;

此定義用「不關(guān)您的事」回答了「HDIB是什麼」這個問題,。

然而,實際上HDIB可能是結(jié)構(gòu)指標,,該結(jié)構(gòu)不僅包括指向packed DIB的指標,,還包括其他資訊:

typedef struct
{
BITMAPINFO 	* 	pPackedDib ;
int          				cx, cy, cBitsPerPixel, cBytesPerRow ;
BYTE       			* pBits ;
{
DIBSTRUCTURE, * PDIBSTRUCTURE ;

此結(jié)構(gòu)的其他五個欄位包括從packed DIB中引出的資訊。當然,,結(jié)構(gòu)中這些值允許更快速地存取它們。不同的DIB程式庫函式都可以處理這個結(jié)構(gòu),,而不是pPackedDib指標,。可以按下面的方法來執(zhí)行DibGetPixelPointer函式:

BYTE * DibGetPixelPointer (HDIB hdib, int x, int y)
{
PDIBSTRUCTURE pdib = hdib ;
return pdib->pBits + 	y * pdib->cBytesPerRow +
x * pdib->cBitsPerPixel / 8 ;
}

當然,,這種方法可能要比PACKEDIB.C中執(zhí)行「get pixel」常式快,。

由於這種方法非常合理,所以我決定放棄packed DIB,,並改用處理DIB區(qū)塊的DIB程式庫,。這實際上使我們對packed DIB的處理有更大的彈性(也就是說,能夠在裝置無關(guān)的方式下操縱DIB圖素位元),,而且在Windows NT下執(zhí)行時將更有效,。

DIBSTRUCT結(jié)構(gòu)
 

DIBHELP.C檔案-如此命名是因為對處理DIB提供幫助-有上千行,並在幾個小部分中顯示,。但是首先讓我們看一下DIBHELP函式所處理的結(jié)構(gòu),,該結(jié)構(gòu)在DIBHELP.C中定義如下:

typedef struct
{
PBYTE    	* ppRow ;       // array of row pointers
int        	iSignature ;  	// = "Dib "
HBITMAP    	hBitmap ;     	// handle returned from CreateDIBSection
BYTE     	* 	pBits ;     // pointer to bitmap bits
DIBSECTION 	ds ;          	// DIBSECTION structure
int        	iRShift[3] ;  	// right-shift values for color masks
int        	iLShift[3] ;  	// left-shift values for color masks
}
DIBSTRUCT, * PDIBSTRUCT ;

現(xiàn)在跳過第一個欄位。它之所以為第一個欄位是因為它使某些巨集更易於使用-在討論完其他欄位以後再來理解第一個欄位就更容易了,。

在DIBHELP.C中,,當DIB建立的函式首先設(shè)定了此結(jié)構(gòu)時,,第二個欄位就設(shè)定為文字字串「Dib」的二進位值。通過一些DIBHELP函式,,第二個欄位將用於結(jié)構(gòu)有效指標的一個標記,。

第三個欄位,即hBitmap,,是從CreateDIBSection函式傳回的點陣圖代號,。您將想起該代號可有多種使用方式,它與我們在 第十四章 遇到的GDI點陣圖物件的代號用法一樣,。不過,,從CreateDIBSection傳回的代號將涉及按裝置無關(guān)格式儲存的點陣圖,該點陣圖格式一直儲存到通過呼叫BitBlt和StretchBlt來將位元圖畫到輸出設(shè)備,。

DIBSTRUCT的第四個欄位是指向點陣圖位元的指標,。此值也可由CreateDIBSection函式設(shè)定。您將想起,,作業(yè)系統(tǒng)將控制這個記憶體塊,,但應(yīng)用程式有存取它的許可權(quán)。在刪除點陣圖代號時,,記憶體塊將自動釋放,。

DIBSTRUCT的第五個欄位是DIBSECTION結(jié)構(gòu)。如果您有從CreateDIBSection傳回的點陣圖代號,,那麼您可以將代號傳遞給GetObject函式以獲得有關(guān)DIBSECTION結(jié)構(gòu)中的點陣圖資訊:

GetObject (hBitmap, sizeof (DIBSECTION), &ds) ;

作為提示,,DIBSECTION結(jié)構(gòu)在WINGDI.H中定義如下:

typedef struct tagDIBSECTION {
BITMAP     				dsBm ;
BITMAPINFOHEADER 	dsBmih ;
DWORD            	dsBitfields[3] ;    // Color masks
HANDLE          dshSection ;
DWORD           dsOffset ;
}
DIBSECTION, * PDIBSECTION ;

第一個欄位是BITMAP結(jié)構(gòu),它與CreateBitmapIndirect一起建立點陣圖物件,,與GetObject一起傳回關(guān)於DDB的資訊,。第二個欄位是BITMAPINFOHEADER結(jié)構(gòu)。不管點陣圖資訊結(jié)構(gòu)是否傳遞給CreateDIBSection函式,,DIBSECTION結(jié)構(gòu)總有BITMAPINFOHEADER結(jié)構(gòu)而不是其他結(jié)構(gòu),,例如BITMAPCOREHEADER結(jié)構(gòu)。這意味著在存取此結(jié)構(gòu)時,,DIBHELP.C中的許多函式都不必檢查與OS/2相容的DIB,。

對於16位元和32位元的DIB,如果BITMAPINFOHEADER結(jié)構(gòu)的biCompression欄位是BI_BITFIELDS,,那麼在資訊表頭結(jié)構(gòu)後面通常有三個遮罩值,。這些遮罩值決定如何將16位元和32位圖素值轉(zhuǎn)換成RGB顏色。遮罩儲存在DIBSECTION結(jié)構(gòu)的第三個欄位中,。

DIBSECTION結(jié)構(gòu)的最後兩個欄位指的是DIB區(qū)塊,,此區(qū)塊由檔案映射建立。DIBHELP不使用CreateDIBSection的這個特性,,因此可以忽略這些欄位,。

DIBSTRUCT的最後兩個欄位儲存左右移位值,,這些值用於處理16位元和32位元DIB的顏色遮罩。我們將在 第十五章 討論這些移位值,。

讓我們再回來看一下DIBSTRUCT的第一個欄位,。正如我們所看到的一樣,在開始建立DIB時,,此欄位設(shè)定為指向一個指標陣列的指標,,該陣列中的每個指標都指向DIB中的一行圖素。這些指標允許以更快的方式來獲得DIB圖素位元,,同時也被定義,,以便頂行可以首先引用DIB圖素位元。此陣列的最後一個元素-引用DIB圖像的最底行-通常等於DIBSTRUCT的pBits欄位,。

資訊函式
 

DIBHELP.C以定義DIBSTRUCT結(jié)構(gòu)開始,,然後提供一個函式集,此函式集允許應(yīng)用程式獲得有關(guān)DIB區(qū)塊的資訊,。程式16-19顯示了DIBHELP.C的第一部分,。

 程式16-19  DIBHELP.C檔案的第一部分
DIBHELP.C (第一部分)
/*--------------------------------------------------------------------------
DIBHELP.C -- 	DIB Section Helper Routines
(c) Charles Petzold, 1998
----------------------------------------------------------------------------*/
#include <windows.h>
#include "dibhelp.h"
#define HDIB_SIGNATURE (* (int *) "Dib ")
typedef struct
{
PBYTE    			* 	ppRow ;    // must be first field for macros!
int        			iSignature ;
HBITMAP    			hBitmap ;
BYTE     			* 	pBits ;
DIBSECTION 		ds ;
int        				iRShift[3] ;
int        				iLShift[3] ;
}
DIBSTRUCT, * PDIBSTRUCT ;
/*----------------------------------------------------------------------------
DibIsValid:  Returns TRUE if hdib points to a valid DIBSTRUCT
-----------------------------------------------------------------------------*/
BOOL DibIsValid (HDIB hdib)
{
PDIBSTRUCT pdib = hdib ;
if (pdib == NULL)
return FALSE ;
if (IsBadReadPtr (pdib, sizeof (DIBSTRUCT)))
return FALSE ;
if (pdib->iSignature != HDIB_SIGNATURE)
return FALSE ;
return TRUE ;
}
/*----------------------------------------------------------------------------
DibBitmapHandle:	Returns the handle to the DIB section bitmap object
-----------------------------------------------------------------------------*/
HBITMAP DibBitmapHandle (HDIB hdib)
{
if (!DibIsValid (hdib))
return NULL ;
return ((PDIBSTRUCT) hdib)->hBitmap ;
}
/*---------------------------------------------------------------------------
DibWidth:  Returns the bitmap pixel width
-----------------------------------------------------------------------------*/
int DibWidth (HDIB hdib)
{
if (!DibIsValid (hdib))
return 0 ;
return ((PDIBSTRUCT) hdib)->ds.dsBm.bmWidth ;
}
/*---------------------------------------------------------------------------
DibHeight:  Returns the bitmap pixel height
----------------------------------------------------------------------------*/
int DibHeight (HDIB hdib)
{
if (!DibIsValid (hdib))
return 0 ;
return ((PDIBSTRUCT) hdib)->ds.dsBm.bmHeight ;
}
/*---------------------------------------------------------------------------
DibBitCount:  	Returns the number of bits per pixel
----------------------------------------------------------------------------*/
int DibBitCount (HDIB hdib)
{
if (!DibIsValid (hdib))
return 0 ;
return ((PDIBSTRUCT) hdib)->ds.dsBm.bmBitsPixel ;
}
/*----------------------------------------------------------------------------
DibRowLength:  	Returns the number of bytes per row of pixels
-----------------------------------------------------------------------------*/
int DibRowLength (HDIB hdib)
{
if (!DibIsValid (hdib))
return 0 ;
return 4 * ((DibWidth (hdib) * DibBitCount (hdib) + 31) / 32) ;
}
/*---------------------------------------------------------------------------
DibNumColors:  	Returns the number of colors in the color table
----------------------------------------------------------------------------*/
int DibNumColors (HDIB hdib)
{
PDIBSTRUCT pdib = hdib ;
if (!DibIsValid (hdib))
return 0 ;
if (pdib->ds.dsBmih.biClrUsed != 0)
{
return pdib->ds.dsBmih.biClrUsed ;
}
else if (DibBitCount (hdib) <= 8)
{
return 1 << DibBitCount (hdib) ;
}
return 0 ;
}
/*---------------------------------------------------------------------------
DibMask:  Returns one of the color masks
---------------------------------------------------------------------------*/
DWORD 	DibMask (HDIB hdib, int i)
{
PDIBSTRUCT pdib = hdib ;
if (!DibIsValid (hdib) || i < 0 || i > 2)
return 0 ;
return pdib->ds.dsBitfields[i] ;
}
/*----------------------------------------------------------------------------
DibRShift:  Returns one of the right-shift values
-----------------------------------------------------------------------------*/
int 	DibRShift (HDIB hdib, int i)
{
PDIBSTRUCT pdib = hdib ;
if (!DibIsValid (hdib) || i < 0 || i > 2)
return 0 ;
return pdib->iRShift[i] ;
}
/*----------------------------------------------------------------------------
DibLShift:  Returns one of the left-shift values
----------------------------------------------------------------------------*/
int DibLShift (HDIB hdib, int i)
{
PDIBSTRUCT pdib = hdib ;
if (!DibIsValid (hdib) || i < 0 || i > 2)
return 0 ;
return pdib->iLShift[i] ;
}
/*---------------------------------------------------------------------------
DibCompression:  Returns the value of the biCompression field
----------------------------------------------------------------------------*/
int DibCompression (HDIB hdib)
{
if (!DibIsValid (hdib))
return 0 ;
return ((PDIBSTRUCT) hdib)->ds.dsBmih.biCompression ;
}
/*---------------------------------------------------------------------------
DibIsAddressable:  Returns TRUE if the DIB is not compressed
----------------------------------------------------------------------------*/
BOOL 	DibIsAddressable (HDIB hdib)
{
int iCompression ;
if (!DibIsValid (hdib))
return FALSE ;
iCompression = DibCompression (hdib) ;
if (	iCompression == BI_RGB || iCompression == BI_BITFIELDS)
return TRUE ;
return FALSE ;
}
/*---------------------------------------------------------------------------
These functions return the sizes of various components of the DIB section
AS THEY WOULD APPEAR in a packed DIB. These functions aid in converting
the DIB section to a packed DIB and in saving DIB files.
-----------------------------------------------------------------------------*/
DWORD DibInfoHeaderSize (HDIB hdib)
{
if (!DibIsValid (hdib))
return 0 ;
return ((PDIBSTRUCT) hdib)->ds.dsBmih.biSize ;
}
DWORD 	DibMaskSize (HDIB hdib)
{
PDIBSTRUCT pdib = hdib ;
if (!DibIsValid (hdib))
return 0 ;
if (pdib->ds.dsBmih.biCompression == BI_BITFIELDS)
return 3 * sizeof (DWORD) ;
return 0 ;
}
DWORD DibColorSize (HDIB hdib)
{
return DibNumColors (hdib) * sizeof (RGBQUAD) ;
}
DWORD DibInfoSize (HDIB hdib)
{
return DibInfoHeaderSize(hdib) + DibMaskSize(hdib) + DibColorSize(hdib) ;
}
DWORD DibBitsSize (HDIB hdib)
{
PDIBSTRUCT pdib = hdib ;
if (!DibIsValid (hdib))
return 0 ;
if (pdib->ds.dsBmih.biSizeImage != 0)
{
return pdib->ds.dsBmih.biSizeImage ;
}
return DibHeight (hdib) * DibRowLength (hdib) ;
}
DWORD DibTotalSize (HDIB hdib)
{
return DibInfoSize (hdib) + DibBitsSize (hdib) ;
}
/*---------------------------------------------------------------------------
These functions return pointers to the various components of the DIB
section.
-----------------------------------------------------------------------------*/
BITMAPINFOHEADER * DibInfoHeaderPtr (HDIB hdib)
{
if (!DibIsValid (hdib))
return NULL ;
return & (((PDIBSTRUCT) hdib)->ds.dsBmih) ;
}
DWORD * DibMaskPtr (HDIB hdib)
{
PDIBSTRUCT pdib = hdib ;
if (!DibIsValid (hdib))
return 0 ;
return pdib->ds.dsBitfields ;
}
void * DibBitsPtr (HDIB hdib)
{
if (!DibIsValid (hdib))
return NULL ;
return ((PDIBSTRUCT) hdib)->pBits ;
}
/*---------------------------------------------------------------------------
DibSetColor:  Obtains entry from the DIB color table
-----------------------------------------------------------------------------*/
BOOL DibGetColor (HDIB hdib, int index, RGBQUAD * prgb)
{
PDIBSTRUCT pdib = hdib ;
HDC        				hdcMem ;
int        				iReturn ;
if (!DibIsValid (hdib))
return 0 ;
hdcMem = CreateCompatibleDC (NULL) ;
SelectObject (hdcMem, pdib->hBitmap) ;
iReturn = GetDIBColorTable (hdcMem, index, 1, prgb) ;
DeleteDC (hdcMem) ;
return iReturn ? TRUE : FALSE ;
}
/*----------------------------------------------------------------------------
DibGetColor:  Sets an entry in the DIB color table
----------------------------------------------------------------------------*/
BOOL DibSetColor (HDIB hdib, int index, RGBQUAD * prgb)
{
PDIBSTRUCT 	pdib = hdib ;
HDC        			hdcMem ;
int        			iReturn ;
if (!DibIsValid (hdib))
return 0 ;
hdcMem = CreateCompatibleDC (NULL) ;
SelectObject (hdcMem, pdib->hBitmap) ;
iReturn = SetDIBColorTable (hdcMem, index, 1, prgb) ;
DeleteDC (hdcMem) ;
return iReturn ? TRUE : FALSE ;
}

DIBHELP.C中的大部分函式是不用解釋的。DibIsValid函式能有助於保護整個系統(tǒng),。在試圖引用DIBSTRUCT中的資訊之前,,其他函式都呼叫DibIsValid。所有這些函式都有(而且通常是只有)HDIB型態(tài)的第一個參數(shù),,( 我們將立即看到)該參數(shù)在DIBHELP.H中定義為空指標,。這些函式可以將此參數(shù)儲存到PDIBSTRUCT,然後再存取結(jié)構(gòu)中的欄位,。

注意傳回BOOL值的DibIsAddressable函式,。DibIsNotCompressed函式也可以呼叫此函式。傳回值表示獨立的DIB圖素能否定址,。

以DibInfoHeaderSize開始的函式集將取得DIB區(qū)塊中不同元件出現(xiàn)在packed DIB中的大小,。與我們所看到的一樣,,這些函式有助於將DIB區(qū)塊轉(zhuǎn)換成packed DIB,,並儲存DIB檔案。這些函式的後面是獲得指向不同DIB元件的指標的函式集,。

儘管DIBHELP.C包括名稱為DibInfoHeaderPtr的函式,,而且該函式將獲得指向BITMAPINFOHEADER結(jié)構(gòu)的指標,但還是沒有函式可以獲得BITMAPINFO結(jié)構(gòu)指標-即接在DIB顏色表後面的資訊結(jié)構(gòu),。這是因為在處理DIB區(qū)塊時,,應(yīng)用程式並不直接存取這種型態(tài)的結(jié)構(gòu)。BITMAPINFOHEADER結(jié)構(gòu)和顏色遮罩都在DIBSECTION結(jié)構(gòu)中有效,,而且從CreateDIBSection函式傳回指向圖素位元的指標,,這時通過呼叫GetDIBColorTable和SetDIBColorTable,,就只能間接存取DIB顏色表。這些功能都封裝到DIBHELP的DibGetColor和DibSetColor函式裡頭了,。

在DIBHELP.C的後面,,檔案DibCopyToInfo配置一個指向BITMAPINFO結(jié)構(gòu)的指標,並填充資訊,,但是那與獲得指向記憶體中現(xiàn)存結(jié)構(gòu)的指標不完全相同,。

    本站是提供個人知識管理的網(wǎng)絡(luò)存儲空間,所有內(nèi)容均由用戶發(fā)布,,不代表本站觀點,。請注意甄別內(nèi)容中的聯(lián)系方式、誘導(dǎo)購買等信息,,謹防詐騙,。如發(fā)現(xiàn)有害或侵權(quán)內(nèi)容,請點擊一鍵舉報,。
    轉(zhuǎn)藏 分享 獻花(0

    0條評論

    發(fā)表

    請遵守用戶 評論公約

    類似文章 更多