[ros-diffs] [fireball] 44112: - Implement GetDC/ReleaseDC for window manager with clipping support. This addresses the invalid drawing order "bug", which is in fact a feature. Client window manager is responsible for compositing all windows in a given rectangle being redrawn. Arwinss implements a very simple client window manager (SWM) which just clips out all contents behind the window on top of a z order. - Notify SWM about a new (or an existing) desktop window. - Fix comment typos.

fireball at svn.reactos.org fireball at svn.reactos.org
Wed Nov 11 20:55:22 CET 2009


Author: fireball
Date: Wed Nov 11 20:55:22 2009
New Revision: 44112

URL: http://svn.reactos.org/svn/reactos?rev=44112&view=rev
Log:
- Implement GetDC/ReleaseDC for window manager with clipping support. This addresses the invalid drawing order "bug", which is in fact a feature. Client window manager is responsible for compositing all windows in a given rectangle being redrawn. Arwinss implements a very simple client window manager (SWM) which just clips out all contents behind the window on top of a z order.
- Notify SWM about a new (or an existing) desktop window.
- Fix comment typos.

Modified:
    branches/arwinss/reactos/dll/win32/winent.drv/gdidrv.c
    branches/arwinss/reactos/dll/win32/winent.drv/userdrv.c
    branches/arwinss/reactos/dll/win32/winent.drv/winent.h
    branches/arwinss/reactos/include/psdk/ntrosgdi.h
    branches/arwinss/reactos/include/reactos/win32k/rosuser.h
    branches/arwinss/reactos/subsystems/win32/win32k/gdi/dc.c
    branches/arwinss/reactos/subsystems/win32/win32k/gre/surfobj.c
    branches/arwinss/reactos/subsystems/win32/win32k/include/dc.h
    branches/arwinss/reactos/subsystems/win32/win32k/w32ksvc.db

