Partly (not working) implementation of TransparentBlt()

svn path=/trunk/; revision=8912
This commit is contained in:
Thomas Bluemel 2004-03-28 21:46:26 +00:00
parent 50c2bd5cc2
commit 4309d1082e
6 changed files with 145 additions and 90 deletions

View file

@ -274,6 +274,7 @@ NtGdiStrokeAndFillPath 1
NtGdiStrokePath 1 NtGdiStrokePath 1
NtGdiSwapBuffers 1 NtGdiSwapBuffers 1
NtGdiTextOut 5 NtGdiTextOut 5
NtGdiTransparentBlt 11
NtGdiTranslateCharsetInfo 3 NtGdiTranslateCharsetInfo 3
NtGdiUnrealizeObject 2 NtGdiUnrealizeObject 2
NtGdiUpdateColors 1 NtGdiUpdateColors 1

View file

@ -304,5 +304,22 @@ NtGdiStretchDIBits (
UINT Usage, UINT Usage,
DWORD ROP DWORD ROP
); );
BOOL
STDCALL
NtGdiTransparentBlt(
HDC hdcDst,
INT xDst,
INT yDst,
INT cxDst,
INT cyDst,
HDC hdcSrc,
INT xSrc,
INT ySrc,
INT cxSrc,
INT cySrc,
COLORREF TransColor
);
#endif #endif

View file

