mirror of
https://github.com/reactos/reactos.git
synced 2024-06-01 18:21:50 +00:00
[WIN32K]
- Slap *a bit* of sense in the way we use region objects and handles, avoiding a massive orgy of handle allocations, locks, leaks and so on. The motto here being "if you don't need a valid user-mode handle, then chances are that you don't need one at all." CORE-8506 #resolve #comment Stale region handles should not be passed anymore to user-mode apps now. svn path=/trunk/; revision=64177
This commit is contained in:
parent
726e4806e9
commit
215e0d90a1
|
@ -52,41 +52,31 @@ IntEngWndUpdateClipObj(
|
|||
XCLIPOBJ* Clip,
|
||||
PWND Window)
|
||||
{
|
||||
HRGN hVisRgn;
|
||||
PROSRGNDATA visRgn;
|
||||
|
||||
TRACE("IntEngWndUpdateClipObj\n");
|
||||
|
||||
hVisRgn = VIS_ComputeVisibleRegion(Window, TRUE, TRUE, TRUE);
|
||||
if (hVisRgn != NULL)
|
||||
visRgn = VIS_ComputeVisibleRegion(Window, TRUE, TRUE, TRUE);
|
||||
if (visRgn != NULL)
|
||||
{
|
||||
visRgn = RGNOBJAPI_Lock(hVisRgn, NULL);
|
||||
if (visRgn != NULL)
|
||||
if (visRgn->rdh.nCount > 0)
|
||||
{
|
||||
if (visRgn->rdh.nCount > 0)
|
||||
IntEngUpdateClipRegion(Clip, visRgn->rdh.nCount, visRgn->Buffer, &visRgn->rdh.rcBound);
|
||||
TRACE("Created visible region with %lu rects\n", visRgn->rdh.nCount);
|
||||
TRACE(" BoundingRect: %d, %d %d, %d\n",
|
||||
visRgn->rdh.rcBound.left, visRgn->rdh.rcBound.top,
|
||||
visRgn->rdh.rcBound.right, visRgn->rdh.rcBound.bottom);
|
||||
{
|
||||
IntEngUpdateClipRegion(Clip, visRgn->rdh.nCount, visRgn->Buffer, &visRgn->rdh.rcBound);
|
||||
TRACE("Created visible region with %lu rects\n", visRgn->rdh.nCount);
|
||||
TRACE(" BoundingRect: %d, %d %d, %d\n",
|
||||
visRgn->rdh.rcBound.left, visRgn->rdh.rcBound.top,
|
||||
visRgn->rdh.rcBound.right, visRgn->rdh.rcBound.bottom);
|
||||
ULONG i;
|
||||
for (i = 0; i < visRgn->rdh.nCount; i++)
|
||||
{
|
||||
ULONG i;
|
||||
for (i = 0; i < visRgn->rdh.nCount; i++)
|
||||
{
|
||||
TRACE(" Rect #%lu: %ld,%ld %ld,%ld\n", i+1,
|
||||
visRgn->Buffer[i].left, visRgn->Buffer[i].top,
|
||||
visRgn->Buffer[i].right, visRgn->Buffer[i].bottom);
|
||||
}
|
||||
TRACE(" Rect #%lu: %ld,%ld %ld,%ld\n", i+1,
|
||||
visRgn->Buffer[i].left, visRgn->Buffer[i].top,
|
||||
visRgn->Buffer[i].right, visRgn->Buffer[i].bottom);
|
||||
}
|
||||
}
|
||||
RGNOBJAPI_Unlock(visRgn);
|
||||
}
|
||||
else
|
||||
{
|
||||
WARN("Couldn't lock visible region of window DC\n");
|
||||
}
|
||||
GreDeleteObject(hVisRgn);
|
||||
REGION_Delete(visRgn);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
|
@ -477,7 +477,7 @@ NtGdiSelectClipPath(
|
|||
HDC hDC,
|
||||
int Mode)
|
||||
{
|
||||
HRGN hrgnPath;
|
||||
PREGION RgnPath;
|
||||
PPATH pPath;
|
||||
BOOL success = FALSE;
|
||||
PDC_ATTR pdcattr;
|
||||
|
@ -507,21 +507,31 @@ NtGdiSelectClipPath(
|
|||
}
|
||||
|
||||
/* Construct a region from the path */
|
||||
else if (PATH_PathToRegion(pPath, pdcattr->jFillMode, &hrgnPath))
|
||||
RgnPath = IntSysCreateRectpRgn(0, 0, 0, 0);
|
||||
if (!RgnPath)
|
||||
{
|
||||
PREGION prgnPath = REGION_LockRgn(hrgnPath);
|
||||
ASSERT(prgnPath);
|
||||
success = IntGdiExtSelectClipRgn(pdc, prgnPath, Mode) != ERROR;
|
||||
REGION_UnlockRgn(prgnPath);
|
||||
GreDeleteObject( hrgnPath );
|
||||
|
||||
/* Empty the path */
|
||||
if (success)
|
||||
PATH_EmptyPath(pPath);
|
||||
|
||||
/* FIXME: Should this function delete the path even if it failed? */
|
||||
EngSetLastError(ERROR_NOT_ENOUGH_MEMORY);
|
||||
DC_UnlockDc(pdc);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (!PATH_PathToRegion(pPath, pdcattr->jFillMode, RgnPath))
|
||||
{
|
||||
EngSetLastError(ERROR_CAN_NOT_COMPLETE);
|
||||
REGION_Delete(RgnPath);
|
||||
DC_UnlockDc(pdc);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
success = IntGdiExtSelectClipRgn(pdc, RgnPath, Mode) != ERROR;
|
||||
REGION_Delete(RgnPath);
|
||||
|
||||
/* Empty the path */
|
||||
if (success)
|
||||
PATH_EmptyPath(pPath);
|
||||
|
||||
/* FIXME: Should this function delete the path even if it failed? */
|
||||
|
||||
PATH_UnlockPath(pPath);
|
||||
DC_UnlockDc(pdc);
|
||||
|
||||
|
|
|
@ -458,8 +458,24 @@ NtGdiPolyPolyDraw( IN HDC hDC,
|
|||
/* Special handling for GdiPolyPolyRgn */
|
||||
if (iFunc == GdiPolyPolyRgn)
|
||||
{
|
||||
PREGION Rgn;
|
||||
HRGN hRgn;
|
||||
hRgn = IntCreatePolyPolygonRgn(SafePoints, SafeCounts, Count, (INT_PTR)hDC);
|
||||
|
||||
Rgn = REGION_AllocUserRgnWithHandle(0);
|
||||
if (!Rgn)
|
||||
{
|
||||
EngSetLastError(ERROR_NOT_ENOUGH_MEMORY);
|
||||
ExFreePoolWithTag(pTemp, TAG_SHAPE);
|
||||
return 0;
|
||||
}
|
||||
hRgn = Rgn->BaseObject.hHmgr;
|
||||
if (!IntSetPolyPolygonRgn(SafePoints, SafeCounts, Count, hDC ? 1 : 2, Rgn))
|
||||
{
|
||||
/* EngSetLastError ? */
|
||||
GreDeleteObject(hRgn);
|
||||
hRgn = NULL;
|
||||
}
|
||||
RGNOBJAPI_Unlock(Rgn);
|
||||
ExFreePoolWithTag(pTemp, TAG_SHAPE);
|
||||
return (ULONG_PTR)hRgn;
|
||||
}
|
||||
|
|
|
@ -98,7 +98,7 @@ PATH_FillPath(
|
|||
//SIZE ptViewportExt, ptWindowExt;
|
||||
//POINTL ptViewportOrg, ptWindowOrg;
|
||||
XFORM xform;
|
||||
HRGN hrgn;
|
||||
PREGION Rgn;
|
||||
PDC_ATTR pdcattr = dc->pdcattr;
|
||||
|
||||
if (pPath->state != PATH_Closed)
|
||||
|
@ -107,61 +107,72 @@ PATH_FillPath(
|
|||
return FALSE;
|
||||
}
|
||||
|
||||
if (PATH_PathToRegion(pPath, pdcattr->jFillMode, &hrgn))
|
||||
/* Allocate a temporary region */
|
||||
Rgn = IntSysCreateRectpRgn(0, 0, 0, 0);
|
||||
if (!Rgn)
|
||||
{
|
||||
/* Since PaintRgn interprets the region as being in logical coordinates
|
||||
* but the points we store for the path are already in device
|
||||
* coordinates, we have to set the mapping mode to MM_TEXT temporarily.
|
||||
* Using SaveDC to save information about the mapping mode / world
|
||||
* transform would be easier but would require more overhead, especially
|
||||
* now that SaveDC saves the current path.
|
||||
*/
|
||||
EngSetLastError(ERROR_NOT_ENOUGH_MEMORY);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/* Save the information about the old mapping mode */
|
||||
//mapMode = pdcattr->iMapMode;
|
||||
//ptViewportExt = pdcattr->szlViewportExt;
|
||||
//ptViewportOrg = pdcattr->ptlViewportOrg;
|
||||
//ptWindowExt = pdcattr->szlWindowExt;
|
||||
//ptWindowOrg = pdcattr->ptlWindowOrg;
|
||||
if (!PATH_PathToRegion(pPath, pdcattr->jFillMode, Rgn))
|
||||
{
|
||||
/* EngSetLastError ? */
|
||||
REGION_Delete(Rgn);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/* Save world transform
|
||||
* NB: The Windows documentation on world transforms would lead one to
|
||||
* believe that this has to be done only in GM_ADVANCED; however, my
|
||||
* tests show that resetting the graphics mode to GM_COMPATIBLE does
|
||||
* not reset the world transform.
|
||||
*/
|
||||
MatrixS2XForm(&xform, &dc->pdcattr->mxWorldToPage);
|
||||
/* Since PaintRgn interprets the region as being in logical coordinates
|
||||
* but the points we store for the path are already in device
|
||||
* coordinates, we have to set the mapping mode to MM_TEXT temporarily.
|
||||
* Using SaveDC to save information about the mapping mode / world
|
||||
* transform would be easier but would require more overhead, especially
|
||||
* now that SaveDC saves the current path.
|
||||
*/
|
||||
|
||||
/* Set MM_TEXT */
|
||||
/* Save the information about the old mapping mode */
|
||||
//mapMode = pdcattr->iMapMode;
|
||||
//ptViewportExt = pdcattr->szlViewportExt;
|
||||
//ptViewportOrg = pdcattr->ptlViewportOrg;
|
||||
//ptWindowExt = pdcattr->szlWindowExt;
|
||||
//ptWindowOrg = pdcattr->ptlWindowOrg;
|
||||
|
||||
/* Save world transform
|
||||
* NB: The Windows documentation on world transforms would lead one to
|
||||
* believe that this has to be done only in GM_ADVANCED; however, my
|
||||
* tests show that resetting the graphics mode to GM_COMPATIBLE does
|
||||
* not reset the world transform.
|
||||
*/
|
||||
MatrixS2XForm(&xform, &dc->pdcattr->mxWorldToPage);
|
||||
|
||||
/* Set MM_TEXT */
|
||||
// IntGdiSetMapMode(dc, MM_TEXT);
|
||||
// pdcattr->ptlViewportOrg.x = 0;
|
||||
// pdcattr->ptlViewportOrg.y = 0;
|
||||
// pdcattr->ptlWindowOrg.x = 0;
|
||||
// pdcattr->ptlWindowOrg.y = 0;
|
||||
|
||||
// graphicsMode = pdcattr->iGraphicsMode;
|
||||
// graphicsMode = pdcattr->iGraphicsMode;
|
||||
// pdcattr->iGraphicsMode = GM_ADVANCED;
|
||||
// IntGdiModifyWorldTransform(dc, &xform, MWT_IDENTITY);
|
||||
// pdcattr->iGraphicsMode = graphicsMode;
|
||||
|
||||
/* Paint the region */
|
||||
IntGdiPaintRgn(dc, hrgn);
|
||||
GreDeleteObject(hrgn);
|
||||
/* Restore the old mapping mode */
|
||||
/* Paint the region */
|
||||
IntGdiPaintRgn(dc, Rgn);
|
||||
REGION_Delete(Rgn);
|
||||
/* Restore the old mapping mode */
|
||||
// IntGdiSetMapMode(dc, mapMode);
|
||||
// pdcattr->szlViewportExt = ptViewportExt;
|
||||
// pdcattr->ptlViewportOrg = ptViewportOrg;
|
||||
// pdcattr->szlWindowExt = ptWindowExt;
|
||||
// pdcattr->ptlWindowOrg = ptWindowOrg;
|
||||
|
||||
/* Go to GM_ADVANCED temporarily to restore the world transform */
|
||||
//graphicsMode = pdcattr->iGraphicsMode;
|
||||
/* Go to GM_ADVANCED temporarily to restore the world transform */
|
||||
//graphicsMode = pdcattr->iGraphicsMode;
|
||||
// pdcattr->iGraphicsMode = GM_ADVANCED;
|
||||
// IntGdiModifyWorldTransform(dc, &xform, MWT_MAX+1);
|
||||
// pdcattr->iGraphicsMode = graphicsMode;
|
||||
return TRUE;
|
||||
}
|
||||
return FALSE;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* PATH_InitGdiPath
|
||||
|
@ -1221,14 +1232,14 @@ FASTCALL
|
|||
PATH_PathToRegion(
|
||||
PPATH pPath,
|
||||
INT nPolyFillMode,
|
||||
HRGN *pHrgn)
|
||||
PREGION Rgn)
|
||||
{
|
||||
int numStrokes, iStroke, i;
|
||||
PULONG pNumPointsInStroke;
|
||||
HRGN hrgn = 0;
|
||||
BOOL Ret;
|
||||
|
||||
ASSERT(pPath != NULL);
|
||||
ASSERT(pHrgn != NULL);
|
||||
ASSERT(Rgn != NULL);
|
||||
|
||||
PATH_FlattenPath(pPath);
|
||||
|
||||
|
@ -1268,23 +1279,18 @@ PATH_PathToRegion(
|
|||
pNumPointsInStroke[iStroke]++;
|
||||
}
|
||||
|
||||
/* Create a region from the strokes */
|
||||
hrgn = IntCreatePolyPolygonRgn(pPath->pPoints,
|
||||
pNumPointsInStroke,
|
||||
numStrokes,
|
||||
nPolyFillMode);
|
||||
if (hrgn == (HRGN)0)
|
||||
{
|
||||
EngSetLastError(ERROR_NOT_ENOUGH_MEMORY);
|
||||
return FALSE;
|
||||
}
|
||||
/* Fill the region with the strokes */
|
||||
Ret = IntSetPolyPolygonRgn(pPath->pPoints,
|
||||
pNumPointsInStroke,
|
||||
numStrokes,
|
||||
nPolyFillMode,
|
||||
Rgn);
|
||||
|
||||
/* Free memory for number-of-points-in-stroke array */
|
||||
ExFreePoolWithTag(pNumPointsInStroke, TAG_PATH);
|
||||
|
||||
/* Success! */
|
||||
*pHrgn = hrgn;
|
||||
return TRUE;
|
||||
return Ret;
|
||||
}
|
||||
|
||||
/* PATH_EmptyPath
|
||||
|
@ -2675,6 +2681,7 @@ NtGdiPathToRegion(HDC hDC)
|
|||
{
|
||||
PPATH pPath;
|
||||
HRGN hrgnRval = 0;
|
||||
PREGION Rgn;
|
||||
DC *pDc;
|
||||
PDC_ATTR pdcattr;
|
||||
|
||||
|
@ -2703,9 +2710,25 @@ NtGdiPathToRegion(HDC hDC)
|
|||
}
|
||||
else
|
||||
{
|
||||
/* Create the region and fill it with the path strokes */
|
||||
Rgn = REGION_AllocUserRgnWithHandle(1);
|
||||
if (!Rgn)
|
||||
{
|
||||
PATH_UnlockPath(pPath);
|
||||
DC_UnlockDc(pDc);
|
||||
}
|
||||
hrgnRval = Rgn->BaseObject.hHmgr;
|
||||
/* FIXME: Should we empty the path even if conversion failed? */
|
||||
if (PATH_PathToRegion(pPath, pdcattr->jFillMode, &hrgnRval))
|
||||
if (PATH_PathToRegion(pPath, pdcattr->jFillMode, Rgn))
|
||||
{
|
||||
PATH_EmptyPath(pPath);
|
||||
}
|
||||
else
|
||||
{
|
||||
GreDeleteObject(hrgnRval);
|
||||
hrgnRval = NULL;
|
||||
}
|
||||
RGNOBJAPI_Unlock(Rgn);
|
||||
}
|
||||
|
||||
PATH_UnlockPath(pPath);
|
||||
|
|
|
@ -67,7 +67,7 @@ BOOL FASTCALL PATH_PolyPolygon ( PDC dc, const POINT* pts, const INT* counts, UI
|
|||
BOOL FASTCALL PATH_PolyPolyline( PDC dc, const POINT* pts, const DWORD* counts, DWORD polylines);
|
||||
BOOL FASTCALL PATH_Rectangle (PDC dc, INT x1, INT y1, INT x2, INT y2);
|
||||
BOOL FASTCALL PATH_RoundRect(DC *dc, INT x1, INT y1, INT x2, INT y2, INT ell_width, INT ell_height);
|
||||
BOOL FASTCALL PATH_PathToRegion (PPATH pPath, INT nPolyFillMode, HRGN *pHrgn);
|
||||
BOOL FASTCALL PATH_PathToRegion (PPATH pPath, INT nPolyFillMode, PREGION Rgn);
|
||||
BOOL FASTCALL PATH_ExtTextOut(PDC dc,INT x,INT y,UINT flags,const RECTL *lprc,LPCWSTR str,UINT count,const INT *dx);
|
||||
|
||||
BOOL FASTCALL PATH_AddEntry (PPATH pPath, const POINT *pPoint, BYTE flags);
|
||||
|
|
|
@ -1956,46 +1956,35 @@ REGION_CreateFrameRgn(
|
|||
}
|
||||
|
||||
|
||||
static
|
||||
BOOL FASTCALL
|
||||
REGION_LPTODP(
|
||||
PDC dc,
|
||||
HRGN hDest,
|
||||
HRGN hSrc)
|
||||
_In_ PDC dc,
|
||||
_Inout_ PREGION RgnDest,
|
||||
_In_ PREGION RgnSrc)
|
||||
{
|
||||
RECTL *pCurRect, *pEndRect;
|
||||
PROSRGNDATA srcObj = NULL;
|
||||
PROSRGNDATA destObj = NULL;
|
||||
|
||||
RECTL tmpRect;
|
||||
BOOL ret = FALSE;
|
||||
PDC_ATTR pdcattr;
|
||||
|
||||
if (!dc)
|
||||
return ret;
|
||||
return FALSE;
|
||||
pdcattr = dc->pdcattr;
|
||||
|
||||
if (pdcattr->iMapMode == MM_TEXT) // Requires only a translation
|
||||
{
|
||||
if (NtGdiCombineRgn(hDest, hSrc, 0, RGN_COPY) == ERROR)
|
||||
goto done;
|
||||
if (IntGdiCombineRgn(RgnDest, RgnSrc, 0, RGN_COPY) == ERROR)
|
||||
return FALSE;
|
||||
|
||||
NtGdiOffsetRgn(hDest, pdcattr->ptlViewportOrg.x - pdcattr->ptlWindowOrg.x,
|
||||
IntGdiOffsetRgn(RgnDest, pdcattr->ptlViewportOrg.x - pdcattr->ptlWindowOrg.x,
|
||||
pdcattr->ptlViewportOrg.y - pdcattr->ptlWindowOrg.y);
|
||||
ret = TRUE;
|
||||
goto done;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
if ( !(srcObj = RGNOBJAPI_Lock(hSrc, NULL)) )
|
||||
goto done;
|
||||
if ( !(destObj = RGNOBJAPI_Lock(hDest, NULL)) )
|
||||
{
|
||||
RGNOBJAPI_Unlock(srcObj);
|
||||
goto done;
|
||||
}
|
||||
EMPTY_REGION(destObj);
|
||||
EMPTY_REGION(RgnDest);
|
||||
|
||||
pEndRect = srcObj->Buffer + srcObj->rdh.nCount;
|
||||
for (pCurRect = srcObj->Buffer; pCurRect < pEndRect; pCurRect++)
|
||||
pEndRect = RgnSrc->Buffer + RgnSrc->rdh.nCount;
|
||||
for (pCurRect = RgnSrc->Buffer; pCurRect < pEndRect; pCurRect++)
|
||||
{
|
||||
tmpRect = *pCurRect;
|
||||
tmpRect.left = XLPTODP(pdcattr, tmpRect.left);
|
||||
|
@ -2016,15 +2005,10 @@ REGION_LPTODP(
|
|||
tmpRect.bottom = tmp;
|
||||
}
|
||||
|
||||
REGION_UnionRectWithRgn(destObj, &tmpRect);
|
||||
REGION_UnionRectWithRgn(RgnDest, &tmpRect);
|
||||
}
|
||||
ret = TRUE;
|
||||
|
||||
RGNOBJAPI_Unlock(srcObj);
|
||||
RGNOBJAPI_Unlock(destObj);
|
||||
|
||||
done:
|
||||
return ret;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
PROSRGNDATA
|
||||
|
@ -2236,7 +2220,7 @@ IntSysCreateRectpRgn(INT LeftRect, INT TopRect, INT RightRect, INT BottomRect)
|
|||
PREGION prgn;
|
||||
|
||||
/* Allocate a region, witout a handle */
|
||||
prgn = (PREGION)GDIOBJ_AllocateObject(GDIObjType_RGN_TYPE, sizeof(REGION), 0);
|
||||
prgn = (PREGION)GDIOBJ_AllocateObject(GDIObjType_RGN_TYPE, sizeof(REGION), BASEFLAG_LOOKASIDE);
|
||||
if (!prgn)
|
||||
{
|
||||
return NULL;
|
||||
|
@ -2250,31 +2234,6 @@ IntSysCreateRectpRgn(INT LeftRect, INT TopRect, INT RightRect, INT BottomRect)
|
|||
return prgn;
|
||||
}
|
||||
|
||||
HRGN
|
||||
FASTCALL
|
||||
IntSysCreateRectRgn(INT LeftRect, INT TopRect, INT RightRect, INT BottomRect)
|
||||
{
|
||||
PREGION prgn;
|
||||
HRGN hrgn;
|
||||
|
||||
/* Allocate a region, witout a handle */
|
||||
prgn = (PREGION)GDIOBJ_AllocObjWithHandle(GDI_OBJECT_TYPE_REGION, sizeof(REGION));
|
||||
if (!prgn)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* Initialize it */
|
||||
prgn->Buffer = &prgn->rdh.rcBound;
|
||||
REGION_SetRectRgn(prgn, LeftRect, TopRect, RightRect, BottomRect);
|
||||
hrgn = prgn->BaseObject.hHmgr;
|
||||
prgn->prgnattr = &prgn->rgnattr;
|
||||
|
||||
REGION_UnlockRgn(prgn);
|
||||
|
||||
return hrgn;
|
||||
}
|
||||
|
||||
VOID NTAPI
|
||||
REGION_vCleanup(PVOID ObjectBody)
|
||||
{
|
||||
|
@ -2479,44 +2438,42 @@ BOOL
|
|||
FASTCALL
|
||||
IntGdiPaintRgn(
|
||||
PDC dc,
|
||||
HRGN hRgn
|
||||
PREGION Rgn
|
||||
)
|
||||
{
|
||||
HRGN tmpVisRgn;
|
||||
PROSRGNDATA visrgn;
|
||||
PROSRGNDATA VisRgn;
|
||||
XCLIPOBJ ClipRegion;
|
||||
BOOL bRet = FALSE;
|
||||
POINTL BrushOrigin;
|
||||
SURFACE *psurf;
|
||||
PDC_ATTR pdcattr;
|
||||
|
||||
if (!dc) return FALSE;
|
||||
if (!dc || !Rgn)
|
||||
return FALSE;
|
||||
|
||||
pdcattr = dc->pdcattr;
|
||||
|
||||
ASSERT(!(pdcattr->ulDirty_ & (DIRTY_FILL | DC_BRUSH_DIRTY)));
|
||||
|
||||
if (!(tmpVisRgn = IntSysCreateRectRgn(0, 0, 0, 0))) return FALSE;
|
||||
|
||||
// Transform region into device co-ords
|
||||
if (!REGION_LPTODP(dc, tmpVisRgn, hRgn) ||
|
||||
NtGdiOffsetRgn(tmpVisRgn, dc->ptlDCOrig.x, dc->ptlDCOrig.y) == ERROR)
|
||||
VisRgn = IntSysCreateRectpRgn(0, 0, 0, 0);
|
||||
if (!VisRgn)
|
||||
{
|
||||
GreDeleteObject(tmpVisRgn);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
visrgn = RGNOBJAPI_Lock(tmpVisRgn, NULL);
|
||||
if (visrgn == NULL)
|
||||
// Transform region into device co-ords
|
||||
if (!REGION_LPTODP(dc, VisRgn, Rgn) ||
|
||||
IntGdiOffsetRgn(VisRgn, dc->ptlDCOrig.x, dc->ptlDCOrig.y) == ERROR)
|
||||
{
|
||||
GreDeleteObject(tmpVisRgn);
|
||||
REGION_Delete(VisRgn);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (dc->prgnRao)
|
||||
IntGdiCombineRgn(visrgn, visrgn, dc->prgnRao, RGN_AND);
|
||||
IntGdiCombineRgn(VisRgn, VisRgn, dc->prgnRao, RGN_AND);
|
||||
|
||||
IntEngInitClipObj(&ClipRegion);
|
||||
IntEngUpdateClipRegion(&ClipRegion, visrgn->rdh.nCount, visrgn->Buffer, &visrgn->rdh.rcBound );
|
||||
IntEngUpdateClipRegion(&ClipRegion, VisRgn->rdh.nCount, VisRgn->Buffer, &VisRgn->rdh.rcBound );
|
||||
|
||||
BrushOrigin.x = pdcattr->ptlBrushOrigin.x;
|
||||
BrushOrigin.y = pdcattr->ptlBrushOrigin.y;
|
||||
|
@ -2529,8 +2486,7 @@ IntGdiPaintRgn(
|
|||
&BrushOrigin,
|
||||
0xFFFF); // FIXME: Don't know what to put here
|
||||
|
||||
RGNOBJAPI_Unlock(visrgn);
|
||||
GreDeleteObject(tmpVisRgn);
|
||||
REGION_Delete(VisRgn);
|
||||
IntEngFreeClipResources(&ClipRegion);
|
||||
|
||||
// Fill the region
|
||||
|
@ -3129,16 +3085,15 @@ REGION_CreateETandAET(
|
|||
}
|
||||
}
|
||||
|
||||
HRGN FASTCALL
|
||||
IntCreatePolyPolygonRgn(
|
||||
BOOL FASTCALL
|
||||
IntSetPolyPolygonRgn(
|
||||
POINT *Pts,
|
||||
PULONG Count,
|
||||
INT nbpolygons,
|
||||
INT mode
|
||||
INT mode,
|
||||
PREGION Rgn
|
||||
)
|
||||
{
|
||||
HRGN hrgn;
|
||||
ROSRGNDATA *region;
|
||||
EdgeTableEntry *pAET; /* Active Edge Table */
|
||||
INT y; /* Current scanline */
|
||||
int iPts = 0; /* Number of pts in buffer */
|
||||
|
@ -3158,10 +3113,6 @@ IntCreatePolyPolygonRgn(
|
|||
|
||||
if (mode == 0 || mode > 2) return 0;
|
||||
|
||||
if (!(region = REGION_AllocUserRgnWithHandle(nbpolygons)))
|
||||
return 0;
|
||||
hrgn = region->BaseObject.hHmgr;
|
||||
|
||||
/* Special case a rectangle */
|
||||
|
||||
if (((nbpolygons == 1) && ((*Count == 4) ||
|
||||
|
@ -3175,18 +3126,19 @@ IntCreatePolyPolygonRgn(
|
|||
(Pts[2].x == Pts[3].x) &&
|
||||
(Pts[3].y == Pts[0].y))))
|
||||
{
|
||||
RGNOBJAPI_Unlock(region);
|
||||
NtGdiSetRectRgn(hrgn, min(Pts[0].x, Pts[2].x), min(Pts[0].y, Pts[2].y),
|
||||
max(Pts[0].x, Pts[2].x), max(Pts[0].y, Pts[2].y));
|
||||
return hrgn;
|
||||
REGION_SetRectRgn(Rgn,
|
||||
min(Pts[0].x, Pts[2].x),
|
||||
min(Pts[0].y, Pts[2].y),
|
||||
max(Pts[0].x, Pts[2].x),
|
||||
max(Pts[0].y, Pts[2].y));
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
for (poly = total = 0; poly < nbpolygons; poly++)
|
||||
total += Count[poly];
|
||||
if (! (pETEs = ExAllocatePoolWithTag(PagedPool, sizeof(EdgeTableEntry) * total, TAG_REGION)) )
|
||||
{
|
||||
GreDeleteObject(hrgn);
|
||||
return 0;
|
||||
return FALSE;
|
||||
}
|
||||
pts = FirstPtBlock.pts;
|
||||
REGION_CreateETandAET(Count, nbpolygons, Pts, &ET, &AET, pETEs, &SLLBlock);
|
||||
|
@ -3230,7 +3182,7 @@ IntCreatePolyPolygonRgn(
|
|||
{
|
||||
DPRINT1("Can't alloc tPB\n");
|
||||
ExFreePoolWithTag(pETEs, TAG_REGION);
|
||||
return 0;
|
||||
return FALSE;
|
||||
}
|
||||
curPtBlock->next = tmpPtBlock;
|
||||
curPtBlock = tmpPtBlock;
|
||||
|
@ -3289,8 +3241,7 @@ IntCreatePolyPolygonRgn(
|
|||
{
|
||||
DPRINT1("Can't alloc tPB\n");
|
||||
ExFreePoolWithTag(pETEs, TAG_REGION);
|
||||
GreDeleteObject(hrgn);
|
||||
return 0;
|
||||
return FALSE;
|
||||
}
|
||||
curPtBlock->next = tmpPtBlock;
|
||||
curPtBlock = tmpPtBlock;
|
||||
|
@ -3315,7 +3266,7 @@ IntCreatePolyPolygonRgn(
|
|||
}
|
||||
}
|
||||
REGION_FreeStorage(SLLBlock.next);
|
||||
REGION_PtsToRegion(numFullPtBlocks, iPts, &FirstPtBlock, region);
|
||||
REGION_PtsToRegion(numFullPtBlocks, iPts, &FirstPtBlock, Rgn);
|
||||
|
||||
for (curPtBlock = FirstPtBlock.next; --numFullPtBlocks >= 0;)
|
||||
{
|
||||
|
@ -3324,8 +3275,7 @@ IntCreatePolyPolygonRgn(
|
|||
curPtBlock = tmpPtBlock;
|
||||
}
|
||||
ExFreePoolWithTag(pETEs, TAG_REGION);
|
||||
RGNOBJAPI_Unlock(region);
|
||||
return hrgn;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL
|
||||
|
@ -3432,6 +3382,8 @@ NtGdiCreateRectRgn(INT LeftRect, INT TopRect, INT RightRect, INT BottomRect)
|
|||
REGION_SetRectRgn(pRgn, LeftRect, TopRect, RightRect, BottomRect);
|
||||
RGNOBJAPI_Unlock(pRgn);
|
||||
|
||||
DPRINT1("Returning %p.\n", hRgn);
|
||||
|
||||
return hRgn;
|
||||
}
|
||||
|
||||
|
@ -3762,7 +3714,7 @@ NtGdiFrameRgn(
|
|||
HRGN FrameRgn;
|
||||
BOOL Ret;
|
||||
|
||||
if (!(FrameRgn = IntSysCreateRectRgn(0, 0, 0, 0)))
|
||||
if (!(FrameRgn = NtGdiCreateRectRgn(0, 0, 0, 0)))
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
|
|
|
@ -40,8 +40,8 @@ VOID FASTCALL IntGdiReleaseRaoRgn(PDC);
|
|||
VOID FASTCALL IntGdiReleaseVisRgn(PDC);
|
||||
|
||||
INT APIENTRY IntGdiGetRgnBox(HRGN, RECTL*);
|
||||
BOOL FASTCALL IntGdiPaintRgn(PDC, HRGN );
|
||||
HRGN FASTCALL IntCreatePolyPolygonRgn(PPOINT, PULONG, INT, INT);
|
||||
BOOL FASTCALL IntGdiPaintRgn(PDC, PREGION );
|
||||
BOOL FASTCALL IntSetPolyPolygonRgn(PPOINT, PULONG, INT, INT, PREGION);
|
||||
INT FASTCALL IntGdiOffsetRgn(PROSRGNDATA,INT,INT);
|
||||
BOOL FASTCALL IntRectInRegion(HRGN,LPRECTL);
|
||||
|
||||
|
@ -49,13 +49,9 @@ INT FASTCALL IntGdiCombineRgn(PROSRGNDATA, PROSRGNDATA, PROSRGNDATA, INT);
|
|||
INT FASTCALL REGION_Complexity(PROSRGNDATA);
|
||||
PROSRGNDATA FASTCALL RGNOBJAPI_Lock(HRGN,PRGN_ATTR *);
|
||||
VOID FASTCALL RGNOBJAPI_Unlock(PROSRGNDATA);
|
||||
HRGN FASTCALL IntSysCreateRectRgn(INT,INT,INT,INT);
|
||||
PROSRGNDATA FASTCALL IntSysCreateRectpRgn(INT,INT,INT,INT);
|
||||
BOOL FASTCALL IntGdiSetRegionOwner(HRGN,DWORD);
|
||||
|
||||
#define IntSysCreateRectRgnIndirect(prc) \
|
||||
IntSysCreateRectRgn((prc)->left, (prc)->top, (prc)->right, (prc)->bottom)
|
||||
|
||||
#define IntSysCreateRectpRgnIndirect(prc) \
|
||||
IntSysCreateRectpRgn((prc)->left, (prc)->top, (prc)->right, (prc)->bottom)
|
||||
|
||||
|
|
|
@ -1010,16 +1010,20 @@ IntDefWindowProc(
|
|||
|
||||
case WM_SYNCPAINT:
|
||||
{
|
||||
HRGN hRgn;
|
||||
PREGION Rgn;
|
||||
Wnd->state &= ~WNDS_SYNCPAINTPENDING;
|
||||
ERR("WM_SYNCPAINT\n");
|
||||
hRgn = IntSysCreateRectRgn(0, 0, 0, 0);
|
||||
if (co_UserGetUpdateRgn(Wnd, hRgn, FALSE) != NULLREGION)
|
||||
Rgn = IntSysCreateRectpRgn(0, 0, 0, 0);
|
||||
if (Rgn)
|
||||
{
|
||||
if (!wParam) wParam = (RDW_ERASENOW | RDW_ERASE | RDW_FRAME | RDW_ALLCHILDREN);
|
||||
co_UserRedrawWindow(Wnd, NULL, hRgn, wParam);
|
||||
if (co_UserGetUpdateRgn(Wnd, Rgn, FALSE) != NULLREGION)
|
||||
{
|
||||
if (!wParam)
|
||||
wParam = (RDW_ERASENOW | RDW_ERASE | RDW_FRAME | RDW_ALLCHILDREN);
|
||||
co_UserRedrawWindow(Wnd, NULL, Rgn, wParam);
|
||||
}
|
||||
REGION_Delete(Rgn);
|
||||
}
|
||||
GreDeleteObject(hRgn);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -752,19 +752,19 @@ VOID APIENTRY
|
|||
UserRedrawDesktop()
|
||||
{
|
||||
PWND Window = NULL;
|
||||
HRGN hRgn;
|
||||
PREGION Rgn;
|
||||
|
||||
Window = UserGetDesktopWindow();
|
||||
hRgn = IntSysCreateRectRgnIndirect(&Window->rcWindow);
|
||||
Rgn = IntSysCreateRectpRgnIndirect(&Window->rcWindow);
|
||||
|
||||
IntInvalidateWindows( Window,
|
||||
hRgn,
|
||||
Rgn,
|
||||
RDW_FRAME |
|
||||
RDW_ERASE |
|
||||
RDW_INVALIDATE |
|
||||
RDW_ALLCHILDREN);
|
||||
|
||||
GreDeleteObject(hRgn);
|
||||
REGION_Delete(Rgn);
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -652,7 +652,6 @@ IntDispatchMessage(PMSG pMsg)
|
|||
LRESULT retval = 0;
|
||||
PTHREADINFO pti;
|
||||
PWND Window = NULL;
|
||||
HRGN hrgn;
|
||||
BOOL DoCallBack = TRUE;
|
||||
|
||||
if (pMsg->hwnd)
|
||||
|
@ -743,11 +742,12 @@ IntDispatchMessage(PMSG pMsg)
|
|||
|
||||
if (pMsg->message == WM_PAINT)
|
||||
{
|
||||
PREGION Rgn;
|
||||
Window->state2 &= ~WNDS2_WMPAINTSENT;
|
||||
/* send a WM_NCPAINT and WM_ERASEBKGND if the non-client area is still invalid */
|
||||
hrgn = IntSysCreateRectRgn( 0, 0, 0, 0 );
|
||||
co_UserGetUpdateRgn( Window, hrgn, TRUE );
|
||||
GreDeleteObject(hrgn);
|
||||
Rgn = IntSysCreateRectpRgn( 0, 0, 0, 0 );
|
||||
co_UserGetUpdateRgn( Window, Rgn, TRUE );
|
||||
REGION_Delete(Rgn);
|
||||
}
|
||||
|
||||
return retval;
|
||||
|
|
|
@ -258,7 +258,11 @@ UserUpdateMonitorSize(IN HDEV hDev)
|
|||
}
|
||||
|
||||
/* ...and create new one */
|
||||
pMonitor->hrgnMonitor = IntSysCreateRectRgnIndirect(&pMonitor->rcMonitor);
|
||||
pMonitor->hrgnMonitor = NtGdiCreateRectRgn(
|
||||
pMonitor->rcMonitor.left,
|
||||
pMonitor->rcMonitor.top,
|
||||
pMonitor->rcMonitor.right,
|
||||
pMonitor->rcMonitor.bottom);
|
||||
if (pMonitor->hrgnMonitor)
|
||||
IntGdiSetRegionOwner(pMonitor->hrgnMonitor, GDI_OBJ_HMGR_PUBLIC);
|
||||
|
||||
|
|
|
@ -56,7 +56,7 @@ IntIntersectWithParents(PWND Child, RECTL *WindowRect)
|
|||
}
|
||||
|
||||
BOOL FASTCALL
|
||||
IntValidateParent(PWND Child, HRGN hValidateRgn, BOOL Recurse)
|
||||
IntValidateParent(PWND Child, PREGION ValidateRgn, BOOL Recurse)
|
||||
{
|
||||
PWND ParentWnd = Child;
|
||||
|
||||
|
@ -81,7 +81,7 @@ IntValidateParent(PWND Child, HRGN hValidateRgn, BOOL Recurse)
|
|||
return FALSE;
|
||||
|
||||
IntInvalidateWindows( ParentWnd,
|
||||
hValidateRgn,
|
||||
ValidateRgn,
|
||||
RDW_VALIDATE | RDW_NOCHILDREN);
|
||||
}
|
||||
|
||||
|
@ -177,9 +177,21 @@ IntCalcWindowRgn(PWND Wnd, BOOL Client)
|
|||
HRGN hRgnWindow;
|
||||
|
||||
if (Client)
|
||||
hRgnWindow = IntSysCreateRectRgnIndirect(&Wnd->rcClient);
|
||||
{
|
||||
hRgnWindow = NtGdiCreateRectRgn(
|
||||
Wnd->rcClient.left,
|
||||
Wnd->rcClient.top,
|
||||
Wnd->rcClient.right,
|
||||
Wnd->rcClient.bottom);
|
||||
}
|
||||
else
|
||||
hRgnWindow = IntSysCreateRectRgnIndirect(&Wnd->rcWindow);
|
||||
{
|
||||
hRgnWindow = NtGdiCreateRectRgn(
|
||||
Wnd->rcWindow.left,
|
||||
Wnd->rcWindow.top,
|
||||
Wnd->rcWindow.right,
|
||||
Wnd->rcWindow.bottom);
|
||||
}
|
||||
|
||||
if (Wnd->hrgnClip != NULL && !(Wnd->style & WS_MINIMIZE))
|
||||
{
|
||||
|
@ -302,8 +314,16 @@ co_IntPaintWindows(PWND Wnd, ULONG Flags, BOOL Recurse)
|
|||
{
|
||||
if (Wnd->hrgnUpdate)
|
||||
{
|
||||
if (!IntValidateParent(Wnd, Wnd->hrgnUpdate, Recurse))
|
||||
return;
|
||||
PREGION RgnUpdate = RGNOBJAPI_Lock(Wnd->hrgnUpdate, NULL);
|
||||
if (RgnUpdate)
|
||||
{
|
||||
if (!IntValidateParent(Wnd, RgnUpdate, Recurse))
|
||||
{
|
||||
RGNOBJAPI_Unlock(RgnUpdate);
|
||||
return;
|
||||
}
|
||||
RGNOBJAPI_Unlock(RgnUpdate);
|
||||
}
|
||||
}
|
||||
|
||||
if (Flags & RDW_UPDATENOW)
|
||||
|
@ -397,7 +417,7 @@ co_IntPaintWindows(PWND Wnd, ULONG Flags, BOOL Recurse)
|
|||
* co_WinPosSetWindowPos, IntValidateParent, co_UserRedrawWindow.
|
||||
*/
|
||||
VOID FASTCALL
|
||||
IntInvalidateWindows(PWND Wnd, HRGN hRgn, ULONG Flags)
|
||||
IntInvalidateWindows(PWND Wnd, PREGION Rgn, ULONG Flags)
|
||||
{
|
||||
INT RgnType;
|
||||
BOOL HadPaintMessage;
|
||||
|
@ -412,11 +432,14 @@ IntInvalidateWindows(PWND Wnd, HRGN hRgn, ULONG Flags)
|
|||
*/
|
||||
if (0 != (Flags & RDW_INVALIDATE) && 0 == (Flags & RDW_FRAME))
|
||||
{
|
||||
HRGN hRgnClient;
|
||||
PREGION RgnClient;
|
||||
|
||||
hRgnClient = IntSysCreateRectRgnIndirect(&Wnd->rcClient);
|
||||
RgnType = NtGdiCombineRgn(hRgn, hRgn, hRgnClient, RGN_AND);
|
||||
GreDeleteObject(hRgnClient);
|
||||
RgnClient = IntSysCreateRectpRgnIndirect(&Wnd->rcClient);
|
||||
if (RgnClient)
|
||||
{
|
||||
RgnType = IntGdiCombineRgn(Rgn, Rgn, RgnClient, RGN_AND);
|
||||
REGION_Delete(RgnClient);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -425,21 +448,27 @@ IntInvalidateWindows(PWND Wnd, HRGN hRgn, ULONG Flags)
|
|||
|
||||
if (!Wnd->hrgnClip || (Wnd->style & WS_MINIMIZE))
|
||||
{
|
||||
HRGN hRgnWindow;
|
||||
|
||||
hRgnWindow = IntSysCreateRectRgnIndirect(&Wnd->rcWindow);
|
||||
RgnType = NtGdiCombineRgn(hRgn, hRgn, hRgnWindow, RGN_AND);
|
||||
GreDeleteObject(hRgnWindow);
|
||||
PREGION RgnWindow = IntSysCreateRectpRgnIndirect(&Wnd->rcWindow);
|
||||
if (RgnWindow)
|
||||
{
|
||||
RgnType = IntGdiCombineRgn(Rgn, Rgn, RgnWindow, RGN_AND);
|
||||
REGION_Delete(RgnWindow);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
NtGdiOffsetRgn( hRgn,
|
||||
-Wnd->rcWindow.left,
|
||||
-Wnd->rcWindow.top);
|
||||
RgnType = NtGdiCombineRgn(hRgn, hRgn, Wnd->hrgnClip, RGN_AND);
|
||||
NtGdiOffsetRgn( hRgn,
|
||||
Wnd->rcWindow.left,
|
||||
Wnd->rcWindow.top);
|
||||
PREGION RgnClip = RGNOBJAPI_Lock(Wnd->hrgnClip, NULL);
|
||||
if (RgnClip)
|
||||
{
|
||||
IntGdiOffsetRgn( Rgn,
|
||||
-Wnd->rcWindow.left,
|
||||
-Wnd->rcWindow.top);
|
||||
RgnType = IntGdiCombineRgn(Rgn, Rgn, RgnClip, RGN_AND);
|
||||
IntGdiOffsetRgn( Rgn,
|
||||
Wnd->rcWindow.left,
|
||||
Wnd->rcWindow.top);
|
||||
RGNOBJAPI_Unlock(RgnClip);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -462,6 +491,8 @@ IntInvalidateWindows(PWND Wnd, HRGN hRgn, ULONG Flags)
|
|||
|
||||
if (Flags & RDW_INVALIDATE && RgnType != NULLREGION)
|
||||
{
|
||||
PREGION RgnUpdate;
|
||||
|
||||
Wnd->state &= ~WNDS_NONCPAINT;
|
||||
|
||||
/* If not the same thread set it dirty. */
|
||||
|
@ -479,16 +510,21 @@ IntInvalidateWindows(PWND Wnd, HRGN hRgn, ULONG Flags)
|
|||
|
||||
if (Wnd->hrgnUpdate == NULL)
|
||||
{
|
||||
Wnd->hrgnUpdate = IntSysCreateRectRgn(0, 0, 0, 0);
|
||||
Wnd->hrgnUpdate = NtGdiCreateRectRgn(0, 0, 0, 0);
|
||||
IntGdiSetRegionOwner(Wnd->hrgnUpdate, GDI_OBJ_HMGR_PUBLIC);
|
||||
}
|
||||
|
||||
if (NtGdiCombineRgn(Wnd->hrgnUpdate, Wnd->hrgnUpdate,
|
||||
hRgn, RGN_OR) == NULLREGION)
|
||||
RgnUpdate = RGNOBJAPI_Lock(Wnd->hrgnUpdate, NULL);
|
||||
if (RgnUpdate)
|
||||
{
|
||||
IntGdiSetRegionOwner(Wnd->hrgnUpdate, GDI_OBJ_HMGR_POWNED);
|
||||
GreDeleteObject(Wnd->hrgnUpdate);
|
||||
Wnd->hrgnUpdate = NULL;
|
||||
RgnType = IntGdiCombineRgn(RgnUpdate, RgnUpdate, Rgn, RGN_OR);
|
||||
RGNOBJAPI_Unlock(RgnUpdate);
|
||||
if (RgnType == NULLREGION)
|
||||
{
|
||||
IntGdiSetRegionOwner(Wnd->hrgnUpdate, GDI_OBJ_HMGR_POWNED);
|
||||
GreDeleteObject(Wnd->hrgnUpdate);
|
||||
Wnd->hrgnUpdate = NULL;
|
||||
}
|
||||
}
|
||||
Flags |= RDW_FRAME; // For children.
|
||||
}
|
||||
|
@ -511,13 +547,20 @@ IntInvalidateWindows(PWND Wnd, HRGN hRgn, ULONG Flags)
|
|||
|
||||
if (Wnd->hrgnUpdate != NULL)
|
||||
{
|
||||
if (NtGdiCombineRgn(Wnd->hrgnUpdate, Wnd->hrgnUpdate,
|
||||
hRgn, RGN_DIFF) == NULLREGION)
|
||||
{
|
||||
IntGdiSetRegionOwner(Wnd->hrgnUpdate, GDI_OBJ_HMGR_POWNED);
|
||||
GreDeleteObject(Wnd->hrgnUpdate);
|
||||
Wnd->hrgnUpdate = NULL;
|
||||
}
|
||||
PREGION RgnUpdate = RGNOBJAPI_Lock(Wnd->hrgnUpdate, NULL);
|
||||
|
||||
if (RgnUpdate)
|
||||
{
|
||||
RgnType = IntGdiCombineRgn(RgnUpdate, RgnUpdate, Rgn, RGN_DIFF);
|
||||
RGNOBJAPI_Unlock(RgnUpdate);
|
||||
|
||||
if(RgnType == NULLREGION)
|
||||
{
|
||||
IntGdiSetRegionOwner(Wnd->hrgnUpdate, GDI_OBJ_HMGR_POWNED);
|
||||
GreDeleteObject(Wnd->hrgnUpdate);
|
||||
Wnd->hrgnUpdate = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (Wnd->hrgnUpdate == NULL)
|
||||
|
@ -541,10 +584,13 @@ IntInvalidateWindows(PWND Wnd, HRGN hRgn, ULONG Flags)
|
|||
/*
|
||||
* Recursive call to update children hrgnUpdate
|
||||
*/
|
||||
HRGN hRgnTemp = IntSysCreateRectRgn(0, 0, 0, 0);
|
||||
NtGdiCombineRgn(hRgnTemp, hRgn, 0, RGN_COPY);
|
||||
IntInvalidateWindows(Child, hRgnTemp, Flags);
|
||||
GreDeleteObject(hRgnTemp);
|
||||
PREGION RgnTemp = IntSysCreateRectpRgn(0, 0, 0, 0);
|
||||
if (RgnTemp)
|
||||
{
|
||||
IntGdiCombineRgn(RgnTemp, Rgn, 0, RGN_COPY);
|
||||
IntInvalidateWindows(Child, RgnTemp, Flags);
|
||||
REGION_Delete(RgnTemp);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -602,10 +648,10 @@ BOOL FASTCALL
|
|||
co_UserRedrawWindow(
|
||||
PWND Window,
|
||||
const RECTL* UpdateRect,
|
||||
HRGN UpdateRgn,
|
||||
PREGION UpdateRgn,
|
||||
ULONG Flags)
|
||||
{
|
||||
HRGN hRgn = NULL;
|
||||
PREGION TmpRgn = NULL;
|
||||
TRACE("co_UserRedrawWindow start\n");
|
||||
|
||||
/*
|
||||
|
@ -626,35 +672,37 @@ co_UserRedrawWindow(
|
|||
|
||||
if (Flags & (RDW_INVALIDATE | RDW_VALIDATE)) // Both are OKAY!
|
||||
{
|
||||
if (UpdateRgn != NULL)
|
||||
if (UpdateRgn)
|
||||
{
|
||||
hRgn = IntSysCreateRectRgn(0, 0, 0, 0);
|
||||
if (NtGdiCombineRgn(hRgn, UpdateRgn, NULL, RGN_COPY) == NULLREGION)
|
||||
{
|
||||
GreDeleteObject(hRgn);
|
||||
hRgn = NULL;
|
||||
}
|
||||
else
|
||||
NtGdiOffsetRgn(hRgn, Window->rcClient.left, Window->rcClient.top);
|
||||
TmpRgn = IntSysCreateRectpRgn(0, 0, 0, 0);
|
||||
if (IntGdiCombineRgn(TmpRgn, UpdateRgn, NULL, RGN_COPY) == NULLREGION)
|
||||
{
|
||||
REGION_Delete(TmpRgn);
|
||||
TmpRgn = NULL;
|
||||
}
|
||||
else
|
||||
{
|
||||
IntGdiOffsetRgn(TmpRgn, Window->rcClient.left, Window->rcClient.top);
|
||||
}
|
||||
}
|
||||
else if (UpdateRect != NULL)
|
||||
{
|
||||
if (!RECTL_bIsEmptyRect(UpdateRect))
|
||||
{
|
||||
hRgn = IntSysCreateRectRgnIndirect((RECTL *)UpdateRect);
|
||||
NtGdiOffsetRgn(hRgn, Window->rcClient.left, Window->rcClient.top);
|
||||
TmpRgn = IntSysCreateRectpRgnIndirect(UpdateRect);
|
||||
IntGdiOffsetRgn(TmpRgn, Window->rcClient.left, Window->rcClient.top);
|
||||
}
|
||||
}
|
||||
else if ((Flags & (RDW_INVALIDATE | RDW_FRAME)) == (RDW_INVALIDATE | RDW_FRAME) ||
|
||||
(Flags & (RDW_VALIDATE | RDW_NOFRAME)) == (RDW_VALIDATE | RDW_NOFRAME))
|
||||
{
|
||||
if (!RECTL_bIsEmptyRect(&Window->rcWindow))
|
||||
hRgn = IntSysCreateRectRgnIndirect(&Window->rcWindow);
|
||||
TmpRgn = IntSysCreateRectpRgnIndirect(&Window->rcWindow);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!RECTL_bIsEmptyRect(&Window->rcClient))
|
||||
hRgn = IntSysCreateRectRgnIndirect(&Window->rcClient);
|
||||
TmpRgn = IntSysCreateRectpRgnIndirect(&Window->rcClient);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -664,9 +712,9 @@ co_UserRedrawWindow(
|
|||
*/
|
||||
|
||||
if (Flags & (RDW_INVALIDATE | RDW_VALIDATE | RDW_INTERNALPAINT | RDW_NOINTERNALPAINT) &&
|
||||
hRgn != NULL)
|
||||
TmpRgn != NULL)
|
||||
{
|
||||
IntInvalidateWindows(Window, hRgn, Flags);
|
||||
IntInvalidateWindows(Window, TmpRgn, Flags);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -685,9 +733,9 @@ co_UserRedrawWindow(
|
|||
* Cleanup ;-)
|
||||
*/
|
||||
|
||||
if (hRgn != NULL)
|
||||
if (TmpRgn != NULL)
|
||||
{
|
||||
GreDeleteObject(hRgn);
|
||||
REGION_Delete(TmpRgn);
|
||||
}
|
||||
TRACE("co_UserRedrawWindow exit\n");
|
||||
|
||||
|
@ -991,7 +1039,7 @@ IntBeginPaint(PWND Window, PPAINTSTRUCT Ps)
|
|||
for (Child = Window->spwndChild; Child; Child = Child->spwndNext)
|
||||
{
|
||||
if (Child->hrgnUpdate == NULL && Child->state & WNDS_SENDNCPAINT) // Helped fixing test_redrawnow.
|
||||
IntInvalidateWindows(Child, Window->hrgnUpdate, RDW_FRAME | RDW_ERASE | RDW_INVALIDATE | RDW_ALLCHILDREN);
|
||||
IntInvalidateWindows(Child, NULL, RDW_FRAME | RDW_ERASE | RDW_INVALIDATE | RDW_ALLCHILDREN);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1157,33 +1205,39 @@ Exit:
|
|||
}
|
||||
|
||||
INT FASTCALL
|
||||
co_UserGetUpdateRgn(PWND Window, HRGN hRgn, BOOL bErase)
|
||||
co_UserGetUpdateRgn(PWND Window, PREGION Rgn, BOOL bErase)
|
||||
{
|
||||
int RegionType;
|
||||
RECTL Rect;
|
||||
int RegionType;
|
||||
RECTL Rect;
|
||||
PREGION UpdateRgn;
|
||||
|
||||
ASSERT_REFS_CO(Window);
|
||||
ASSERT_REFS_CO(Window);
|
||||
|
||||
Window->state &= ~WNDS_UPDATEDIRTY;
|
||||
Window->state &= ~WNDS_UPDATEDIRTY;
|
||||
|
||||
if (Window->hrgnUpdate == NULL)
|
||||
{
|
||||
RegionType = (NtGdiSetRectRgn(hRgn, 0, 0, 0, 0) ? NULLREGION : ERROR);
|
||||
}
|
||||
else
|
||||
{
|
||||
Rect = Window->rcClient;
|
||||
IntIntersectWithParents(Window, &Rect);
|
||||
NtGdiSetRectRgn(hRgn, Rect.left, Rect.top, Rect.right, Rect.bottom);
|
||||
RegionType = NtGdiCombineRgn(hRgn, hRgn, Window->hrgnUpdate, RGN_AND);
|
||||
NtGdiOffsetRgn(hRgn, -Window->rcClient.left, -Window->rcClient.top);
|
||||
}
|
||||
if (Window->hrgnUpdate == NULL)
|
||||
{
|
||||
REGION_SetRectRgn(Rgn, 0, 0, 0, 0);
|
||||
return NULLREGION;
|
||||
}
|
||||
|
||||
UpdateRgn = RGNOBJAPI_Lock(Window->hrgnUpdate, NULL);
|
||||
if (!UpdateRgn)
|
||||
return ERROR;
|
||||
|
||||
Rect = Window->rcClient;
|
||||
IntIntersectWithParents(Window, &Rect);
|
||||
REGION_SetRectRgn(Rgn, Rect.left, Rect.top, Rect.right, Rect.bottom);
|
||||
RegionType = IntGdiCombineRgn(Rgn, Rgn, UpdateRgn, RGN_AND);
|
||||
IntGdiOffsetRgn(Rgn, -Window->rcClient.left, -Window->rcClient.top);
|
||||
|
||||
if (bErase && RegionType != NULLREGION && RegionType != ERROR)
|
||||
{
|
||||
co_UserRedrawWindow(Window, NULL, NULL, RDW_ERASENOW | RDW_NOCHILDREN);
|
||||
}
|
||||
|
||||
RGNOBJAPI_Unlock(UpdateRgn);
|
||||
|
||||
return RegionType;
|
||||
}
|
||||
|
||||
|
@ -1201,6 +1255,7 @@ NtUserGetUpdateRgn(HWND hWnd, HRGN hRgn, BOOL bErase)
|
|||
PWND Window;
|
||||
INT ret;
|
||||
USER_REFERENCE_ENTRY Ref;
|
||||
PREGION Rgn = NULL;
|
||||
|
||||
TRACE("Enter NtUserGetUpdateRgn\n");
|
||||
UserEnterExclusive();
|
||||
|
@ -1210,13 +1265,19 @@ NtUserGetUpdateRgn(HWND hWnd, HRGN hRgn, BOOL bErase)
|
|||
RETURN(ERROR);
|
||||
}
|
||||
|
||||
Rgn = RGNOBJAPI_Lock(hRgn, NULL);
|
||||
if (!Rgn)
|
||||
RETURN(ERROR);
|
||||
|
||||
UserRefObjectCo(Window, &Ref);
|
||||
ret = co_UserGetUpdateRgn(Window, hRgn, bErase);
|
||||
ret = co_UserGetUpdateRgn(Window, Rgn, bErase);
|
||||
UserDerefObjectCo(Window);
|
||||
|
||||
RETURN(ret);
|
||||
|
||||
CLEANUP:
|
||||
if (Rgn)
|
||||
RGNOBJAPI_Unlock(Rgn);
|
||||
TRACE("Leave NtUserGetUpdateRgn, ret=%i\n",_ret_);
|
||||
UserLeave();
|
||||
END_CLEANUP;
|
||||
|
@ -1327,6 +1388,7 @@ NtUserRedrawWindow(
|
|||
BOOL Ret;
|
||||
USER_REFERENCE_ENTRY Ref;
|
||||
NTSTATUS Status = STATUS_SUCCESS;
|
||||
PREGION RgnUpdate = NULL;
|
||||
DECLARE_RETURN(BOOL);
|
||||
|
||||
TRACE("Enter NtUserRedrawWindow\n");
|
||||
|
@ -1365,11 +1427,21 @@ NtUserRedrawWindow(
|
|||
RETURN( FALSE);
|
||||
}
|
||||
|
||||
if (hrgnUpdate)
|
||||
{
|
||||
RgnUpdate = RGNOBJAPI_Lock(hrgnUpdate, NULL);
|
||||
if (!RgnUpdate)
|
||||
{
|
||||
EngSetLastError(ERROR_INVALID_HANDLE);
|
||||
RETURN(FALSE);
|
||||
}
|
||||
}
|
||||
|
||||
UserRefObjectCo(Wnd, &Ref);
|
||||
|
||||
Ret = co_UserRedrawWindow( Wnd,
|
||||
lprcUpdate ? &SafeUpdateRect : NULL,
|
||||
hrgnUpdate,
|
||||
RgnUpdate,
|
||||
flags);
|
||||
|
||||
UserDerefObjectCo(Wnd);
|
||||
|
@ -1377,6 +1449,8 @@ NtUserRedrawWindow(
|
|||
RETURN( Ret);
|
||||
|
||||
CLEANUP:
|
||||
if (RgnUpdate)
|
||||
RGNOBJAPI_Unlock(RgnUpdate);
|
||||
TRACE("Leave NtUserRedrawWindow, ret=%i\n",_ret_);
|
||||
UserLeave();
|
||||
END_CLEANUP;
|
||||
|
@ -1390,7 +1464,7 @@ UserScrollDC(
|
|||
INT dy,
|
||||
const RECTL *prcScroll,
|
||||
const RECTL *prcClip,
|
||||
HRGN hrgnUpdate,
|
||||
PREGION RgnUpdate,
|
||||
RECTL *prcUpdate)
|
||||
{
|
||||
PDC pDC;
|
||||
|
@ -1435,10 +1509,9 @@ UserScrollDC(
|
|||
|
||||
/* Calculate the region that was invalidated by moving or
|
||||
could not be copied, because it was not visible */
|
||||
if (hrgnUpdate || prcUpdate)
|
||||
if (RgnUpdate || prcUpdate)
|
||||
{
|
||||
HRGN hrgnOwn, hrgnTmp;
|
||||
PREGION prgnTmp;
|
||||
PREGION RgnOwn, RgnTmp;
|
||||
|
||||
pDC = DC_LockDc(hDC);
|
||||
if (!pDC)
|
||||
|
@ -1450,44 +1523,38 @@ UserScrollDC(
|
|||
rcDst = rcScroll;
|
||||
RECTL_vOffsetRect(&rcDst, dx, dy);
|
||||
RECTL_bIntersectRect(&rcDst, &rcDst, &rcClip);
|
||||
if (hrgnUpdate)
|
||||
if (RgnUpdate)
|
||||
{
|
||||
hrgnOwn = hrgnUpdate;
|
||||
if (!NtGdiSetRectRgn(hrgnOwn, rcDst.left, rcDst.top, rcDst.right, rcDst.bottom))
|
||||
{
|
||||
DC_UnlockDc(pDC);
|
||||
return ERROR;
|
||||
}
|
||||
RgnOwn = RgnUpdate;
|
||||
REGION_SetRectRgn(RgnOwn, rcDst.left, rcDst.top, rcDst.right, rcDst.bottom);
|
||||
}
|
||||
else
|
||||
{
|
||||
hrgnOwn = IntSysCreateRectRgnIndirect(&rcDst);
|
||||
RgnOwn = IntSysCreateRectpRgnIndirect(&rcDst);
|
||||
}
|
||||
|
||||
/* Add the source rect */
|
||||
hrgnTmp = IntSysCreateRectRgnIndirect(&rcSrc);
|
||||
NtGdiCombineRgn(hrgnOwn, hrgnOwn, hrgnTmp, RGN_OR);
|
||||
RgnTmp = IntSysCreateRectpRgnIndirect(&rcSrc);
|
||||
IntGdiCombineRgn(RgnOwn, RgnOwn, RgnTmp, RGN_OR);
|
||||
|
||||
/* Substract the part of the dest that was visible in source */
|
||||
prgnTmp = RGNOBJAPI_Lock(hrgnTmp, NULL);
|
||||
IntGdiCombineRgn(prgnTmp, prgnTmp, pDC->prgnVis, RGN_AND);
|
||||
RGNOBJAPI_Unlock(prgnTmp);
|
||||
NtGdiOffsetRgn(hrgnTmp, dx, dy);
|
||||
Result = NtGdiCombineRgn(hrgnOwn, hrgnOwn, hrgnTmp, RGN_DIFF);
|
||||
IntGdiCombineRgn(RgnTmp, RgnTmp, pDC->prgnVis, RGN_AND);
|
||||
IntGdiOffsetRgn(RgnTmp, dx, dy);
|
||||
Result = IntGdiCombineRgn(RgnOwn, RgnOwn, RgnTmp, RGN_DIFF);
|
||||
|
||||
/* DO NOT Unlock DC while messing with prgnVis! */
|
||||
DC_UnlockDc(pDC);
|
||||
|
||||
GreDeleteObject(hrgnTmp);
|
||||
REGION_Delete(RgnTmp);
|
||||
|
||||
if (prcUpdate)
|
||||
{
|
||||
IntGdiGetRgnBox(hrgnOwn, prcUpdate);
|
||||
REGION_GetRgnBox(RgnOwn, prcUpdate);
|
||||
}
|
||||
|
||||
if (!hrgnUpdate)
|
||||
if (!RgnUpdate)
|
||||
{
|
||||
GreDeleteObject(hrgnOwn);
|
||||
REGION_Delete(RgnOwn);
|
||||
}
|
||||
}
|
||||
else
|
||||
|
@ -1516,6 +1583,7 @@ NtUserScrollDC(
|
|||
RECTL rcScroll, rcClip, rcUpdate;
|
||||
NTSTATUS Status = STATUS_SUCCESS;
|
||||
DWORD Result;
|
||||
PREGION RgnUpdate = NULL;
|
||||
|
||||
TRACE("Enter NtUserScrollDC\n");
|
||||
UserEnterExclusive();
|
||||
|
@ -1548,12 +1616,19 @@ NtUserScrollDC(
|
|||
RETURN(FALSE);
|
||||
}
|
||||
|
||||
if (hrgnUpdate)
|
||||
{
|
||||
RgnUpdate = RGNOBJAPI_Lock(hrgnUpdate, NULL);
|
||||
if (!RgnUpdate)
|
||||
RETURN(FALSE);
|
||||
}
|
||||
|
||||
Result = UserScrollDC( hDC,
|
||||
dx,
|
||||
dy,
|
||||
prcUnsafeScroll? &rcScroll : 0,
|
||||
prcUnsafeClip? &rcClip : 0,
|
||||
hrgnUpdate,
|
||||
RgnUpdate,
|
||||
prcUnsafeUpdate? &rcUpdate : NULL);
|
||||
if(Result == ERROR)
|
||||
{
|
||||
|
@ -1583,6 +1658,8 @@ NtUserScrollDC(
|
|||
RETURN(TRUE);
|
||||
|
||||
CLEANUP:
|
||||
if (RgnUpdate)
|
||||
RGNOBJAPI_Unlock(RgnUpdate);
|
||||
TRACE("Leave NtUserScrollDC, ret=%lu\n",_ret_);
|
||||
UserLeave();
|
||||
END_CLEANUP;
|
||||
|
@ -1610,7 +1687,7 @@ NtUserScrollWindowEx(
|
|||
INT Result;
|
||||
PWND Window = NULL, CaretWnd;
|
||||
HDC hDC;
|
||||
HRGN hrgnOwn = NULL, hrgnTemp, hrgnWinupd = NULL;
|
||||
PREGION RgnOwn = NULL, RgnTemp, RgnWinupd = NULL;
|
||||
HWND hwndCaret;
|
||||
DWORD dcxflags = 0;
|
||||
int rdw_flags;
|
||||
|
@ -1668,11 +1745,15 @@ NtUserScrollWindowEx(
|
|||
|
||||
if (hrgnUpdate)
|
||||
{
|
||||
hrgnOwn = hrgnUpdate;
|
||||
RgnOwn = RGNOBJAPI_Lock(hrgnUpdate, NULL);
|
||||
if (!RgnOwn)
|
||||
{
|
||||
RETURN(ERROR);
|
||||
}
|
||||
bOwnRgn = FALSE;
|
||||
}
|
||||
else
|
||||
hrgnOwn = IntSysCreateRectRgn(0, 0, 0, 0);
|
||||
RgnOwn = IntSysCreateRectpRgn(0, 0, 0, 0);
|
||||
|
||||
/* ScrollWindow uses the window DC, ScrollWindowEx doesn't */
|
||||
if (flags & SW_SCROLLWNDDCE)
|
||||
|
@ -1709,7 +1790,7 @@ NtUserScrollWindowEx(
|
|||
dy,
|
||||
&rcScroll,
|
||||
&rcClip,
|
||||
hrgnOwn,
|
||||
RgnOwn,
|
||||
prcUnsafeUpdate? &rcUpdate : NULL);
|
||||
|
||||
UserReleaseDC(Window, hDC, FALSE);
|
||||
|
@ -1719,22 +1800,29 @@ NtUserScrollWindowEx(
|
|||
* the scroll. Keep a copy in hrgnWinupd to be added to hrngUpdate at the end.
|
||||
*/
|
||||
|
||||
hrgnTemp = IntSysCreateRectRgn(0, 0, 0, 0);
|
||||
if (co_UserGetUpdateRgn(Window, hrgnTemp, FALSE) != NULLREGION)
|
||||
RgnTemp = IntSysCreateRectpRgn(0, 0, 0, 0);
|
||||
if (RgnTemp)
|
||||
{
|
||||
HRGN hrgnClip = IntSysCreateRectRgnIndirect(&rcClip);
|
||||
if (!bOwnRgn)
|
||||
{
|
||||
hrgnWinupd = IntSysCreateRectRgn( 0, 0, 0, 0);
|
||||
NtGdiCombineRgn( hrgnWinupd, hrgnTemp, 0, RGN_COPY);
|
||||
}
|
||||
NtGdiOffsetRgn(hrgnTemp, dx, dy);
|
||||
NtGdiCombineRgn(hrgnTemp, hrgnTemp, hrgnClip, RGN_AND);
|
||||
if (!bOwnRgn) NtGdiCombineRgn( hrgnWinupd, hrgnWinupd, hrgnTemp, RGN_OR );
|
||||
co_UserRedrawWindow(Window, NULL, hrgnTemp, rdw_flags );
|
||||
GreDeleteObject(hrgnClip);
|
||||
if (co_UserGetUpdateRgn(Window, RgnTemp, FALSE) != NULLREGION)
|
||||
{
|
||||
PREGION RgnClip = IntSysCreateRectpRgnIndirect(&rcClip);
|
||||
if (RgnClip)
|
||||
{
|
||||
if (!bOwnRgn)
|
||||
{
|
||||
RgnWinupd = IntSysCreateRectpRgn( 0, 0, 0, 0);
|
||||
IntGdiCombineRgn( RgnWinupd, RgnTemp, 0, RGN_COPY);
|
||||
}
|
||||
IntGdiOffsetRgn(RgnTemp, dx, dy);
|
||||
IntGdiCombineRgn(RgnTemp, RgnTemp, RgnClip, RGN_AND);
|
||||
if (!bOwnRgn)
|
||||
IntGdiCombineRgn( RgnWinupd, RgnWinupd, RgnTemp, RGN_OR );
|
||||
co_UserRedrawWindow(Window, NULL, RgnTemp, rdw_flags );
|
||||
REGION_Delete(RgnClip);
|
||||
}
|
||||
}
|
||||
REGION_Delete(RgnTemp);
|
||||
}
|
||||
GreDeleteObject(hrgnTemp);
|
||||
|
||||
if (flags & SW_SCROLLCHILDREN)
|
||||
{
|
||||
|
@ -1766,7 +1854,7 @@ NtUserScrollWindowEx(
|
|||
|
||||
if (flags & (SW_INVALIDATE | SW_ERASE))
|
||||
{
|
||||
co_UserRedrawWindow(Window, NULL, hrgnOwn, rdw_flags |
|
||||
co_UserRedrawWindow(Window, NULL, RgnOwn, rdw_flags |
|
||||
((flags & SW_ERASE) ? RDW_ERASENOW : 0) |
|
||||
((flags & SW_SCROLLCHILDREN) ? RDW_ALLCHILDREN : 0));
|
||||
}
|
||||
|
@ -1805,15 +1893,19 @@ NtUserScrollWindowEx(
|
|||
RETURN(Result);
|
||||
|
||||
CLEANUP:
|
||||
if (hrgnWinupd && !bOwnRgn)
|
||||
if (RgnWinupd && !bOwnRgn)
|
||||
{
|
||||
NtGdiCombineRgn( hrgnOwn, hrgnOwn, hrgnWinupd, RGN_OR);
|
||||
GreDeleteObject(hrgnWinupd);
|
||||
IntGdiCombineRgn( RgnOwn, RgnOwn, RgnWinupd, RGN_OR);
|
||||
REGION_Delete(RgnWinupd);
|
||||
}
|
||||
|
||||
if (hrgnOwn && !hrgnUpdate)
|
||||
if (RgnOwn && !hrgnUpdate)
|
||||
{
|
||||
GreDeleteObject(hrgnOwn);
|
||||
REGION_Delete(RgnOwn);
|
||||
}
|
||||
else if (RgnOwn)
|
||||
{
|
||||
RGNOBJAPI_Unlock(RgnOwn);
|
||||
}
|
||||
|
||||
if (Window)
|
||||
|
|
|
@ -1,12 +1,12 @@
|
|||
#pragma once
|
||||
|
||||
BOOL FASTCALL co_UserRedrawWindow(PWND Wnd, const RECTL* UpdateRect, HRGN UpdateRgn, ULONG Flags);
|
||||
VOID FASTCALL IntInvalidateWindows(PWND Window, HRGN hRgn, ULONG Flags);
|
||||
BOOL FASTCALL co_UserRedrawWindow(PWND Wnd, const RECTL* UpdateRect, PREGION UpdateRgn, ULONG Flags);
|
||||
VOID FASTCALL IntInvalidateWindows(PWND Window, PREGION Rgn, ULONG Flags);
|
||||
BOOL FASTCALL IntGetPaintMessage(PWND Window, UINT MsgFilterMin, UINT MsgFilterMax, PTHREADINFO Thread, MSG *Message, BOOL Remove);
|
||||
INT FASTCALL UserRealizePalette(HDC);
|
||||
INT FASTCALL co_UserGetUpdateRgn(PWND, HRGN, BOOL);
|
||||
INT FASTCALL co_UserGetUpdateRgn(PWND, PREGION, BOOL);
|
||||
VOID FASTCALL co_IntPaintWindows(PWND Window, ULONG Flags, BOOL Recurse);
|
||||
BOOL FASTCALL IntValidateParent(PWND Child, HRGN hValidateRgn, BOOL Recurse);
|
||||
BOOL FASTCALL IntValidateParent(PWND Child, PREGION ValidateRgn, BOOL Recurse);
|
||||
BOOL FASTCALL IntIsWindowDirty(PWND);
|
||||
BOOL FASTCALL IntEndPaint(PWND,PPAINTSTRUCT);
|
||||
HDC FASTCALL IntBeginPaint(PWND,PPAINTSTRUCT);
|
||||
|
|
|
@ -793,8 +793,15 @@ NtUserCallHwndParamLock(
|
|||
switch (Routine)
|
||||
{
|
||||
case TWOPARAM_ROUTINE_VALIDATERGN:
|
||||
Ret = (DWORD)co_UserRedrawWindow( Window, NULL, (HRGN)Param, RDW_VALIDATE);
|
||||
break;
|
||||
{
|
||||
PREGION Rgn = RGNOBJAPI_Lock((HRGN)Param, NULL);
|
||||
if (Rgn)
|
||||
{
|
||||
Ret = (DWORD)co_UserRedrawWindow( Window, NULL, Rgn, RDW_VALIDATE);
|
||||
RGNOBJAPI_Unlock(Rgn);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
UserDerefObjectCo(Window);
|
||||
|
|
|
@ -9,14 +9,14 @@
|
|||
#include <win32k.h>
|
||||
DBG_DEFAULT_CHANNEL(UserWinpos);
|
||||
|
||||
HRGN FASTCALL
|
||||
PREGION FASTCALL
|
||||
VIS_ComputeVisibleRegion(
|
||||
PWND Wnd,
|
||||
BOOLEAN ClientArea,
|
||||
BOOLEAN ClipChildren,
|
||||
BOOLEAN ClipSiblings)
|
||||
{
|
||||
HRGN VisRgn, ClipRgn;
|
||||
PREGION VisRgn, ClipRgn;
|
||||
PWND PreviousWindow, CurrentWindow, CurrentSibling;
|
||||
|
||||
if (!Wnd || !(Wnd->style & WS_VISIBLE))
|
||||
|
@ -28,11 +28,11 @@ VIS_ComputeVisibleRegion(
|
|||
|
||||
if (ClientArea)
|
||||
{
|
||||
VisRgn = IntSysCreateRectRgnIndirect(&Wnd->rcClient);
|
||||
VisRgn = IntSysCreateRectpRgnIndirect(&Wnd->rcClient);
|
||||
}
|
||||
else
|
||||
{
|
||||
VisRgn = IntSysCreateRectRgnIndirect(&Wnd->rcWindow);
|
||||
VisRgn = IntSysCreateRectpRgnIndirect(&Wnd->rcWindow);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -48,19 +48,21 @@ VIS_ComputeVisibleRegion(
|
|||
if (!VerifyWnd(CurrentWindow))
|
||||
{
|
||||
ERR("ATM the Current Window or Parent is dead! %p\n",CurrentWindow);
|
||||
if (VisRgn) GreDeleteObject(VisRgn);
|
||||
if (VisRgn)
|
||||
REGION_Delete(VisRgn);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!(CurrentWindow->style & WS_VISIBLE))
|
||||
{
|
||||
if (VisRgn) GreDeleteObject(VisRgn);
|
||||
if (VisRgn)
|
||||
REGION_Delete(VisRgn);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ClipRgn = IntSysCreateRectRgnIndirect(&CurrentWindow->rcClient);
|
||||
NtGdiCombineRgn(VisRgn, VisRgn, ClipRgn, RGN_AND);
|
||||
GreDeleteObject(ClipRgn);
|
||||
ClipRgn = IntSysCreateRectpRgnIndirect(&CurrentWindow->rcClient);
|
||||
IntGdiCombineRgn(VisRgn, VisRgn, ClipRgn, RGN_AND);
|
||||
REGION_Delete(ClipRgn);
|
||||
|
||||
if ((PreviousWindow->style & WS_CLIPSIBLINGS) ||
|
||||
(PreviousWindow == Wnd && ClipSiblings))
|
||||
|
@ -72,16 +74,21 @@ VIS_ComputeVisibleRegion(
|
|||
if ((CurrentSibling->style & WS_VISIBLE) &&
|
||||
!(CurrentSibling->ExStyle & WS_EX_TRANSPARENT))
|
||||
{
|
||||
ClipRgn = IntSysCreateRectRgnIndirect(&CurrentSibling->rcWindow);
|
||||
ClipRgn = IntSysCreateRectpRgnIndirect(&CurrentSibling->rcWindow);
|
||||
/* Combine it with the window region if available */
|
||||
if (CurrentSibling->hrgnClip && !(CurrentSibling->style & WS_MINIMIZE))
|
||||
{
|
||||
NtGdiOffsetRgn(ClipRgn, -CurrentSibling->rcWindow.left, -CurrentSibling->rcWindow.top);
|
||||
NtGdiCombineRgn(ClipRgn, ClipRgn, CurrentSibling->hrgnClip, RGN_AND);
|
||||
NtGdiOffsetRgn(ClipRgn, CurrentSibling->rcWindow.left, CurrentSibling->rcWindow.top);
|
||||
PREGION SiblingClipRgn = RGNOBJAPI_Lock(CurrentSibling->hrgnClip, NULL);
|
||||
if (SiblingClipRgn)
|
||||
{
|
||||
IntGdiOffsetRgn(ClipRgn, -CurrentSibling->rcWindow.left, -CurrentSibling->rcWindow.top);
|
||||
IntGdiCombineRgn(ClipRgn, ClipRgn, SiblingClipRgn, RGN_AND);
|
||||
IntGdiOffsetRgn(ClipRgn, CurrentSibling->rcWindow.left, CurrentSibling->rcWindow.top);
|
||||
RGNOBJAPI_Unlock(SiblingClipRgn);
|
||||
}
|
||||
}
|
||||
NtGdiCombineRgn(VisRgn, VisRgn, ClipRgn, RGN_DIFF);
|
||||
GreDeleteObject(ClipRgn);
|
||||
IntGdiCombineRgn(VisRgn, VisRgn, ClipRgn, RGN_DIFF);
|
||||
REGION_Delete(ClipRgn);
|
||||
}
|
||||
CurrentSibling = CurrentSibling->spwndNext;
|
||||
}
|
||||
|
@ -99,16 +106,20 @@ VIS_ComputeVisibleRegion(
|
|||
if ((CurrentWindow->style & WS_VISIBLE) &&
|
||||
!(CurrentWindow->ExStyle & WS_EX_TRANSPARENT))
|
||||
{
|
||||
ClipRgn = IntSysCreateRectRgnIndirect(&CurrentWindow->rcWindow);
|
||||
ClipRgn = IntSysCreateRectpRgnIndirect(&CurrentWindow->rcWindow);
|
||||
/* Combine it with the window region if available */
|
||||
if (CurrentWindow->hrgnClip && !(CurrentWindow->style & WS_MINIMIZE))
|
||||
{
|
||||
NtGdiOffsetRgn(ClipRgn, -CurrentWindow->rcWindow.left, -CurrentWindow->rcWindow.top);
|
||||
NtGdiCombineRgn(ClipRgn, ClipRgn, CurrentWindow->hrgnClip, RGN_AND);
|
||||
NtGdiOffsetRgn(ClipRgn, CurrentWindow->rcWindow.left, CurrentWindow->rcWindow.top);
|
||||
PREGION CurrentRgnClip = RGNOBJAPI_Lock(CurrentWindow->hrgnClip, NULL);
|
||||
if (CurrentRgnClip)
|
||||
{
|
||||
IntGdiOffsetRgn(ClipRgn, -CurrentWindow->rcWindow.left, -CurrentWindow->rcWindow.top);
|
||||
IntGdiCombineRgn(ClipRgn, ClipRgn, CurrentRgnClip, RGN_AND);
|
||||
IntGdiOffsetRgn(ClipRgn, CurrentWindow->rcWindow.left, CurrentWindow->rcWindow.top);
|
||||
}
|
||||
}
|
||||
NtGdiCombineRgn(VisRgn, VisRgn, ClipRgn, RGN_DIFF);
|
||||
GreDeleteObject(ClipRgn);
|
||||
IntGdiCombineRgn(VisRgn, VisRgn, ClipRgn, RGN_DIFF);
|
||||
REGION_Delete(ClipRgn);
|
||||
}
|
||||
CurrentWindow = CurrentWindow->spwndNext;
|
||||
}
|
||||
|
@ -116,9 +127,14 @@ VIS_ComputeVisibleRegion(
|
|||
|
||||
if (Wnd->hrgnClip && !(Wnd->style & WS_MINIMIZE))
|
||||
{
|
||||
NtGdiOffsetRgn(VisRgn, -Wnd->rcWindow.left, -Wnd->rcWindow.top);
|
||||
NtGdiCombineRgn(VisRgn, VisRgn, Wnd->hrgnClip, RGN_AND);
|
||||
NtGdiOffsetRgn(VisRgn, Wnd->rcWindow.left, Wnd->rcWindow.top);
|
||||
PREGION WndRgnClip = RGNOBJAPI_Lock(Wnd->hrgnClip, NULL);
|
||||
if (WndRgnClip)
|
||||
{
|
||||
IntGdiOffsetRgn(VisRgn, -Wnd->rcWindow.left, -Wnd->rcWindow.top);
|
||||
IntGdiCombineRgn(VisRgn, VisRgn, WndRgnClip, RGN_AND);
|
||||
IntGdiOffsetRgn(VisRgn, Wnd->rcWindow.left, Wnd->rcWindow.top);
|
||||
RGNOBJAPI_Unlock(WndRgnClip);
|
||||
}
|
||||
}
|
||||
|
||||
return VisRgn;
|
||||
|
@ -127,9 +143,8 @@ VIS_ComputeVisibleRegion(
|
|||
VOID FASTCALL
|
||||
co_VIS_WindowLayoutChanged(
|
||||
PWND Wnd,
|
||||
HRGN NewlyExposed)
|
||||
PREGION NewlyExposed)
|
||||
{
|
||||
HRGN Temp;
|
||||
PWND Parent;
|
||||
USER_REFERENCE_ENTRY Ref;
|
||||
|
||||
|
@ -138,20 +153,23 @@ co_VIS_WindowLayoutChanged(
|
|||
Parent = Wnd->spwndParent;
|
||||
if(Parent)
|
||||
{
|
||||
Temp = IntSysCreateRectRgn(0, 0, 0, 0);
|
||||
PREGION TempRgn = IntSysCreateRectpRgn(0, 0, 0, 0);
|
||||
|
||||
NtGdiCombineRgn(Temp, NewlyExposed, NULL, RGN_COPY);
|
||||
NtGdiOffsetRgn(Temp,
|
||||
Wnd->rcWindow.left - Parent->rcClient.left,
|
||||
Wnd->rcWindow.top - Parent->rcClient.top);
|
||||
if (!TempRgn)
|
||||
return;
|
||||
|
||||
UserRefObjectCo(Parent, &Ref);
|
||||
co_UserRedrawWindow(Parent, NULL, Temp,
|
||||
RDW_FRAME | RDW_ERASE | RDW_INVALIDATE |
|
||||
RDW_ALLCHILDREN);
|
||||
UserDerefObjectCo(Parent);
|
||||
IntGdiCombineRgn(TempRgn, NewlyExposed, NULL, RGN_COPY);
|
||||
IntGdiOffsetRgn(TempRgn,
|
||||
Wnd->rcWindow.left - Parent->rcClient.left,
|
||||
Wnd->rcWindow.top - Parent->rcClient.top);
|
||||
|
||||
GreDeleteObject(Temp);
|
||||
UserRefObjectCo(Parent, &Ref);
|
||||
co_UserRedrawWindow(Parent, NULL, TempRgn,
|
||||
RDW_FRAME | RDW_ERASE | RDW_INVALIDATE |
|
||||
RDW_ALLCHILDREN);
|
||||
UserDerefObjectCo(Parent);
|
||||
|
||||
REGION_Delete(TempRgn);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
|
||||
#pragma once
|
||||
|
||||
HRGN FASTCALL VIS_ComputeVisibleRegion(PWND Window, BOOLEAN ClientArea, BOOLEAN ClipChildren, BOOLEAN ClipSiblings);
|
||||
VOID FASTCALL co_VIS_WindowLayoutChanged(PWND Window, HRGN UncoveredRgn);
|
||||
PREGION FASTCALL VIS_ComputeVisibleRegion(PWND Window, BOOLEAN ClientArea, BOOLEAN ClipChildren, BOOLEAN ClipSiblings);
|
||||
VOID FASTCALL co_VIS_WindowLayoutChanged(PWND Window, PREGION UncoveredRgn);
|
||||
|
||||
/* EOF */
|
||||
|
|
|
@ -69,24 +69,10 @@ static
|
|||
PREGION FASTCALL
|
||||
DceGetVisRgn(PWND Window, ULONG Flags, HWND hWndChild, ULONG CFlags)
|
||||
{
|
||||
PREGION RetRgn;
|
||||
HRGN hVisRgn;
|
||||
hVisRgn = VIS_ComputeVisibleRegion( Window,
|
||||
0 == (Flags & DCX_WINDOW),
|
||||
0 != (Flags & DCX_CLIPCHILDREN),
|
||||
0 != (Flags & DCX_CLIPSIBLINGS));
|
||||
|
||||
RetRgn = IntSysCreateRectpRgn(0, 0, 0, 0);
|
||||
|
||||
if (hVisRgn != NULL)
|
||||
{
|
||||
PREGION VisRgn = REGION_LockRgn(hVisRgn);
|
||||
IntGdiCombineRgn(RetRgn, VisRgn, NULL, RGN_COPY);
|
||||
REGION_UnlockRgn(VisRgn);
|
||||
GreDeleteObject(hVisRgn);
|
||||
}
|
||||
|
||||
return RetRgn;
|
||||
return VIS_ComputeVisibleRegion( Window,
|
||||
0 == (Flags & DCX_WINDOW),
|
||||
0 != (Flags & DCX_CLIPCHILDREN),
|
||||
0 != (Flags & DCX_CLIPSIBLINGS));
|
||||
}
|
||||
|
||||
PDCE FASTCALL
|
||||
|
@ -582,11 +568,19 @@ UserGetDCEx(PWND Wnd OPTIONAL, HANDLE ClipRegion, ULONG Flags)
|
|||
{
|
||||
if (!(Flags & DCX_WINDOW))
|
||||
{
|
||||
Dce->hrgnClip = IntSysCreateRectRgnIndirect(&Wnd->rcClient);
|
||||
Dce->hrgnClip = NtGdiCreateRectRgn(
|
||||
Wnd->rcClient.left,
|
||||
Wnd->rcClient.top,
|
||||
Wnd->rcClient.right,
|
||||
Wnd->rcClient.bottom);
|
||||
}
|
||||
else
|
||||
{
|
||||
Dce->hrgnClip = IntSysCreateRectRgnIndirect(&Wnd->rcWindow);
|
||||
Dce->hrgnClip = NtGdiCreateRectRgn(
|
||||
Wnd->rcWindow.left,
|
||||
Wnd->rcWindow.top,
|
||||
Wnd->rcWindow.right,
|
||||
Wnd->rcWindow.bottom);
|
||||
}
|
||||
Dce->DCXFlags &= ~DCX_KEEPCLIPRGN;
|
||||
bUpdateVisRgn = TRUE;
|
||||
|
|
|
@ -1652,13 +1652,10 @@ co_WinPosSetWindowPos(
|
|||
RECTL NewWindowRect;
|
||||
RECTL NewClientRect;
|
||||
RECTL valid_rects[2];
|
||||
PROSRGNDATA VisRgn;
|
||||
HRGN VisBefore = NULL;
|
||||
HRGN VisBeforeJustClient = NULL;
|
||||
HRGN VisAfter = NULL;
|
||||
HRGN DirtyRgn = NULL;
|
||||
HRGN ExposedRgn = NULL;
|
||||
HRGN CopyRgn = NULL;
|
||||
PREGION VisBefore = NULL;
|
||||
PREGION VisBeforeJustClient = NULL;
|
||||
PREGION VisAfter = NULL;
|
||||
PREGION CopyRgn = NULL;
|
||||
ULONG WvrFlags = 0;
|
||||
RECTL OldWindowRect, OldClientRect;
|
||||
int RgnType;
|
||||
|
@ -1736,20 +1733,16 @@ co_WinPosSetWindowPos(
|
|||
{
|
||||
VisBefore = VIS_ComputeVisibleRegion(Window, FALSE, FALSE,
|
||||
(Window->style & WS_CLIPSIBLINGS) ? TRUE : FALSE);
|
||||
VisRgn = NULL;
|
||||
|
||||
if ( VisBefore != NULL &&
|
||||
(VisRgn = (PROSRGNDATA)RGNOBJAPI_Lock(VisBefore, NULL)) &&
|
||||
REGION_Complexity(VisRgn) == NULLREGION )
|
||||
REGION_Complexity(VisBefore) == NULLREGION )
|
||||
{
|
||||
RGNOBJAPI_Unlock(VisRgn);
|
||||
GreDeleteObject(VisBefore);
|
||||
REGION_Delete(VisBefore);
|
||||
VisBefore = NULL;
|
||||
}
|
||||
else if(VisRgn)
|
||||
else if(VisBefore)
|
||||
{
|
||||
RGNOBJAPI_Unlock(VisRgn);
|
||||
NtGdiOffsetRgn(VisBefore, -Window->rcWindow.left, -Window->rcWindow.top);
|
||||
IntGdiOffsetRgn(VisBefore, -Window->rcWindow.left, -Window->rcWindow.top);
|
||||
}
|
||||
|
||||
/* Calculate the non client area for resizes, as this is used in the copy region */
|
||||
|
@ -1757,20 +1750,16 @@ co_WinPosSetWindowPos(
|
|||
{
|
||||
VisBeforeJustClient = VIS_ComputeVisibleRegion(Window, TRUE, FALSE,
|
||||
(Window->style & WS_CLIPSIBLINGS) ? TRUE : FALSE);
|
||||
VisRgn = NULL;
|
||||
|
||||
if ( VisBeforeJustClient != NULL &&
|
||||
(VisRgn = (PROSRGNDATA)RGNOBJAPI_Lock(VisBeforeJustClient, NULL)) &&
|
||||
REGION_Complexity(VisRgn) == NULLREGION )
|
||||
REGION_Complexity(VisBeforeJustClient) == NULLREGION )
|
||||
{
|
||||
RGNOBJAPI_Unlock(VisRgn);
|
||||
GreDeleteObject(VisBeforeJustClient);
|
||||
REGION_Delete(VisBeforeJustClient);
|
||||
VisBeforeJustClient = NULL;
|
||||
}
|
||||
else if(VisRgn)
|
||||
else if(VisBeforeJustClient)
|
||||
{
|
||||
RGNOBJAPI_Unlock(VisRgn);
|
||||
NtGdiOffsetRgn(VisBeforeJustClient, -Window->rcWindow.left, -Window->rcWindow.top);
|
||||
IntGdiOffsetRgn(VisBeforeJustClient, -Window->rcWindow.left, -Window->rcWindow.top);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1843,20 +1832,16 @@ co_WinPosSetWindowPos(
|
|||
/* Determine the new visible region */
|
||||
VisAfter = VIS_ComputeVisibleRegion(Window, FALSE, FALSE,
|
||||
(Window->style & WS_CLIPSIBLINGS) ? TRUE : FALSE);
|
||||
VisRgn = NULL;
|
||||
|
||||
if ( VisAfter != NULL &&
|
||||
(VisRgn = (PROSRGNDATA)RGNOBJAPI_Lock(VisAfter, NULL)) &&
|
||||
REGION_Complexity(VisRgn) == NULLREGION )
|
||||
REGION_Complexity(VisAfter) == NULLREGION )
|
||||
{
|
||||
RGNOBJAPI_Unlock(VisRgn);
|
||||
GreDeleteObject(VisAfter);
|
||||
REGION_Delete(VisAfter);
|
||||
VisAfter = NULL;
|
||||
}
|
||||
else if(VisRgn)
|
||||
else if(VisAfter)
|
||||
{
|
||||
RGNOBJAPI_Unlock(VisRgn);
|
||||
NtGdiOffsetRgn(VisAfter, -Window->rcWindow.left, -Window->rcWindow.top);
|
||||
IntGdiOffsetRgn(VisAfter, -Window->rcWindow.left, -Window->rcWindow.top);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -1882,21 +1867,26 @@ co_WinPosSetWindowPos(
|
|||
* region...)
|
||||
*/
|
||||
|
||||
CopyRgn = IntSysCreateRectRgn(0, 0, 0, 0);
|
||||
CopyRgn = IntSysCreateRectpRgn(0, 0, 0, 0);
|
||||
if (WinPos.flags & SWP_NOSIZE)
|
||||
RgnType = NtGdiCombineRgn(CopyRgn, VisAfter, VisBefore, RGN_AND);
|
||||
RgnType = IntGdiCombineRgn(CopyRgn, VisAfter, VisBefore, RGN_AND);
|
||||
else if (VisBeforeJustClient != NULL)
|
||||
{
|
||||
RgnType = NtGdiCombineRgn(CopyRgn, VisAfter, VisBeforeJustClient, RGN_AND);
|
||||
GreDeleteObject(VisBeforeJustClient);
|
||||
RgnType = IntGdiCombineRgn(CopyRgn, VisAfter, VisBeforeJustClient, RGN_AND);
|
||||
REGION_Delete(VisBeforeJustClient);
|
||||
}
|
||||
|
||||
/* No use in copying bits which are in the update region. */
|
||||
if (Window->hrgnUpdate != NULL)
|
||||
{
|
||||
NtGdiOffsetRgn(CopyRgn, NewWindowRect.left, NewWindowRect.top);
|
||||
NtGdiCombineRgn(CopyRgn, CopyRgn, Window->hrgnUpdate, RGN_DIFF);
|
||||
NtGdiOffsetRgn(CopyRgn, -NewWindowRect.left, -NewWindowRect.top);
|
||||
PREGION RgnUpdate = RGNOBJAPI_Lock(Window->hrgnUpdate, NULL);
|
||||
if (RgnUpdate)
|
||||
{
|
||||
IntGdiOffsetRgn(CopyRgn, NewWindowRect.left, NewWindowRect.top);
|
||||
IntGdiCombineRgn(CopyRgn, CopyRgn, RgnUpdate, RGN_DIFF);
|
||||
IntGdiOffsetRgn(CopyRgn, -NewWindowRect.left, -NewWindowRect.top);
|
||||
RGNOBJAPI_Unlock(RgnUpdate);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -1904,21 +1894,17 @@ co_WinPosSetWindowPos(
|
|||
* there's nothing to copy. Also, it's no use copying bits onto
|
||||
* themselves.
|
||||
*/
|
||||
if ( (VisRgn = (PROSRGNDATA)RGNOBJAPI_Lock(CopyRgn, NULL)) &&
|
||||
REGION_GetRgnBox(VisRgn, &CopyRect) == NULLREGION)
|
||||
if (REGION_GetRgnBox(CopyRgn, &CopyRect) == NULLREGION)
|
||||
{
|
||||
/* Nothing to copy, clean up */
|
||||
RGNOBJAPI_Unlock(VisRgn);
|
||||
GreDeleteObject(CopyRgn);
|
||||
REGION_Delete(CopyRgn);
|
||||
CopyRgn = NULL;
|
||||
}
|
||||
else if (OldWindowRect.left != NewWindowRect.left ||
|
||||
OldWindowRect.top != NewWindowRect.top)
|
||||
{
|
||||
if(VisRgn)
|
||||
{
|
||||
RGNOBJAPI_Unlock(VisRgn);
|
||||
}
|
||||
HRGN DcRgn = NtGdiCreateRectRgn(0, 0, 0, 0);
|
||||
PREGION DcRgnObj = RGNOBJAPI_Lock(DcRgn, NULL);
|
||||
|
||||
/*
|
||||
* Small trick here: there is no function to bitblt a region. So
|
||||
|
@ -1929,9 +1915,11 @@ co_WinPosSetWindowPos(
|
|||
* Since NtUserGetDCEx takes ownership of the clip region, we need
|
||||
* to create a copy of CopyRgn and pass that. We need CopyRgn later
|
||||
*/
|
||||
NtGdiOffsetRgn(CopyRgn, NewWindowRect.left, NewWindowRect.top);
|
||||
IntGdiCombineRgn(DcRgnObj, CopyRgn, NULL, RGN_COPY);
|
||||
IntGdiOffsetRgn(DcRgnObj, NewWindowRect.left, NewWindowRect.top);
|
||||
RGNOBJAPI_Unlock(DcRgnObj);
|
||||
Dc = UserGetDCEx( Window,
|
||||
CopyRgn,
|
||||
DcRgn,
|
||||
DCX_WINDOW|DCX_CACHE|DCX_INTERSECTRGN|DCX_CLIPSIBLINGS|DCX_KEEPCLIPRGN);
|
||||
NtGdiBitBlt( Dc,
|
||||
CopyRect.left, CopyRect.top,
|
||||
|
@ -1946,11 +1934,7 @@ co_WinPosSetWindowPos(
|
|||
|
||||
UserReleaseDC(Window, Dc, FALSE);
|
||||
IntValidateParent(Window, CopyRgn, FALSE);
|
||||
NtGdiOffsetRgn(CopyRgn, -NewWindowRect.left, -NewWindowRect.top);
|
||||
}
|
||||
else if(VisRgn)
|
||||
{
|
||||
RGNOBJAPI_Unlock(VisRgn);
|
||||
GreDeleteObject(DcRgn);
|
||||
}
|
||||
}
|
||||
else
|
||||
|
@ -1961,78 +1945,84 @@ co_WinPosSetWindowPos(
|
|||
/* We need to redraw what wasn't visible before */
|
||||
if (VisAfter != NULL)
|
||||
{
|
||||
DirtyRgn = IntSysCreateRectRgn(0, 0, 0, 0);
|
||||
if (CopyRgn != NULL)
|
||||
PREGION DirtyRgn = IntSysCreateRectpRgn(0, 0, 0, 0);
|
||||
if (DirtyRgn)
|
||||
{
|
||||
RgnType = NtGdiCombineRgn(DirtyRgn, VisAfter, CopyRgn, RGN_DIFF);
|
||||
}
|
||||
else
|
||||
{
|
||||
RgnType = NtGdiCombineRgn(DirtyRgn, VisAfter, 0, RGN_COPY);
|
||||
}
|
||||
if (RgnType != ERROR && RgnType != NULLREGION)
|
||||
{
|
||||
/* old code
|
||||
NtGdiOffsetRgn(DirtyRgn, Window->rcWindow.left, Window->rcWindow.top);
|
||||
IntInvalidateWindows( Window,
|
||||
DirtyRgn,
|
||||
RDW_ERASE | RDW_FRAME | RDW_INVALIDATE | RDW_ALLCHILDREN);
|
||||
}
|
||||
GreDeleteObject(DirtyRgn);
|
||||
*/
|
||||
|
||||
PWND Parent = Window->spwndParent;
|
||||
|
||||
NtGdiOffsetRgn( DirtyRgn,
|
||||
Window->rcWindow.left,
|
||||
Window->rcWindow.top);
|
||||
if ( (Window->style & WS_CHILD) &&
|
||||
(Parent) &&
|
||||
!(Parent->style & WS_CLIPCHILDREN))
|
||||
{
|
||||
IntInvalidateWindows( Parent,
|
||||
DirtyRgn,
|
||||
RDW_ERASE | RDW_INVALIDATE);
|
||||
co_IntPaintWindows(Parent, RDW_ERASENOW, FALSE);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (CopyRgn != NULL)
|
||||
{
|
||||
RgnType = IntGdiCombineRgn(DirtyRgn, VisAfter, CopyRgn, RGN_DIFF);
|
||||
}
|
||||
else
|
||||
{
|
||||
RgnType = IntGdiCombineRgn(DirtyRgn, VisAfter, 0, RGN_COPY);
|
||||
}
|
||||
if (RgnType != ERROR && RgnType != NULLREGION)
|
||||
{
|
||||
/* old code
|
||||
NtGdiOffsetRgn(DirtyRgn, Window->rcWindow.left, Window->rcWindow.top);
|
||||
IntInvalidateWindows( Window,
|
||||
DirtyRgn,
|
||||
RDW_ERASE | RDW_FRAME | RDW_INVALIDATE | RDW_ALLCHILDREN);
|
||||
}
|
||||
RDW_ERASE | RDW_FRAME | RDW_INVALIDATE | RDW_ALLCHILDREN);
|
||||
}
|
||||
GreDeleteObject(DirtyRgn);
|
||||
*/
|
||||
|
||||
PWND Parent = Window->spwndParent;
|
||||
|
||||
IntGdiOffsetRgn( DirtyRgn,
|
||||
Window->rcWindow.left,
|
||||
Window->rcWindow.top);
|
||||
if ( (Window->style & WS_CHILD) &&
|
||||
(Parent) &&
|
||||
!(Parent->style & WS_CLIPCHILDREN))
|
||||
{
|
||||
IntInvalidateWindows( Parent,
|
||||
DirtyRgn,
|
||||
RDW_ERASE | RDW_INVALIDATE);
|
||||
co_IntPaintWindows(Parent, RDW_ERASENOW, FALSE);
|
||||
}
|
||||
else
|
||||
{
|
||||
IntInvalidateWindows( Window,
|
||||
DirtyRgn,
|
||||
RDW_ERASE | RDW_FRAME | RDW_INVALIDATE | RDW_ALLCHILDREN);
|
||||
}
|
||||
}
|
||||
REGION_Delete(DirtyRgn);
|
||||
}
|
||||
GreDeleteObject(DirtyRgn);
|
||||
}
|
||||
|
||||
if (CopyRgn != NULL)
|
||||
{
|
||||
GreDeleteObject(CopyRgn);
|
||||
REGION_Delete(CopyRgn);
|
||||
}
|
||||
|
||||
/* Expose what was covered before but not covered anymore */
|
||||
if (VisBefore != NULL)
|
||||
{
|
||||
ExposedRgn = IntSysCreateRectRgn(0, 0, 0, 0);
|
||||
RgnType = NtGdiCombineRgn(ExposedRgn, VisBefore, NULL, RGN_COPY);
|
||||
NtGdiOffsetRgn( ExposedRgn,
|
||||
OldWindowRect.left - NewWindowRect.left,
|
||||
OldWindowRect.top - NewWindowRect.top);
|
||||
|
||||
if (VisAfter != NULL)
|
||||
RgnType = NtGdiCombineRgn(ExposedRgn, ExposedRgn, VisAfter, RGN_DIFF);
|
||||
|
||||
if (RgnType != ERROR && RgnType != NULLREGION)
|
||||
PREGION ExposedRgn = IntSysCreateRectpRgn(0, 0, 0, 0);
|
||||
if (ExposedRgn)
|
||||
{
|
||||
co_VIS_WindowLayoutChanged(Window, ExposedRgn);
|
||||
RgnType = IntGdiCombineRgn(ExposedRgn, VisBefore, NULL, RGN_COPY);
|
||||
IntGdiOffsetRgn( ExposedRgn,
|
||||
OldWindowRect.left - NewWindowRect.left,
|
||||
OldWindowRect.top - NewWindowRect.top);
|
||||
|
||||
if (VisAfter != NULL)
|
||||
RgnType = IntGdiCombineRgn(ExposedRgn, ExposedRgn, VisAfter, RGN_DIFF);
|
||||
|
||||
if (RgnType != ERROR && RgnType != NULLREGION)
|
||||
{
|
||||
co_VIS_WindowLayoutChanged(Window, ExposedRgn);
|
||||
}
|
||||
REGION_Delete(ExposedRgn);
|
||||
}
|
||||
GreDeleteObject(ExposedRgn);
|
||||
GreDeleteObject(VisBefore);
|
||||
REGION_Delete(VisBefore);
|
||||
}
|
||||
|
||||
if (VisAfter != NULL)
|
||||
{
|
||||
GreDeleteObject(VisAfter);
|
||||
REGION_Delete(VisAfter);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3112,7 +3102,7 @@ NtUserSetWindowRgn(
|
|||
HRGN hRgn,
|
||||
BOOL bRedraw)
|
||||
{
|
||||
HRGN hrgnCopy;
|
||||
HRGN hrgnCopy = NULL;
|
||||
PWND Window;
|
||||
INT flags = (SWP_NOCLIENTSIZE|SWP_NOCLIENTMOVE|SWP_NOACTIVATE|SWP_FRAMECHANGED|SWP_NOSIZE|SWP_NOMOVE);
|
||||
BOOLEAN Ret = FALSE;
|
||||
|
@ -3132,7 +3122,7 @@ NtUserSetWindowRgn(
|
|||
{
|
||||
if (GreIsHandleValid(hRgn))
|
||||
{
|
||||
hrgnCopy = IntSysCreateRectRgn(0, 0, 0, 0);
|
||||
hrgnCopy = NtGdiCreateRectRgn(0, 0, 0, 0);
|
||||
/* The coordinates of a window's window region are relative to the
|
||||
upper-left corner of the window, not the client area of the window. */
|
||||
NtGdiCombineRgn( hrgnCopy, hRgn, 0, RGN_COPY);
|
||||
|
@ -3140,10 +3130,6 @@ NtUserSetWindowRgn(
|
|||
else
|
||||
RETURN( 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
hrgnCopy = NULL;
|
||||
}
|
||||
|
||||
if (Window->hrgnClip)
|
||||
{
|
||||
|
|
Loading…
Reference in a new issue