Modified: branches/arwinss/reactos/dll/win32/winent.drv/gdidrv.c
URL: http://svn.reactos.org/svn/reactos/branches/arwinss/reactos/dll/win32/winent.drv/gdidrv.c?rev=44112&r1=44111&r2=44112&view=diff
==============================================================================
--- branches/arwinss/reactos/dll/win32/winent.drv/gdidrv.c [iso-8859-1] (original)
+++ branches/arwinss/reactos/dll/win32/winent.drv/gdidrv.c [iso-8859-1] Wed Nov 11 20:55:22 2009
@@ -228,6 +228,12 @@
                 {
                     const struct ntdrv_escape_set_drawable *data = in_data;
                     RosGdiSetDcRects(physDev->hKernelDC, (RECT*)&data->dc_rect, (RECT*)&data->drawable_rect);
+
+                    if (!data->release)
+                        RosGdiGetDC(physDev->hKernelDC, data->hwnd, data->clip_children);
+                    else
+                        RosGdiReleaseDC(physDev->hKernelDC);
+
                     TRACE( "SET_DRAWABLE hdc %p dc_rect %s drawable_rect %s\n",
                            physDev->hUserDC, wine_dbgstr_rect(&data->dc_rect), wine_dbgstr_rect(&data->drawable_rect) );
                     return TRUE;

Modified: branches/arwinss/reactos/dll/win32/winent.drv/userdrv.c
URL: http://svn.reactos.org/svn/reactos/branches/arwinss/reactos/dll/win32/winent.drv/userdrv.c?rev=44112&r1=44111&r2=44112&view=diff
==============================================================================
--- branches/arwinss/reactos/dll/win32/winent.drv/userdrv.c [iso-8859-1] (original)
+++ branches/arwinss/reactos/dll/win32/winent.drv/userdrv.c [iso-8859-1] Wed Nov 11 20:55:22 2009
@@ -458,6 +458,8 @@
 
     TRACE("RosDrv_CreateDesktopWindow(%x), w %d h %d\n", hwnd, width, height);
 
+    SwmAddDesktopWindow(hwnd, width, height);
+
     if (!width && !height)  /* not initialized yet */
     {
         SERVER_START_REQ( set_window_pos )
@@ -490,27 +492,25 @@
     NTDRV_destroy_win_data( hwnd );
 }
 
-void CDECL RosDrv_GetDC( HDC hdc, HWND hwnd, HWND top_win, const RECT *win_rect,
+void CDECL RosDrv_GetDC( HDC hdc, HWND hwnd, HWND top, const RECT *win_rect,
                                  const RECT *top_rect, DWORD flags )
 {
     struct ntdrv_escape_set_drawable escape;
-    //struct ntdrv_win_data *data = X11DRV_get_win_data( hwnd );
+    struct ntdrv_win_data *data = NTDRV_get_win_data( hwnd );
 
     escape.code        = NTDRV_SET_DRAWABLE;
-    //escape.mode        = IncludeInferiors;
-    //escape.fbconfig_id = 0;
-    //escape.gl_drawable = 0;
-    //escape.pixmap      = 0;
+    escape.clip_children = FALSE;
     escape.gl_copy     = FALSE;
-
-#if 0
-    if (top == hwnd && data && IsIconic( hwnd ) && data->icon_window)
+    escape.hwnd        = hwnd;
+    escape.release     = FALSE;
+
+    if (top == hwnd && data && IsIconic( hwnd ) /*&& data->icon_window*/)
     {
         //escape.drawable = data->icon_window;
     }
     else if (top == hwnd)
     {
-        escape.fbconfig_id = data ? data->fbconfig_id : (XID)GetPropA( hwnd, fbconfig_id_prop );
+        //escape.fbconfig_id = data ? data->fbconfig_id : (XID)GetPropA( hwnd, fbconfig_id_prop );
         /* GL draws to the client area even for window DCs */
         /*escape.gl_drawable = data ? data->client_window : X11DRV_get_client_window( hwnd );
         if (flags & DCX_WINDOW)
@@ -525,9 +525,9 @@
         //escape.gl_drawable = data ? data->gl_drawable : (Drawable)GetPropA( hwnd, gl_drawable_prop );
         //escape.pixmap      = data ? data->pixmap : (Pixmap)GetPropA( hwnd, pixmap_prop );
         //escape.gl_copy     = (escape.gl_drawable != 0);
-        if (flags & DCX_CLIPCHILDREN) escape.mode = ClipByChildren;
-    }
-#endif
+
+        if (flags & DCX_CLIPCHILDREN) escape.clip_children = TRUE;
+    }
 
     escape.dc_rect.left         = win_rect->left - top_rect->left;
     escape.dc_rect.top          = win_rect->top - top_rect->top;
@@ -544,7 +544,7 @@
 DWORD CDECL RosDrv_MsgWaitForMultipleObjectsEx( DWORD count, const HANDLE *handles, DWORD timeout,
                                                         DWORD mask, DWORD flags )
 {
-    TRACE("WaitForMultipleObjectsEx(%d %p %d %x %x %x\n", count, handles, timeout, mask, flags);
+    //TRACE("WaitForMultipleObjectsEx(%d %p %d %x %x %x\n", count, handles, timeout, mask, flags);
 
     if (!count && !timeout) return WAIT_TIMEOUT;
     return WaitForMultipleObjectsEx( count, handles, flags & MWMO_WAITALL,
@@ -557,6 +557,8 @@
 
     escape.code        = NTDRV_SET_DRAWABLE;
     escape.gl_copy     = FALSE;
+    escape.hwnd        = hwnd;
+    escape.release     = TRUE;
 
     escape.dc_rect.left         = 0;
     escape.dc_rect.top          = 0;
@@ -840,8 +842,8 @@
 
     if (!data) return;
 
-    TRACE( "win %x pos changed. new vis rect %s, old whole rect %s\n",
-           hwnd, wine_dbgstr_rect(visible_rect), wine_dbgstr_rect(&data->whole_rect) );
+    TRACE( "win %x pos changed. new vis rect %s, old whole rect %s, swp_flags %x\n",
+           hwnd, wine_dbgstr_rect(visible_rect), wine_dbgstr_rect(&data->whole_rect), swp_flags );
 
     old_whole_rect  = data->whole_rect;
     old_client_rect = data->client_rect;
@@ -864,15 +866,17 @@
             old_client_rect.bottom - data->client_rect.bottom == y_offset &&
             !memcmp( &valid_rects[0], &data->client_rect, sizeof(RECT) ))
         {
-             //move_window_bits( data, &old_whole_rect, &data->whole_rect, &old_client_rect );
+            //move_window_bits( data, &old_whole_rect, &data->whole_rect, &old_client_rect );
             SwmPosChanged(hwnd, &data->whole_rect, &old_whole_rect);
+            FIXME("change1\n");
         }
         else
         {
-            //move_window_bits( data, &valid_rects[1], &valid_rects[0], &old_client_rect );
+            move_window_bits( data, &valid_rects[1], &valid_rects[0], &old_client_rect );
+            FIXME("change2\n");
         }
     }
-
+// visible: 0x1843, hide: 0x1883. 1843 = 1 + 2 + 64 + 2048 + 4096
     //RosDrv_UpdateZOrder(hwnd, (RECT*)visible_rect);
 }
 

Modified: branches/arwinss/reactos/dll/win32/winent.drv/winent.h
URL: http://svn.reactos.org/svn/reactos/branches/arwinss/reactos/dll/win32/winent.drv/winent.h?rev=44112&r1=44111&r2=44112&view=diff
==============================================================================
--- branches/arwinss/reactos/dll/win32/winent.drv/winent.h [iso-8859-1] (original)
+++ branches/arwinss/reactos/dll/win32/winent.drv/winent.h [iso-8859-1] Wed Nov 11 20:55:22 2009
@@ -19,14 +19,12 @@
 struct ntdrv_escape_set_drawable
 {
     enum ntdrv_escape_codes  code;         /* escape code (X11DRV_SET_DRAWABLE) */
-    //Drawable                 drawable;     /* X drawable */
-    int                      mode;         /* ClipByChildren or IncludeInferiors */
+    BOOL                     clip_children;/* ClipByChildren or IncludeInferiors */
     RECT                     dc_rect;      /* DC rectangle relative to drawable */
     RECT                     drawable_rect;/* Drawable rectangle relative to screen */
-    //XID                      fbconfig_id;  /* fbconfig id used by the GL drawable */
-    //Drawable                 gl_drawable;  /* GL drawable */
-    //Pixmap                   pixmap;       /* Pixmap for a GLXPixmap gl_drawable */
+    HWND                     hwnd;         /* hwnd of which the GetDC is performed */
     int                      gl_copy;      /* whether the GL contents need explicit copying */
+    BOOL                     release;      /* whether the DC is acquired or released */
 };
 
 /* ntdrv private window data */

Modified: branches/arwinss/reactos/include/psdk/ntrosgdi.h
URL: http://svn.reactos.org/svn/reactos/branches/arwinss/reactos/include/psdk/ntrosgdi.h?rev=44112&r1=44111&r2=44112&view=diff
==============================================================================
--- branches/arwinss/reactos/include/psdk/ntrosgdi.h [iso-8859-1] (original)
+++ branches/arwinss/reactos/include/psdk/ntrosgdi.h [iso-8859-1] Wed Nov 11 20:55:22 2009
@@ -119,6 +119,8 @@
 COLORREF APIENTRY RosGdiSetTextColor( HDC physDev, COLORREF color );
 VOID APIENTRY RosGdiSetDcRects( HDC physDev, RECT *rcDcRect, RECT *rcVport );
 VOID APIENTRY RosGdiGetDcRects( HDC physDev, RECT *rcDcRect, RECT *rcVport );
+VOID APIENTRY RosGdiGetDC( HDC physDev, HWND hwnd, BOOL clipChildren );
+VOID APIENTRY RosGdiReleaseDC( HDC physDev );
 
 /* enum.c */
 int APIENTRY RosGdiChoosePixelFormat(HDC physDev,

Modified: branches/arwinss/reactos/include/reactos/win32k/rosuser.h
URL: http://svn.reactos.org/svn/reactos/branches/arwinss/reactos/include/reactos/win32k/rosuser.h?rev=44112&r1=44111&r2=44112&view=diff
==============================================================================
--- branches/arwinss/reactos/include/reactos/win32k/rosuser.h [iso-8859-1] (original)
+++ branches/arwinss/reactos/include/reactos/win32k/rosuser.h [iso-8859-1] Wed Nov 11 20:55:22 2009
@@ -140,6 +140,9 @@
 SwmAddWindow(HWND hWnd, RECT *WindowRect);
 
 VOID NTAPI
+SwmAddDesktopWindow(HWND hWnd, UINT Width, UINT Height);
+
+VOID NTAPI
 SwmRemoveWindow(HWND hWnd);
 
 VOID NTAPI

Modified: branches/arwinss/reactos/subsystems/win32/win32k/gdi/dc.c
URL: http://svn.reactos.org/svn/reactos/branches/arwinss/reactos/subsystems/win32/win32k/gdi/dc.c?rev=44112&r1=44111&r2=44112&view=diff
==============================================================================
--- branches/arwinss/reactos/subsystems/win32/win32k/gdi/dc.c [iso-8859-1] (original)
+++ branches/arwinss/reactos/subsystems/win32/win32k/gdi/dc.c [iso-8859-1] Wed Nov 11 20:55:22 2009
@@ -9,6 +9,11 @@
 /* INCLUDES ******************************************************************/
 
 #include <win32k.h>
+
+#include "object.h"
+#include "handle.h"
+#include "user.h"
+
 #define NDEBUG
 #include <debug.h>
 
@@ -143,6 +148,7 @@
 
     /* Create an empty combined clipping region */
     pNewDC->CombinedClip = EngCreateClip();
+    pNewDC->Clipping = create_empty_region();
 
     /* Set default palette */
     pNewDC->hPalette = hSystemPal;
@@ -447,6 +453,36 @@
     return 0;
 }
 
+VOID APIENTRY RosGdiUpdateClipping(PDC pDC)
+{
+    struct region *inter;
+    if (!pDC->pWindow)
+    {
+        /* Easy case, just copy the existing clipping region */
+        if (pDC->CombinedClip) EngDeleteClip(pDC->CombinedClip);
+        pDC->CombinedClip = IntEngCreateClipRegionFromRegion(pDC->Clipping);
+    }
+    else
+    {
+        /* Intersect with window's visibility */
+        inter = create_empty_region();
+        copy_region(inter, pDC->Clipping);
+
+        /* Acquire SWM lock */
+        SwmAcquire();
+
+        /* Intersect current clipping region and window's visible region */
+        intersect_region(inter, inter, pDC->pWindow->Visible);
+
+        /* Release SWM lock */
+        SwmRelease();
+
+        if (pDC->CombinedClip) EngDeleteClip(pDC->CombinedClip);
+        pDC->CombinedClip = IntEngCreateClipRegionFromRegion(inter);
+        free_region(inter);
+    }
+}
+
 void APIENTRY RosGdiSetDeviceClipping( HDC physDev, UINT count, PRECTL pRects, PRECTL rcBounds )
 {
     PDC pDC;
@@ -510,8 +546,8 @@
                       pDC->rcDcRect.top + pDC->rcVport.top);
 
     /* Delete old clipping region */
-    if (pDC->CombinedClip)
-        IntEngDeleteClipRegion(pDC->CombinedClip);
+    if (pDC->Clipping)
+        free_region(pDC->Clipping);
 
     if (count == 0)
     {
@@ -534,12 +570,12 @@
         RECTL_bIntersectRect(&rcSafeBounds, &rcSafeBounds, &rcSurface);
 
         /* Set the clipping object */
-        pDC->CombinedClip = IntEngCreateClipRegion(1, &rcSafeBounds, &rcSafeBounds);
+        pDC->Clipping = create_region_from_rects(&rcSafeBounds, 1);
     }
     else
     {
         /* Set the clipping object */
-        pDC->CombinedClip = IntEngCreateClipRegion(count, pSafeRects, &rcSafeBounds);
+        pDC->Clipping = create_region_from_rects(pSafeRects, count);
     }
 
     DPRINT("RosGdiSetDeviceClipping() for DC %x, bounding rect (%d,%d)-(%d, %d)\n",
@@ -550,6 +586,9 @@
     {
         DPRINT("%d: (%d,%d)-(%d, %d)\n", i, pSafeRects[i].left, pSafeRects[i].top, pSafeRects[i].right, pSafeRects[i].bottom);
     }
+
+    /* Update the combined clipping */
+    RosGdiUpdateClipping(pDC);
 
     /* Release the object */
     DC_Unlock(pDC);
@@ -641,4 +680,38 @@
     DC_Unlock(pDC);
 }
 
+VOID APIENTRY RosGdiGetDC(HDC physDev, HWND hwnd, BOOL clipChildren)
+{
+    PDC pDC;
+
+    /* Acquire SWM lock before locking the DC */
+    SwmAcquire();
+
+    /* Get a pointer to the DC */
+    pDC = DC_Lock(physDev);
+
+    /* Get a pointer to this window */
+    pDC->pWindow = SwmFindByHwnd(hwnd);
+
+    /* Release the object */
+    DC_Unlock(pDC);
+
+    /* Release SWM lock */
+    SwmRelease();
+}
+
+VOID APIENTRY RosGdiReleaseDC(HDC physDev)
+{
+    PDC pDC;
+
+    /* Get a pointer to the DC */
+    pDC = DC_Lock(physDev);
+
+    /* No window clipping is to be performed */
+    pDC->pWindow = NULL;
+
+    /* Release the object */
+    DC_Unlock(pDC);
+}
+
 /* EOF */

Modified: branches/arwinss/reactos/subsystems/win32/win32k/gre/surfobj.c
URL: http://svn.reactos.org/svn/reactos/branches/arwinss/reactos/subsystems/win32/win32k/gre/surfobj.c?rev=44112&r1=44111&r2=44112&view=diff
==============================================================================
--- branches/arwinss/reactos/subsystems/win32/win32k/gre/surfobj.c [iso-8859-1] (original)
+++ branches/arwinss/reactos/subsystems/win32/win32k/gre/surfobj.c [iso-8859-1] Wed Nov 11 20:55:22 2009
@@ -298,7 +298,7 @@
     x += pDC->rcVport.left + pDC->rcDcRect.left;
     y += pDC->rcVport.top + pDC->rcDcRect.top;
 
-    /* If points is outside combined clipping region - return error */
+    /* If point is outside the combined clipping region - return error */
     if (!RECTL_bPointInRect(&pDC->CombinedClip->rclBounds, x, y))
         return CLR_INVALID;
 

Modified: branches/arwinss/reactos/subsystems/win32/win32k/include/dc.h
URL: http://svn.reactos.org/svn/reactos/branches/arwinss/reactos/subsystems/win32/win32k/include/dc.h?rev=44112&r1=44111&r2=44112&view=diff
==============================================================================
--- branches/arwinss/reactos/subsystems/win32/win32k/include/dc.h [iso-8859-1] (original)
+++ branches/arwinss/reactos/subsystems/win32/win32k/include/dc.h [iso-8859-1] Wed Nov 11 20:55:22 2009
@@ -20,7 +20,9 @@
     POINT        ptBrushOrg;
 
     /* Combined clipping region */
-    CLIPOBJ *CombinedClip;
+    struct region *Clipping;
+    CLIPOBJ      *CombinedClip;
+    PSWM_WINDOW  pWindow;
 
     /* Transformations */
     MATRIX       mxWorldToDevice;

Modified: branches/arwinss/reactos/subsystems/win32/win32k/w32ksvc.db
URL: http://svn.reactos.org/svn/reactos/branches/arwinss/reactos/subsystems/win32/win32k/w32ksvc.db?rev=44112&r1=44111&r2=44112&view=diff
==============================================================================
--- branches/arwinss/reactos/subsystems/win32/win32k/w32ksvc.db [iso-8859-1] (original)
+++ branches/arwinss/reactos/subsystems/win32/win32k/w32ksvc.db [iso-8859-1] Wed Nov 11 20:55:22 2009
@@ -39,6 +39,7 @@
 RosGdiGetCharWidth                 4
 RosGdiGetDeviceCaps                2
 RosGdiGetDeviceGammaRamp           2
+RosGdiGetDC                        3
 RosGdiGetICMProfile                3
 RosGdiGetNearestColor              2
 RosGdiGetPixelFormat               1
@@ -60,6 +61,7 @@
 RosGdiRealizeDefaultPalette        1
 RosGdiRealizePalette               3
 RosGdiRectangle                    2
+RosGdiReleaseDC                    1
 RosGdiRoundRect                    7
 RosGdiSwapBuffers                  1
 RosGdiUnrealizePalette             1
@@ -83,6 +85,7 @@
 RosUserMapVirtualKeyEx             4
 RosUserGetAsyncKeyState            1
 SwmAddWindow                       2
+SwmAddDesktopWindow                3
 SwmRemoveWindow                    1
 SwmSetForeground                   1
 SwmPosChanging                     2




More information about the Ros-diffs mailing list