@ -1,13 +1,10 @@
/* $Id: bitblt.c,v 1.19 2004/03/24 00:13:31 royce Exp $ /* $Id: bitblt.c,v 1.20 2004/03/28 21:46:26 weiden Exp $
* *
* COPYRIGHT: See COPYING in the top level directory * COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS system libraries * PROJECT: ReactOS system libraries
* FILE: lib/gdi32/object/bitblt.c * FILE: lib/gdi32/object/bitblt.c
* PURPOSE: * PURPOSE:
* PROGRAMMER: * PROGRAMMER:
*
* GdiTransparentBlt Copyright Kevin Koltzau
* adapted from WINE 2-13-04
*/ */
#ifdef UNICODE #ifdef UNICODE
@ -396,87 +393,12 @@ PolyPatBlt(HDC hDC,DWORD dwRop,PPATRECT pRects,int cRects,ULONG Reserved)
*/ */
WINBOOL WINBOOL
STDCALL STDCALL
GdiTransparentBlt( HDC hdcDst, int xDst, int yDst, int cxDst, int cyDst, GdiTransparentBlt(HDC hdcDst, int xDst, int yDst, int cxDst, int cyDst,
HDC hdcSrc, int xSrc, int ySrc, int cxSrc, int cySrc, HDC hdcSrc, int xSrc, int ySrc, int cxSrc, int cySrc,
COLORREF TransColor ) COLORREF TransColor)
{ {
BOOL ret = FALSE; return (WINBOOL)NtGdiTransparentBlt(hdcDst, xDst, yDst, cxDst, cyDst, hdcSrc,
HDC hdcWork; xSrc, ySrc, cxSrc, cySrc, TransColor);
HBITMAP bmpWork;
HGDIOBJ oldWork;
HDC hdcMask = NULL;
HBITMAP bmpMask = NULL;
HBITMAP oldMask = NULL;
COLORREF oldBackground;
COLORREF oldForeground;
int oldStretchMode;
if(cxDst < 0 || cyDst < 0 || cxSrc < 0 || cySrc < 0) {
DPRINT("Can not mirror\n");
return FALSE;
}
oldBackground = SetBkColor(hdcDst, RGB(255,255,255));
oldForeground = SetTextColor(hdcDst, RGB(0,0,0));
/* Stretch bitmap */
oldStretchMode = GetStretchBltMode(hdcSrc);
if(oldStretchMode == BLACKONWHITE || oldStretchMode == WHITEONBLACK)
SetStretchBltMode(hdcSrc, COLORONCOLOR);
hdcWork = CreateCompatibleDC(hdcDst);
bmpWork = CreateCompatibleBitmap(hdcDst, cxDst, cyDst);
oldWork = SelectObject(hdcWork, bmpWork);
if(!StretchBlt(hdcWork, 0, 0, cxDst, cyDst, hdcSrc, xSrc, ySrc, cxSrc, cySrc, SRCCOPY)) {
DPRINT("Failed to stretch\n");
goto error;
}
SetBkColor(hdcWork, TransColor);
/* Create mask */
hdcMask = CreateCompatibleDC(hdcDst);
bmpMask = CreateCompatibleBitmap(hdcMask, cxDst, cyDst);
oldMask = SelectObject(hdcMask, bmpMask);
if(!BitBlt(hdcMask, 0, 0, cxDst, cyDst, hdcWork, 0, 0, SRCCOPY)) {
DPRINT("Failed to create mask\n");
goto error;
}
/* Replace transparent color with black */
SetBkColor(hdcWork, RGB(0,0,0));
SetTextColor(hdcWork, RGB(255,255,255));
if(!BitBlt(hdcWork, 0, 0, cxDst, cyDst, hdcMask, 0, 0, SRCAND)) {
DPRINT("Failed to mask out background\n");
goto error;
}
/* Replace non-transparent area on destination with black */
if(!BitBlt(hdcDst, xDst, yDst, cxDst, cyDst, hdcMask, 0, 0, SRCAND)) {
DPRINT("Failed to clear destination area\n");
goto error;
}
/* Draw the image */
if(!BitBlt(hdcDst, xDst, yDst, cxDst, cyDst, hdcWork, 0, 0, SRCPAINT)) {
DPRINT("Failed to paint image\n");
goto error;
}
ret = TRUE;
error:
SetStretchBltMode(hdcSrc, oldStretchMode);
SetBkColor(hdcDst, oldBackground);
SetTextColor(hdcDst, oldForeground);
if(hdcWork) {
SelectObject(hdcWork, oldWork);
DeleteDC(hdcWork);
}
if(bmpWork) DeleteObject(bmpWork);
if(hdcMask) {
SelectObject(hdcMask, oldMask);
DeleteDC(hdcMask);
}
if(bmpMask) DeleteObject(bmpMask);
return ret;
} }
/* /*

View file

@ -16,7 +16,7 @@
* along with this program; if not, write to the Free Software * along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/ */
/* $Id: msgqueue.c,v 1.78 2004/03/28 16:21:58 weiden Exp $ /* $Id: msgqueue.c,v 1.79 2004/03/28 21:46:26 weiden Exp $
* *
* COPYRIGHT: See COPYING in the top level directory * COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS kernel * PROJECT: ReactOS kernel
@ -842,7 +842,7 @@ MsqDispatchOneSentMessage(PUSER_MESSAGE_QUEUE MessageQueue)
IntLockMessageQueue(MessageQueue); IntLockMessageQueue(MessageQueue);
if (IsListEmpty(&MessageQueue->SentMessagesListHead)) if (IsListEmpty(&MessageQueue->SentMessagesListHead))
{ {
ExReleaseFastMutex(&MessageQueue->Lock); IntUnLockMessageQueue(MessageQueue);
return(FALSE); return(FALSE);
} }
Entry = RemoveHeadList(&MessageQueue->SentMessagesListHead); Entry = RemoveHeadList(&MessageQueue->SentMessagesListHead);

View file

@ -16,7 +16,7 @@
* along with this program; if not, write to the Free Software * along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/ */
/* $Id: window.c,v 1.201 2004/03/23 21:47:37 weiden Exp $ /* $Id: window.c,v 1.202 2004/03/28 21:46:26 weiden Exp $
* *
* COPYRIGHT: See COPYING in the top level directory * COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS kernel * PROJECT: ReactOS kernel
@ -3410,7 +3410,6 @@ IntGetWindowRgn(HWND hWnd, HRGN hRgn)
if(!hRgn) if(!hRgn)
{ {
IntReleaseWindowObject(WindowObject); IntReleaseWindowObject(WindowObject);
SetLastWin32Error(ERROR_INVALID_PARAMETER);
return ERROR; return ERROR;
} }
@ -3453,7 +3452,6 @@ IntGetWindowRgnBox(HWND hWnd, RECT *Rect)
if(!Rect) if(!Rect)
{ {
IntReleaseWindowObject(WindowObject); IntReleaseWindowObject(WindowObject);
SetLastWin32Error(ERROR_INVALID_PARAMETER);
return ERROR; return ERROR;
} }

View file

@ -16,7 +16,7 @@
* along with this program; if not, write to the Free Software * along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/ */
/* $Id: bitmaps.c,v 1.64 2004/03/22 20:46:33 royce Exp $ */ /* $Id: bitmaps.c,v 1.65 2004/03/28 21:46:26 weiden Exp $ */
#undef WIN32_LEAN_AND_MEAN #undef WIN32_LEAN_AND_MEAN
#include <windows.h> #include <windows.h>
#include <stdlib.h> #include <stdlib.h>
@ -263,6 +263,123 @@ NtGdiBitBlt(
return Status; return Status;
} }
BOOL STDCALL
NtGdiTransparentBlt(
HDC hdcDst,
INT xDst,
INT yDst,
INT cxDst,
INT cyDst,
HDC hdcSrc,
INT xSrc,
INT ySrc,
INT cxSrc,
INT cySrc,
COLORREF TransColor)
{
PDC DCDest, DCSrc;
RECT rcDest, rcSrc;
PSURFOBJ SurfDest, SurfSrc;
PSURFGDI SurfGDIDest, SurfGDISrc;
PXLATEOBJ XlateObj;
HPALETTE SourcePalette, DestPalette;
PPALGDI PalDestGDI, PalSourceGDI;
USHORT PalDestMode, PalSrcMode;
if(!(DCDest = DC_LockDc(hdcDst)))
{
DPRINT1("Invalid destination dc handle (0x%08x) passed to NtGdiTransparentBlt\n", hdcDst);
SetLastWin32Error(ERROR_INVALID_HANDLE);
return FALSE;
}
if((hdcDst != hdcSrc) && !(DCSrc = DC_LockDc(hdcSrc)))
{
DC_UnlockDc(hdcDst);
DPRINT1("Invalid source dc handle (0x%08x) passed to NtGdiTransparentBlt\n", hdcSrc);
SetLastWin32Error(ERROR_INVALID_HANDLE);
return FALSE;
}
if(hdcDst == hdcSrc)
{
DCSrc = DCDest;
}
if(DCDest->w.hPalette)
DestPalette = DCDest->w.hPalette;
else
DestPalette = NtGdiGetStockObject(DEFAULT_PALETTE);
if(DCSrc->w.hPalette)
SourcePalette = DCSrc->w.hPalette;
else
SourcePalette = NtGdiGetStockObject(DEFAULT_PALETTE);
if(!(PalSourceGDI = PALETTE_LockPalette(SourcePalette)))
{
DC_UnlockDc(hdcSrc);
DC_UnlockDc(hdcDst);
SetLastWin32Error(ERROR_INVALID_HANDLE);
return FALSE;
}
if((DestPalette != SourcePalette) && !(PalDestGDI = PALETTE_LockPalette(DestPalette)))
{
PALETTE_UnlockPalette(SourcePalette);
DC_UnlockDc(hdcSrc);
DC_UnlockDc(hdcDst);
SetLastWin32Error(ERROR_INVALID_HANDLE);
return FALSE;
}
if(DestPalette != SourcePalette)
{
PalDestMode = PalDestGDI->Mode;
PalSrcMode = PalSourceGDI->Mode;
PALETTE_UnlockPalette(DestPalette);
}
else
{
PalDestMode = PalSrcMode = PalSourceGDI->Mode;
}
PALETTE_UnlockPalette(SourcePalette);
XlateObj = (PXLATEOBJ)IntEngCreateXlate(PalDestMode, PalSrcMode, DestPalette, SourcePalette);
SurfDest = (PSURFOBJ)AccessUserObject((ULONG)DCDest->Surface);
ASSERT(SurfDest);
SurfGDIDest = (PSURFGDI)AccessInternalObjectFromUserObject(SurfDest);
ASSERT(SurfGDIDest);
SurfSrc = (PSURFOBJ)AccessUserObject((ULONG)DCSrc->Surface);
ASSERT(SurfSrc);
SurfGDISrc = (PSURFGDI)AccessInternalObjectFromUserObject(SurfSrc);
ASSERT(SurfGDISrc);
rcDest.left = xDst;
rcDest.top = yDst;
rcDest.right = rcDest.left + cxDst;
rcDest.bottom = rcDest.bottom + cyDst;
rcSrc.left = xSrc;
rcSrc.top = ySrc;
rcSrc.right = rcDest.left + cxSrc;
rcSrc.bottom = rcDest.bottom + cySrc;
if((cxDst != cxSrc) || (cyDst != cySrc))
{
/* FIXME - Create a temporary bitmap and stretchblt it */
}
DC_UnlockDc(hdcSrc);
if(hdcDst != hdcSrc)
{
DC_UnlockDc(hdcDst);
}
if(XlateObj)
{
EngDeleteXlate(XlateObj);
}
return TRUE;
}
HBITMAP STDCALL HBITMAP STDCALL
NtGdiCreateBitmap( NtGdiCreateBitmap(
INT Width, INT Width,