gdi32: Simplify computation of the DIB header size for internal BITMAPINFO structures.
This commit is contained in:
parent
82e1a4616c
commit
8db263d2eb
|
@ -83,7 +83,7 @@ static BOOL store_bitmap_bits( BRUSHOBJ *brush, BITMAPOBJ *bmp )
|
||||||
|
|
||||||
/* release the unneeded space */
|
/* release the unneeded space */
|
||||||
HeapReAlloc( GetProcessHeap(), HEAP_REALLOC_IN_PLACE_ONLY, info,
|
HeapReAlloc( GetProcessHeap(), HEAP_REALLOC_IN_PLACE_ONLY, info,
|
||||||
bitmap_info_size( info, DIB_RGB_COLORS ));
|
get_dib_info_size( info, DIB_RGB_COLORS ));
|
||||||
brush->info = info;
|
brush->info = info;
|
||||||
brush->bits = bits;
|
brush->bits = bits;
|
||||||
brush->usage = DIB_RGB_COLORS;
|
brush->usage = DIB_RGB_COLORS;
|
||||||
|
@ -119,7 +119,7 @@ static BOOL copy_bitmap( BRUSHOBJ *brush, HBITMAP bitmap )
|
||||||
}
|
}
|
||||||
|
|
||||||
info = HeapAlloc( GetProcessHeap(), 0,
|
info = HeapAlloc( GetProcessHeap(), 0,
|
||||||
bitmap_info_size( (BITMAPINFO *)&bmp->dib->dsBmih, DIB_RGB_COLORS ));
|
get_dib_info_size( (BITMAPINFO *)&bmp->dib->dsBmih, DIB_RGB_COLORS ));
|
||||||
if (!info) goto done;
|
if (!info) goto done;
|
||||||
info->bmiHeader = bmp->dib->dsBmih;
|
info->bmiHeader = bmp->dib->dsBmih;
|
||||||
if (info->bmiHeader.biCompression == BI_BITFIELDS)
|
if (info->bmiHeader.biCompression == BI_BITFIELDS)
|
||||||
|
@ -161,7 +161,7 @@ BOOL get_brush_bitmap_info( HBRUSH handle, BITMAPINFO *info, void **bits, UINT *
|
||||||
}
|
}
|
||||||
if (brush->info)
|
if (brush->info)
|
||||||
{
|
{
|
||||||
memcpy( info, brush->info, bitmap_info_size( brush->info, brush->usage ));
|
memcpy( info, brush->info, get_dib_info_size( brush->info, brush->usage ));
|
||||||
*bits = brush->bits.ptr;
|
*bits = brush->bits.ptr;
|
||||||
*usage = brush->usage;
|
*usage = brush->usage;
|
||||||
ret = TRUE;
|
ret = TRUE;
|
||||||
|
@ -224,7 +224,7 @@ HBRUSH WINAPI CreateBrushIndirect( const LOGBRUSH * brush )
|
||||||
ptr->info = copy_packed_dib( (BITMAPINFO *)ptr->logbrush.lbHatch, ptr->usage );
|
ptr->info = copy_packed_dib( (BITMAPINFO *)ptr->logbrush.lbHatch, ptr->usage );
|
||||||
if (hmem) GlobalUnlock( hmem );
|
if (hmem) GlobalUnlock( hmem );
|
||||||
if (!ptr->info) goto error;
|
if (!ptr->info) goto error;
|
||||||
ptr->bits.ptr = (char *)ptr->info + bitmap_info_size( ptr->info, ptr->usage );
|
ptr->bits.ptr = (char *)ptr->info + get_dib_info_size( ptr->info, ptr->usage );
|
||||||
ptr->logbrush.lbStyle = BS_DIBPATTERN;
|
ptr->logbrush.lbStyle = BS_DIBPATTERN;
|
||||||
ptr->logbrush.lbColor = 0;
|
ptr->logbrush.lbColor = 0;
|
||||||
break;
|
break;
|
||||||
|
|
|
@ -168,6 +168,12 @@ static BOOL bitmapinfoheader_from_user_bitmapinfo( BITMAPINFOHEADER *dst, const
|
||||||
|
|
||||||
/*******************************************************************************************
|
/*******************************************************************************************
|
||||||
* Fill out a true BITMAPINFO from a variable sized BITMAPINFO / BITMAPCOREINFO.
|
* Fill out a true BITMAPINFO from a variable sized BITMAPINFO / BITMAPCOREINFO.
|
||||||
|
*
|
||||||
|
* The resulting stanitized BITMAPINFO is guaranteed to have:
|
||||||
|
* - biSize set to sizeof(BITMAPINFOHEADER)
|
||||||
|
* - biSizeImage set to the actual image size even for non-compressed DIB
|
||||||
|
* - biClrUsed set to the size of the color table, and 0 only when there is no color table
|
||||||
|
* - color table present only for <= 8 bpp, always starts at info->bmiColors
|
||||||
*/
|
*/
|
||||||
static BOOL bitmapinfo_from_user_bitmapinfo( BITMAPINFO *dst, const BITMAPINFO *info,
|
static BOOL bitmapinfo_from_user_bitmapinfo( BITMAPINFO *dst, const BITMAPINFO *info,
|
||||||
UINT coloruse, BOOL allow_compression )
|
UINT coloruse, BOOL allow_compression )
|
||||||
|
@ -1122,16 +1128,16 @@ BITMAPINFO *copy_packed_dib( const BITMAPINFO *src_info, UINT usage )
|
||||||
{
|
{
|
||||||
char buffer[FIELD_OFFSET( BITMAPINFO, bmiColors[256] )];
|
char buffer[FIELD_OFFSET( BITMAPINFO, bmiColors[256] )];
|
||||||
BITMAPINFO *ret, *info = (BITMAPINFO *)buffer;
|
BITMAPINFO *ret, *info = (BITMAPINFO *)buffer;
|
||||||
int info_size, image_size;
|
unsigned int info_size;
|
||||||
|
|
||||||
if (!bitmapinfo_from_user_bitmapinfo( info, src_info, usage, FALSE )) return NULL;
|
if (!bitmapinfo_from_user_bitmapinfo( info, src_info, usage, FALSE )) return NULL;
|
||||||
|
|
||||||
info_size = bitmap_info_size( info, usage );
|
info_size = get_dib_info_size( info, usage );
|
||||||
image_size = get_dib_image_size( info );
|
if ((ret = HeapAlloc( GetProcessHeap(), 0, info_size + info->bmiHeader.biSizeImage )))
|
||||||
if ((ret = HeapAlloc( GetProcessHeap(), 0, info_size + image_size )))
|
|
||||||
{
|
{
|
||||||
memcpy( ret, info, info_size );
|
memcpy( ret, info, info_size );
|
||||||
memcpy( (char *)ret + info_size, (char *)src_info + bitmap_info_size(src_info,usage), image_size );
|
memcpy( (char *)ret + info_size, (char *)src_info + bitmap_info_size( src_info, usage ),
|
||||||
|
info->bmiHeader.biSizeImage );
|
||||||
}
|
}
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
|
@ -178,7 +178,7 @@ INT EMFDRV_StretchDIBits( PHYSDEV dev, INT xDst, INT yDst, INT widthDst, INT hei
|
||||||
UINT bmi_size, emr_size;
|
UINT bmi_size, emr_size;
|
||||||
|
|
||||||
/* calculate the size of the colour table */
|
/* calculate the size of the colour table */
|
||||||
bmi_size = bitmap_info_size(info, wUsage);
|
bmi_size = get_dib_info_size(info, wUsage);
|
||||||
|
|
||||||
emr_size = sizeof (EMRSTRETCHDIBITS) + bmi_size + info->bmiHeader.biSizeImage;
|
emr_size = sizeof (EMRSTRETCHDIBITS) + bmi_size + info->bmiHeader.biSizeImage;
|
||||||
emr = HeapAlloc(GetProcessHeap(), 0, emr_size );
|
emr = HeapAlloc(GetProcessHeap(), 0, emr_size );
|
||||||
|
@ -231,7 +231,7 @@ INT EMFDRV_SetDIBitsToDevice( PHYSDEV dev, INT xDst, INT yDst, DWORD width, DWOR
|
||||||
LPCVOID bits, BITMAPINFO *info, UINT wUsage )
|
LPCVOID bits, BITMAPINFO *info, UINT wUsage )
|
||||||
{
|
{
|
||||||
EMRSETDIBITSTODEVICE* pEMR;
|
EMRSETDIBITSTODEVICE* pEMR;
|
||||||
DWORD bmiSize = bitmap_info_size(info, wUsage);
|
DWORD bmiSize = get_dib_info_size(info, wUsage);
|
||||||
DWORD size = sizeof(EMRSETDIBITSTODEVICE) + bmiSize + info->bmiHeader.biSizeImage;
|
DWORD size = sizeof(EMRSETDIBITSTODEVICE) + bmiSize + info->bmiHeader.biSizeImage;
|
||||||
|
|
||||||
pEMR = HeapAlloc(GetProcessHeap(), 0, size);
|
pEMR = HeapAlloc(GetProcessHeap(), 0, size);
|
||||||
|
|
|
@ -138,15 +138,15 @@ DWORD EMFDRV_CreateBrushIndirect( PHYSDEV dev, HBRUSH hBrush )
|
||||||
EMRCREATEDIBPATTERNBRUSHPT *emr;
|
EMRCREATEDIBPATTERNBRUSHPT *emr;
|
||||||
char buffer[FIELD_OFFSET( BITMAPINFO, bmiColors[256] )];
|
char buffer[FIELD_OFFSET( BITMAPINFO, bmiColors[256] )];
|
||||||
BITMAPINFO *info = (BITMAPINFO *)buffer;
|
BITMAPINFO *info = (BITMAPINFO *)buffer;
|
||||||
DWORD info_size, image_size;
|
DWORD info_size;
|
||||||
void *bits;
|
void *bits;
|
||||||
UINT usage;
|
UINT usage;
|
||||||
|
|
||||||
if (!get_brush_bitmap_info( hBrush, info, &bits, &usage )) break;
|
if (!get_brush_bitmap_info( hBrush, info, &bits, &usage )) break;
|
||||||
info_size = bitmap_info_size( info, usage );
|
info_size = get_dib_info_size( info, usage );
|
||||||
image_size = get_dib_image_size( info );
|
|
||||||
|
|
||||||
emr = HeapAlloc( GetProcessHeap(), 0, sizeof(EMRCREATEDIBPATTERNBRUSHPT)+info_size+image_size );
|
emr = HeapAlloc( GetProcessHeap(), 0,
|
||||||
|
sizeof(EMRCREATEDIBPATTERNBRUSHPT)+info_size+info->bmiHeader.biSizeImage );
|
||||||
if(!emr) break;
|
if(!emr) break;
|
||||||
|
|
||||||
if (logbrush.lbStyle == BS_PATTERN && info->bmiHeader.biBitCount == 1)
|
if (logbrush.lbStyle == BS_PATTERN && info->bmiHeader.biBitCount == 1)
|
||||||
|
@ -176,7 +176,7 @@ DWORD EMFDRV_CreateBrushIndirect( PHYSDEV dev, HBRUSH hBrush )
|
||||||
emr->ihBrush = index = EMFDRV_AddHandle( dev, hBrush );
|
emr->ihBrush = index = EMFDRV_AddHandle( dev, hBrush );
|
||||||
emr->iUsage = usage;
|
emr->iUsage = usage;
|
||||||
emr->offBits = emr->offBmi + emr->cbBmi;
|
emr->offBits = emr->offBmi + emr->cbBmi;
|
||||||
emr->cbBits = image_size;
|
emr->cbBits = info->bmiHeader.biSizeImage;
|
||||||
|
|
||||||
memcpy( (BYTE *)emr + emr->offBmi, info, emr->cbBmi );
|
memcpy( (BYTE *)emr + emr->offBmi, info, emr->cbBmi );
|
||||||
memcpy( (BYTE *)emr + emr->offBits, bits, emr->cbBits );
|
memcpy( (BYTE *)emr + emr->offBits, bits, emr->cbBits );
|
||||||
|
|
|
@ -469,11 +469,20 @@ static inline int get_dib_image_size( const BITMAPINFO *info )
|
||||||
* abs( info->bmiHeader.biHeight );
|
* abs( info->bmiHeader.biHeight );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* only for use on sanitized BITMAPINFO structures */
|
||||||
|
static inline int get_dib_info_size( const BITMAPINFO *info, UINT coloruse )
|
||||||
|
{
|
||||||
|
if (info->bmiHeader.biCompression == BI_BITFIELDS)
|
||||||
|
return sizeof(BITMAPINFOHEADER) + 3 * sizeof(DWORD);
|
||||||
|
if (coloruse == DIB_PAL_COLORS)
|
||||||
|
return sizeof(BITMAPINFOHEADER) + info->bmiHeader.biClrUsed * sizeof(WORD);
|
||||||
|
return FIELD_OFFSET( BITMAPINFO, bmiColors[info->bmiHeader.biClrUsed] );
|
||||||
|
}
|
||||||
|
|
||||||
|
/* only for use on sanitized BITMAPINFO structures */
|
||||||
static inline void copy_bitmapinfo( BITMAPINFO *dst, const BITMAPINFO *src )
|
static inline void copy_bitmapinfo( BITMAPINFO *dst, const BITMAPINFO *src )
|
||||||
{
|
{
|
||||||
unsigned int size = FIELD_OFFSET( BITMAPINFO, bmiColors[src->bmiHeader.biClrUsed] );
|
memcpy( dst, src, get_dib_info_size( src, DIB_RGB_COLORS ));
|
||||||
if (src->bmiHeader.biCompression == BI_BITFIELDS) size += 3 * sizeof(DWORD);
|
|
||||||
memcpy( dst, src, size );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline const struct gdi_dc_funcs *get_bitmap_funcs( const BITMAPOBJ *bitmap )
|
static inline const struct gdi_dc_funcs *get_bitmap_funcs( const BITMAPOBJ *bitmap )
|
||||||
|
|
|
@ -90,8 +90,7 @@ BOOL MFDRV_StretchBlt( PHYSDEV devDst, struct bitblt_coords *dst,
|
||||||
len,rop,lpBMI->biYPelsPerMeter,GetDeviceCaps(devSrc->hdc, LOGPIXELSY));
|
len,rop,lpBMI->biYPelsPerMeter,GetDeviceCaps(devSrc->hdc, LOGPIXELSY));
|
||||||
|
|
||||||
if (GetDIBits(devSrc->hdc, hBitmap, 0, (UINT)lpBMI->biHeight,
|
if (GetDIBits(devSrc->hdc, hBitmap, 0, (UINT)lpBMI->biHeight,
|
||||||
(LPSTR)lpBMI + bitmap_info_size( (BITMAPINFO *)lpBMI,
|
(LPSTR)lpBMI + get_dib_info_size( (BITMAPINFO *)lpBMI, DIB_RGB_COLORS ),
|
||||||
DIB_RGB_COLORS ),
|
|
||||||
(LPBITMAPINFO)lpBMI, DIB_RGB_COLORS))
|
(LPBITMAPINFO)lpBMI, DIB_RGB_COLORS))
|
||||||
#else
|
#else
|
||||||
len = sizeof(METARECORD) + 15 * sizeof(INT16) + BM.bmWidthBytes * BM.bmHeight;
|
len = sizeof(METARECORD) + 15 * sizeof(INT16) + BM.bmWidthBytes * BM.bmHeight;
|
||||||
|
@ -135,7 +134,7 @@ INT MFDRV_StretchDIBits( PHYSDEV dev, INT xDst, INT yDst, INT widthDst,
|
||||||
INT heightSrc, const void *bits,
|
INT heightSrc, const void *bits,
|
||||||
BITMAPINFO *info, UINT wUsage, DWORD dwRop )
|
BITMAPINFO *info, UINT wUsage, DWORD dwRop )
|
||||||
{
|
{
|
||||||
DWORD infosize = bitmap_info_size(info, wUsage);
|
DWORD infosize = get_dib_info_size(info, wUsage);
|
||||||
DWORD len = sizeof(METARECORD) + 10 * sizeof(WORD) + infosize + info->bmiHeader.biSizeImage;
|
DWORD len = sizeof(METARECORD) + 10 * sizeof(WORD) + infosize + info->bmiHeader.biSizeImage;
|
||||||
METARECORD *mr = HeapAlloc( GetProcessHeap(), 0, len );
|
METARECORD *mr = HeapAlloc( GetProcessHeap(), 0, len );
|
||||||
if(!mr) return 0;
|
if(!mr) return 0;
|
||||||
|
@ -169,7 +168,7 @@ INT MFDRV_SetDIBitsToDevice( PHYSDEV dev, INT xDst, INT yDst, DWORD cx,
|
||||||
UINT lines, LPCVOID bits, BITMAPINFO *info, UINT coloruse )
|
UINT lines, LPCVOID bits, BITMAPINFO *info, UINT coloruse )
|
||||||
|
|
||||||
{
|
{
|
||||||
DWORD infosize = bitmap_info_size(info, coloruse);
|
DWORD infosize = get_dib_info_size(info, coloruse);
|
||||||
DWORD len = sizeof(METARECORD) + 8 * sizeof(WORD) + infosize + info->bmiHeader.biSizeImage;
|
DWORD len = sizeof(METARECORD) + 8 * sizeof(WORD) + infosize + info->bmiHeader.biSizeImage;
|
||||||
METARECORD *mr = HeapAlloc( GetProcessHeap(), 0, len );
|
METARECORD *mr = HeapAlloc( GetProcessHeap(), 0, len );
|
||||||
if(!mr) return 0;
|
if(!mr) return 0;
|
||||||
|
|
|
@ -178,16 +178,15 @@ INT16 MFDRV_CreateBrushIndirect(PHYSDEV dev, HBRUSH hBrush )
|
||||||
{
|
{
|
||||||
char buffer[FIELD_OFFSET( BITMAPINFO, bmiColors[256] )];
|
char buffer[FIELD_OFFSET( BITMAPINFO, bmiColors[256] )];
|
||||||
BITMAPINFO *dst_info, *src_info = (BITMAPINFO *)buffer;
|
BITMAPINFO *dst_info, *src_info = (BITMAPINFO *)buffer;
|
||||||
DWORD info_size, image_size;
|
DWORD info_size;
|
||||||
char *dst_ptr;
|
char *dst_ptr;
|
||||||
void *bits;
|
void *bits;
|
||||||
UINT usage;
|
UINT usage;
|
||||||
|
|
||||||
if (!get_brush_bitmap_info( hBrush, src_info, &bits, &usage )) goto done;
|
if (!get_brush_bitmap_info( hBrush, src_info, &bits, &usage )) goto done;
|
||||||
|
|
||||||
info_size = bitmap_info_size( src_info, usage );
|
info_size = get_dib_info_size( src_info, usage );
|
||||||
image_size = get_dib_image_size( src_info );
|
size = FIELD_OFFSET( METARECORD, rdParm[2] ) + info_size + src_info->bmiHeader.biSizeImage;
|
||||||
size = FIELD_OFFSET( METARECORD, rdParm[2] ) + info_size + image_size;
|
|
||||||
|
|
||||||
if (!(mr = HeapAlloc( GetProcessHeap(), 0, size ))) goto done;
|
if (!(mr = HeapAlloc( GetProcessHeap(), 0, size ))) goto done;
|
||||||
mr->rdFunction = META_DIBCREATEPATTERNBRUSH;
|
mr->rdFunction = META_DIBCREATEPATTERNBRUSH;
|
||||||
|
@ -210,7 +209,7 @@ INT16 MFDRV_CreateBrushIndirect(PHYSDEV dev, HBRUSH hBrush )
|
||||||
for (i = 0; i < dst_info->bmiHeader.biHeight; i++, dst_ptr -= width_bytes)
|
for (i = 0; i < dst_info->bmiHeader.biHeight; i++, dst_ptr -= width_bytes)
|
||||||
memcpy( dst_ptr, (char *)bits + i * width_bytes, width_bytes );
|
memcpy( dst_ptr, (char *)bits + i * width_bytes, width_bytes );
|
||||||
}
|
}
|
||||||
else memcpy( dst_ptr, bits, image_size );
|
else memcpy( dst_ptr, bits, src_info->bmiHeader.biSizeImage );
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue