gdi32: Always use the DIB engine for DDB rendering.
This commit is contained in:
parent
77ee0b56bb
commit
592bfd52c9
|
@ -230,7 +230,7 @@ HBITMAP WINAPI CreateBitmapIndirect( const BITMAP *bmp )
|
||||||
|
|
||||||
bmpobj->dib.dsBm = bm;
|
bmpobj->dib.dsBm = bm;
|
||||||
bmpobj->dib.dsBm.bmBits = NULL;
|
bmpobj->dib.dsBm.bmBits = NULL;
|
||||||
bmpobj->funcs = &null_driver;
|
bmpobj->funcs = &dib_driver;
|
||||||
|
|
||||||
if (!(hbitmap = alloc_gdi_handle( &bmpobj->header, OBJ_BITMAP, &bitmap_funcs )))
|
if (!(hbitmap = alloc_gdi_handle( &bmpobj->header, OBJ_BITMAP, &bitmap_funcs )))
|
||||||
{
|
{
|
||||||
|
@ -431,48 +431,6 @@ LONG WINAPI SetBitmapBits(
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static void set_initial_bitmap_bits( HBITMAP hbitmap, BITMAPOBJ *bmp )
|
|
||||||
{
|
|
||||||
char src_bmibuf[FIELD_OFFSET( BITMAPINFO, bmiColors[256] )];
|
|
||||||
BITMAPINFO *src_info = (BITMAPINFO *)src_bmibuf;
|
|
||||||
char dst_bmibuf[FIELD_OFFSET( BITMAPINFO, bmiColors[256] )];
|
|
||||||
BITMAPINFO *dst_info = (BITMAPINFO *)dst_bmibuf;
|
|
||||||
DWORD err;
|
|
||||||
struct gdi_image_bits bits;
|
|
||||||
struct bitblt_coords src, dst;
|
|
||||||
|
|
||||||
if (!bmp->dib.dsBm.bmBits) return;
|
|
||||||
if (bmp->funcs->pPutImage == nulldrv_PutImage) return;
|
|
||||||
|
|
||||||
get_ddb_bitmapinfo( bmp, src_info );
|
|
||||||
|
|
||||||
bits.ptr = bmp->dib.dsBm.bmBits;
|
|
||||||
bits.is_copy = FALSE;
|
|
||||||
bits.free = NULL;
|
|
||||||
bits.param = NULL;
|
|
||||||
|
|
||||||
src.x = 0;
|
|
||||||
src.y = 0;
|
|
||||||
src.width = bmp->dib.dsBm.bmWidth;
|
|
||||||
src.height = bmp->dib.dsBm.bmHeight;
|
|
||||||
src.visrect.left = 0;
|
|
||||||
src.visrect.top = 0;
|
|
||||||
src.visrect.right = bmp->dib.dsBm.bmWidth;
|
|
||||||
src.visrect.bottom = bmp->dib.dsBm.bmHeight;
|
|
||||||
dst = src;
|
|
||||||
|
|
||||||
copy_bitmapinfo( dst_info, src_info );
|
|
||||||
|
|
||||||
err = bmp->funcs->pPutImage( NULL, hbitmap, 0, dst_info, &bits, &src, &dst, 0 );
|
|
||||||
if (err == ERROR_BAD_FORMAT)
|
|
||||||
{
|
|
||||||
err = convert_bits( src_info, &src, dst_info, &bits, FALSE );
|
|
||||||
if (!err) err = bmp->funcs->pPutImage( NULL, hbitmap, 0, dst_info, &bits, &src, &dst, 0 );
|
|
||||||
if (bits.free) bits.free( &bits );
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/***********************************************************************
|
/***********************************************************************
|
||||||
* BITMAP_SelectObject
|
* BITMAP_SelectObject
|
||||||
*/
|
*/
|
||||||
|
@ -481,7 +439,7 @@ static HGDIOBJ BITMAP_SelectObject( HGDIOBJ handle, HDC hdc )
|
||||||
HGDIOBJ ret;
|
HGDIOBJ ret;
|
||||||
BITMAPOBJ *bitmap;
|
BITMAPOBJ *bitmap;
|
||||||
DC *dc;
|
DC *dc;
|
||||||
PHYSDEV physdev = NULL, old_physdev = NULL, createdev;
|
PHYSDEV physdev;
|
||||||
|
|
||||||
if (!(dc = get_dc_ptr( hdc ))) return 0;
|
if (!(dc = get_dc_ptr( hdc ))) return 0;
|
||||||
|
|
||||||
|
@ -516,51 +474,7 @@ static HGDIOBJ BITMAP_SelectObject( HGDIOBJ handle, HDC hdc )
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (dc->dibdrv) old_physdev = pop_dc_driver( dc, dc->dibdrv );
|
physdev = GET_DC_PHYSDEV( dc, pSelectBitmap );
|
||||||
|
|
||||||
if (bitmap->dib.dsBm.bmBitsPixel > 1)
|
|
||||||
{
|
|
||||||
physdev = GET_DC_PHYSDEV( dc, pSelectBitmap );
|
|
||||||
createdev = GET_DC_PHYSDEV( dc, pCreateBitmap );
|
|
||||||
}
|
|
||||||
else physdev = createdev = &dc->nulldrv; /* force use of the DIB engine for 1-bpp */
|
|
||||||
|
|
||||||
if (physdev->funcs == &null_driver)
|
|
||||||
{
|
|
||||||
physdev = dc->dibdrv;
|
|
||||||
if (physdev) push_dc_driver( &dc->physDev, physdev, physdev->funcs );
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (!dib_driver.pCreateDC( &dc->physDev, NULL, NULL, NULL, NULL )) goto done;
|
|
||||||
dc->dibdrv = physdev = dc->physDev;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* never set the owner of the stock bitmap since it can be selected in multiple DCs */
|
|
||||||
if (handle != GetStockObject(DEFAULT_BITMAP) && bitmap->funcs != createdev->funcs)
|
|
||||||
{
|
|
||||||
/* we can only change from the null driver to some other driver */
|
|
||||||
if (bitmap->funcs != &null_driver)
|
|
||||||
{
|
|
||||||
FIXME( "Trying to select bitmap %p in different DC type\n", handle );
|
|
||||||
GDI_ReleaseObj( handle );
|
|
||||||
ret = 0;
|
|
||||||
goto done;
|
|
||||||
}
|
|
||||||
if (createdev->funcs != &null_driver)
|
|
||||||
{
|
|
||||||
if (!createdev->funcs->pCreateBitmap( createdev, handle ))
|
|
||||||
{
|
|
||||||
GDI_ReleaseObj( handle );
|
|
||||||
ret = 0;
|
|
||||||
goto done;
|
|
||||||
}
|
|
||||||
bitmap->funcs = createdev->funcs;
|
|
||||||
set_initial_bitmap_bits( handle, bitmap );
|
|
||||||
}
|
|
||||||
else bitmap->funcs = &dib_driver; /* use the DIB driver to emulate DDB support */
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!physdev->funcs->pSelectBitmap( physdev, handle ))
|
if (!physdev->funcs->pSelectBitmap( physdev, handle ))
|
||||||
{
|
{
|
||||||
GDI_ReleaseObj( handle );
|
GDI_ReleaseObj( handle );
|
||||||
|
@ -582,11 +496,6 @@ static HGDIOBJ BITMAP_SelectObject( HGDIOBJ handle, HDC hdc )
|
||||||
}
|
}
|
||||||
|
|
||||||
done:
|
done:
|
||||||
if(!ret)
|
|
||||||
{
|
|
||||||
if (physdev && physdev == dc->dibdrv) pop_dc_driver( dc, dc->dibdrv );
|
|
||||||
if (old_physdev) push_dc_driver( &dc->physDev, old_physdev, old_physdev->funcs );
|
|
||||||
}
|
|
||||||
release_dc_ptr( dc );
|
release_dc_ptr( dc );
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
@ -597,17 +506,9 @@ static HGDIOBJ BITMAP_SelectObject( HGDIOBJ handle, HDC hdc )
|
||||||
*/
|
*/
|
||||||
static BOOL BITMAP_DeleteObject( HGDIOBJ handle )
|
static BOOL BITMAP_DeleteObject( HGDIOBJ handle )
|
||||||
{
|
{
|
||||||
const struct gdi_dc_funcs *funcs;
|
BITMAPOBJ *bmp = free_gdi_handle( handle );
|
||||||
BITMAPOBJ *bmp = GDI_GetObjPtr( handle, OBJ_BITMAP );
|
|
||||||
|
|
||||||
if (!bmp) return FALSE;
|
if (!bmp) return FALSE;
|
||||||
funcs = bmp->funcs;
|
|
||||||
GDI_ReleaseObj( handle );
|
|
||||||
|
|
||||||
funcs->pDeleteBitmap( handle );
|
|
||||||
|
|
||||||
if (!(bmp = free_gdi_handle( handle ))) return FALSE;
|
|
||||||
|
|
||||||
HeapFree( GetProcessHeap(), 0, bmp->dib.dsBm.bmBits );
|
HeapFree( GetProcessHeap(), 0, bmp->dib.dsBm.bmBits );
|
||||||
return HeapFree( GetProcessHeap(), 0, bmp );
|
return HeapFree( GetProcessHeap(), 0, bmp );
|
||||||
}
|
}
|
||||||
|
|
|
@ -159,9 +159,7 @@ void free_dc_ptr( DC *dc )
|
||||||
PHYSDEV physdev = dc->physDev;
|
PHYSDEV physdev = dc->physDev;
|
||||||
dc->physDev = physdev->next;
|
dc->physDev = physdev->next;
|
||||||
physdev->funcs->pDeleteDC( physdev );
|
physdev->funcs->pDeleteDC( physdev );
|
||||||
if (physdev == dc->dibdrv) dc->dibdrv = NULL;
|
|
||||||
}
|
}
|
||||||
if (dc->dibdrv) dc->dibdrv->funcs->pDeleteDC( dc->dibdrv );
|
|
||||||
free_gdi_handle( dc->hSelf );
|
free_gdi_handle( dc->hSelf );
|
||||||
free_dc_state( dc );
|
free_dc_state( dc );
|
||||||
}
|
}
|
||||||
|
@ -709,6 +707,15 @@ HDC WINAPI CreateCompatibleDC( HDC hdc )
|
||||||
free_dc_ptr( dc );
|
free_dc_ptr( dc );
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!dib_driver.pCreateDC( &dc->physDev, NULL, NULL, NULL, NULL ))
|
||||||
|
{
|
||||||
|
free_dc_ptr( dc );
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
physDev = GET_DC_PHYSDEV( dc, pSelectBitmap );
|
||||||
|
physDev->funcs->pSelectBitmap( physDev, dc->hBitmap );
|
||||||
|
|
||||||
DC_InitDC( dc );
|
DC_InitDC( dc );
|
||||||
release_dc_ptr( dc );
|
release_dc_ptr( dc );
|
||||||
return ret;
|
return ret;
|
||||||
|
|
|
@ -1570,7 +1570,7 @@ static HGDIOBJ DIB_SelectObject( HGDIOBJ handle, HDC hdc )
|
||||||
HGDIOBJ ret;
|
HGDIOBJ ret;
|
||||||
BITMAPOBJ *bitmap;
|
BITMAPOBJ *bitmap;
|
||||||
DC *dc;
|
DC *dc;
|
||||||
PHYSDEV physdev = NULL, old_physdev = NULL;
|
PHYSDEV physdev;
|
||||||
|
|
||||||
if (!(dc = get_dc_ptr( hdc ))) return 0;
|
if (!(dc = get_dc_ptr( hdc ))) return 0;
|
||||||
|
|
||||||
|
@ -1596,18 +1596,7 @@ static HGDIOBJ DIB_SelectObject( HGDIOBJ handle, HDC hdc )
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
|
|
||||||
old_physdev = GET_DC_PHYSDEV( dc, pSelectBitmap );
|
physdev = GET_DC_PHYSDEV( dc, pSelectBitmap );
|
||||||
physdev = dc->dibdrv;
|
|
||||||
if (old_physdev != dc->dibdrv)
|
|
||||||
{
|
|
||||||
if (physdev) push_dc_driver( &dc->physDev, physdev, physdev->funcs );
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (!dib_driver.pCreateDC( &dc->physDev, NULL, NULL, NULL, NULL )) goto done;
|
|
||||||
dc->dibdrv = physdev = dc->physDev;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!physdev->funcs->pSelectBitmap( physdev, handle ))
|
if (!physdev->funcs->pSelectBitmap( physdev, handle ))
|
||||||
{
|
{
|
||||||
GDI_ReleaseObj( handle );
|
GDI_ReleaseObj( handle );
|
||||||
|
@ -1629,10 +1618,6 @@ static HGDIOBJ DIB_SelectObject( HGDIOBJ handle, HDC hdc )
|
||||||
}
|
}
|
||||||
|
|
||||||
done:
|
done:
|
||||||
if(!ret)
|
|
||||||
{
|
|
||||||
if (old_physdev && old_physdev != dc->dibdrv) pop_dc_driver( dc, dc->dibdrv );
|
|
||||||
}
|
|
||||||
release_dc_ptr( dc );
|
release_dc_ptr( dc );
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
|
@ -80,7 +80,6 @@ typedef struct tagDC
|
||||||
GDIOBJHDR header;
|
GDIOBJHDR header;
|
||||||
HDC hSelf; /* Handle to this DC */
|
HDC hSelf; /* Handle to this DC */
|
||||||
struct gdi_physdev nulldrv; /* physdev for the null driver */
|
struct gdi_physdev nulldrv; /* physdev for the null driver */
|
||||||
PHYSDEV dibdrv; /* physdev for the dib driver */
|
|
||||||
PHYSDEV physDev; /* current top of the physdev stack */
|
PHYSDEV physDev; /* current top of the physdev stack */
|
||||||
DWORD thread; /* thread owning the DC */
|
DWORD thread; /* thread owning the DC */
|
||||||
LONG refcount; /* thread refcount */
|
LONG refcount; /* thread refcount */
|
||||||
|
|
|
@ -3576,6 +3576,7 @@ static void test_GdiAlphaBlend(void)
|
||||||
SetViewportExtEx(hdcDst, -1, -1, NULL);
|
SetViewportExtEx(hdcDst, -1, -1, NULL);
|
||||||
SetLastError(0xdeadbeef);
|
SetLastError(0xdeadbeef);
|
||||||
ret = pGdiAlphaBlend(hdcDst, 0, 0, 20, 20, hdcSrc, 0, -1, 50, 50, blend);
|
ret = pGdiAlphaBlend(hdcDst, 0, 0, 20, 20, hdcSrc, 0, -1, 50, 50, blend);
|
||||||
|
todo_wine
|
||||||
ok( ret, "GdiAlphaBlend failed err %u\n", GetLastError() );
|
ok( ret, "GdiAlphaBlend failed err %u\n", GetLastError() );
|
||||||
SetLastError(0xdeadbeef);
|
SetLastError(0xdeadbeef);
|
||||||
ret = pGdiAlphaBlend(hdcDst, -20, -20, 20, 20, hdcSrc, 0, -1, 50, 50, blend);
|
ret = pGdiAlphaBlend(hdcDst, -20, -20, 20, 20, hdcSrc, 0, -1, 50, 50, blend);
|
||||||
|
|
Loading…
Reference in New Issue