Use max tracking size instead of maximized size to limit window size.
[reactos.git] / reactos / lib / user32 / windows / defwnd.c
index a7a231e..2756baa 100644 (file)
@@ -1,4 +1,4 @@
-/* $Id: defwnd.c,v 1.97 2003/10/08 13:46:34 weiden Exp $
+/* $Id$
  *
  * COPYRIGHT:       See COPYING in the top level directory
  * PROJECT:         ReactOS user32.dll
 
 /* INCLUDES ******************************************************************/
 
-#include <windows.h>
 #include <user32.h>
-#include <window.h>
-#include <user32/wininternal.h>
-#include <string.h>
-#include <menu.h>
-#include <cursor.h>
-#include <winpos.h>
-
 #define NDEBUG
 #include <debug.h>
 
-/* GLOBALS *******************************************************************/
+#ifndef WM_SETVISIBLE
+#define WM_SETVISIBLE 9
+#endif
+#ifndef WM_QUERYDROPOBJECT
+#define WM_QUERYDROPOBJECT  0x022B
+#endif
 
-static HBITMAP hbSysMenu;
-/* TODO:  widgets will be cached here.
-static HBITMAP hbClose;
-static HBITMAP hbCloseD;
-static HBITMAP hbMinimize;
-static HBITMAP hbMinimizeD;
-static HBITMAP hbRestore;
-static HBITMAP hbRestoreD;
-static HBITMAP hbMaximize;
-static HBITMAP hbScrUp;
-static HBITMAP hbScrDwn;
-static HBITMAP hbScrLeft;
-static HBITMAP hbScrRight;
-*/
+LRESULT DefWndNCPaint(HWND hWnd, HRGN hRgn, BOOL Active);
+LRESULT DefWndNCCalcSize(HWND hWnd, BOOL CalcSizeStruct, RECT *Rect);
+LRESULT DefWndNCActivate(HWND hWnd, WPARAM wParam);
+LRESULT DefWndNCHitTest(HWND hWnd, POINT Point);
+LRESULT DefWndNCLButtonDown(HWND hWnd, WPARAM wParam, LPARAM lParam);
+LRESULT DefWndNCLButtonDblClk(HWND hWnd, WPARAM wParam, LPARAM lParam);
+void FASTCALL MenuInitSysMenuPopup(HMENU Menu, DWORD Style, DWORD ClsStyle, LONG HitTest );
 
+/* GLOBALS *******************************************************************/
 
-static COLORREF SysColours[] =
-  {
-    RGB(224, 224, 224) /* COLOR_SCROLLBAR */,
-    RGB(58, 110, 165) /* COLOR_BACKGROUND */,
-    RGB(0, 0, 128) /* COLOR_ACTIVECAPTION */,
-    RGB(128, 128, 128) /* COLOR_INACTIVECAPTION */,
-    RGB(192, 192, 192) /* COLOR_MENU */,
-    RGB(255, 255, 255) /* COLOR_WINDOW */,
-    RGB(0, 0, 0) /* COLOR_WINDOWFRAME */,
-    RGB(0, 0, 0) /* COLOR_MENUTEXT */,
-    RGB(0, 0, 0) /* COLOR_WINDOWTEXT */,
-    RGB(255, 255, 255) /* COLOR_CAPTIONTEXT */,
-    RGB(128, 128, 128) /* COLOR_ACTIVEBORDER */,
-    RGB(255, 255, 255) /* COLOR_INACTIVEBORDER */,
-    RGB(255, 255, 232) /* COLOR_APPWORKSPACE */,
-    RGB(224, 224, 224) /* COLOR_HILIGHT */,
-    RGB(0, 0, 128) /* COLOR_HILIGHTTEXT */,
-    RGB(192, 192, 192) /* COLOR_BTNFACE */,
-    RGB(128, 128, 128) /* COLOR_BTNSHADOW */,
-    RGB(192, 192, 192) /* COLOR_GRAYTEXT */,
-    RGB(0, 0, 0) /* COLOR_BTNTEXT */,
-    RGB(192, 192, 192) /* COLOR_INACTIVECAPTIONTEXT */,
-    RGB(255, 255, 255) /* COLOR_BTNHILIGHT */,
-    RGB(32, 32, 32) /* COLOR_3DDKSHADOW */,
-    RGB(192, 192, 192) /* COLOR_3DLIGHT */,
-    RGB(0, 0, 0) /* COLOR_INFOTEXT */,
-    RGB(255, 255, 192) /* COLOR_INFOBK */,
-    RGB(184, 180, 184) /* COLOR_ALTERNATEBTNFACE */,
-    RGB(0, 0, 255) /* COLOR_HOTLIGHT */,
-    RGB(16, 132, 208) /* COLOR_GRADIENTACTIVECAPTION */,
-    RGB(181, 181, 181) /* COLOR_GRADIENTINACTIVECAPTION */,
-  };
-
-static ATOM AtomInternalPos;
+COLORREF SysColors[NUM_SYSCOLORS] = {0};
+HPEN SysPens[NUM_SYSCOLORS] = {0};
+HBRUSH SysBrushes[NUM_SYSCOLORS] = {0};
 
 /* Bits in the dwKeyData */
 #define KEYDATA_ALT   0x2000
 
 /* FUNCTIONS *****************************************************************/
 
-VOID
-UserSetupInternalPos(VOID)
+void
+InitStockObjects(void)
 {
-    LPSTR Str = "SysIP";
-    AtomInternalPos = GlobalAddAtomA(Str);
+  /* FIXME - Instead of copying the stuff to usermode we should map the tables to
+             userland. The current implementation has one big flaw: the system color
+             table doesn't get updated when another process changes them. That's why
+             we should rather map the table into usermode. But it only affects the
+             SysColors table - the pens, brushes and stock objects are not affected
+             as their handles never change. But it'd be faster to map them, too. */
+  if(SysBrushes[0] == NULL)
+  {
+    /* only initialize once */
+    NtUserGetSysColors(SysColors, NUM_SYSCOLORS);
+    NtUserGetSysColorPens(SysPens, NUM_SYSCOLORS);
+    NtUserGetSysColorBrushes(SysBrushes, NUM_SYSCOLORS);
+  }
 }
 
 /*
@@ -94,7 +65,13 @@ UserSetupInternalPos(VOID)
 DWORD STDCALL
 GetSysColor(int nIndex)
 {
-    return SysColours[nIndex];
+  if(nIndex >= 0 && nIndex <= NUM_SYSCOLORS)
+  {
+    return SysColors[nIndex];
+  }
+
+  SetLastError(ERROR_INVALID_PARAMETER);
+  return 0;
 }
 
 /*
@@ -103,22 +80,13 @@ GetSysColor(int nIndex)
 HPEN STDCALL
 GetSysColorPen(int nIndex)
 {
-  static HPEN SysPens[sizeof(SysColours) / sizeof(SysColours[0])];
-
-  if (nIndex < 0 || sizeof(SysColours) / sizeof(SysColours[0]) < nIndex)
-    {
-      SetLastError(ERROR_INVALID_PARAMETER);
-      return NULL;
-    }
-
-  /* FIXME should register this object with DeleteObject() so it
-     can't be deleted */
-  if (NULL == SysPens[nIndex])
-    {
-      SysPens[nIndex] = CreatePen(PS_SOLID, 1, SysColours[nIndex]);
-    }
+  if(nIndex >= 0 && nIndex <= NUM_SYSCOLORS)
+  {
+    return SysPens[nIndex];
+  }
 
-  return SysPens[nIndex];
+  SetLastError(ERROR_INVALID_PARAMETER);
+  return NULL;
 }
 
 /*
@@ -127,143 +95,51 @@ GetSysColorPen(int nIndex)
 HBRUSH STDCALL
 GetSysColorBrush(int nIndex)
 {
-  static HBRUSH SysBrushes[sizeof(SysColours) / sizeof(SysColours[0])];
-
-  if (nIndex < 0 || sizeof(SysColours) / sizeof(SysColours[0]) < nIndex)
-    {
-      SetLastError(ERROR_INVALID_PARAMETER);
-      return NULL;
-    }
-
-  /* FIXME should register this object with DeleteObject() so it
-     can't be deleted */
-  if (NULL == SysBrushes[nIndex])
-    {
-      SysBrushes[nIndex] = (HBRUSH) ((DWORD) CreateSolidBrush(SysColours[nIndex]) | 0x00800000);
-    }
+  if(nIndex >= 0 && nIndex <= NUM_SYSCOLORS)
+  {
+    return SysBrushes[nIndex];
+  }
 
-  return SysBrushes[nIndex];
+  SetLastError(ERROR_INVALID_PARAMETER);
+  return NULL;
 }
 
 /*
- * @unimplemented
- */
-LRESULT STDCALL
-DefFrameProcA( HWND hWnd,
-             HWND hWndMDIClient,
-             UINT uMsg,
-             WPARAM wParam,
-             LPARAM lParam )
-{
-    UNIMPLEMENTED;
-    return ((LRESULT)0);
-}
-
-/*
- * @unimplemented
+ * @implemented
  */
-LRESULT STDCALL
-DefFrameProcW(HWND hWnd,
-             HWND hWndMDIClient,
-             UINT uMsg,
-             WPARAM wParam,
-             LPARAM lParam)
-{
-    UNIMPLEMENTED;
-    return ((LRESULT)0);
-}
-
-PINTERNALPOS
-UserGetInternalPos(HWND hWnd)
-{
-    PINTERNALPOS lpPos;
-    lpPos = (PINTERNALPOS)GetPropA(hWnd, (LPSTR)(DWORD)AtomInternalPos);
-    return(lpPos);
-}
-
-BOOL
-DefWndRedrawIconTitle(HWND hWnd)
-{
-    PINTERNALPOS lpPos = (PINTERNALPOS)GetPropA(hWnd, (LPSTR)(DWORD)AtomInternalPos);
-
-    if (lpPos != NULL)
-    {
-        if (lpPos->IconTitle != NULL)
-        {
-            SendMessageA(lpPos->IconTitle, WM_SHOWWINDOW, TRUE, 0);
-            InvalidateRect(lpPos->IconTitle, NULL, TRUE);
-            return(TRUE);
-        }
-    }
-    return(FALSE);
-}
-
 BOOL
-UserHasMenu(HWND hWnd, ULONG Style)
-{
-    return (!(Style & WS_CHILD) && GetMenu(hWnd) != 0);
-}
-
-ULONG
-UserHasAnyFrameStyle(ULONG Style, ULONG ExStyle)
-{
-    return ((Style & (WS_THICKFRAME | WS_DLGFRAME | WS_BORDER)) ||
-            (ExStyle & WS_EX_DLGMODALFRAME) ||
-            (!(Style & (WS_CHILD | WS_POPUP))));
-}
-
-ULONG
-UserHasDlgFrameStyle(ULONG Style, ULONG ExStyle)
-{
-    return ((ExStyle & WS_EX_DLGMODALFRAME) ||
-            ((Style & WS_DLGFRAME) && (!(Style & WS_THICKFRAME))));
-}
-
-ULONG
-UserHasThickFrameStyle(ULONG Style, ULONG ExStyle)
-{
-    return ((Style & WS_THICKFRAME) &&
-            (!((Style & (WS_DLGFRAME | WS_BORDER)) == WS_DLGFRAME)));
-}
-
-ULONG
-UserHasThinFrameStyle(ULONG Style, ULONG ExStyle)
+STDCALL
+SetSysColors(
+  int cElements,
+  CONST INT *lpaElements,
+  CONST COLORREF *lpaRgbValues)
 {
-    return ((Style & WS_BORDER) || (!(Style & (WS_CHILD | WS_POPUP))));
-}
+  BOOL Ret;
+  struct
+  {
+    INT *Elements;
+    COLORREF *Colors;
+  } ChangeSysColors;
 
-ULONG
-UserHasBigFrameStyle(ULONG Style, ULONG ExStyle)
-{
-    return ((Style & (WS_THICKFRAME | WS_DLGFRAME)) ||
-            (ExStyle & WS_EX_DLGMODALFRAME));
-}
+  ChangeSysColors.Elements = (INT*)lpaElements;
+  ChangeSysColors.Colors = (COLORREF*)lpaRgbValues;
 
-void
-UserGetFrameSize(ULONG Style, ULONG ExStyle, SIZE *Size)
-{
-  if (UserHasThickFrameStyle(Style, ExStyle))
-  {
-    Size->cx = GetSystemMetrics(SM_CXFRAME);
-    Size->cy = GetSystemMetrics(SM_CYFRAME);
-    return;
-  }
-  else if (UserHasDlgFrameStyle(Style, ExStyle))
+  if(cElements > 0)
   {
-    Size->cx = GetSystemMetrics(SM_CXDLGFRAME);
-    Size->cy = GetSystemMetrics(SM_CYDLGFRAME);
-    return;
-  }
-  else if (UserHasThinFrameStyle(Style, ExStyle))
-  {
-    Size->cx = GetSystemMetrics(SM_CXBORDER);
-    Size->cy = GetSystemMetrics(SM_CYBORDER);
-    return;
+    Ret = NtUserSetSysColors(&ChangeSysColors, cElements);
+    if(Ret)
+    {
+      /* FIXME - just change it in the usermode structure, too, instead of asking win32k again */
+      NtUserGetSysColors(SysColors, NUM_SYSCOLORS);
+    }
   }
   else
   {
-    Size->cx = Size->cy = 0;
+    SetLastError(ERROR_INVALID_PARAMETER);
+    Ret = FALSE;
   }
+
+  return Ret;
 }
 
 void
@@ -312,819 +188,21 @@ UserGetInsideRectNC(HWND hWnd, RECT *rect)
     }
 }
 
-WINBOOL
-UserDrawSysMenuButton(HWND hWnd, HDC hDC, LPRECT Rect, BOOL down)
-{
-    HDC hDcMem;
-    HBITMAP hSavedBitmap;
-
-    if (!hbSysMenu)
-    {
-        hbSysMenu = (HBITMAP)LoadBitmapW(0, MAKEINTRESOURCEW(OBM_CLOSE));
-    }
-    hDcMem = CreateCompatibleDC(hDC);
-    if (!hDcMem)
-    {
-        return FALSE;
-    }
-    hSavedBitmap = SelectObject(hDcMem, hbSysMenu);
-    if (!hSavedBitmap)
-    {
-        DeleteDC(hDcMem);
-        return FALSE;
-    }
-
-    BitBlt(hDC, Rect->left + 2, Rect->top + 3, 16, 14, hDcMem,
-           (GetWindowLongW(hWnd, GWL_STYLE) & WS_CHILD) ?
-               GetSystemMetrics(SM_CXSIZE): 0, 0, SRCCOPY);
-
-    SelectObject(hDcMem, hSavedBitmap);
-    DeleteDC(hDcMem);
-    return TRUE;
-}
-
-/*
- * FIXME:
- * Cache bitmaps, then just bitblt instead of calling DFC() (and
- * wasting precious CPU cycles) every time
- */
-static void
-UserDrawCaptionButton(HWND hWnd, HDC hDC, BOOL bDown, ULONG Type)
-{
-    RECT rect;
-    ULONG ExStyle;
-    ULONG Style = GetWindowLongW(hWnd, GWL_STYLE);
-    INT iBmpWidth = GetSystemMetrics(SM_CXSIZE) - 2;
-    INT iBmpHeight = GetSystemMetrics(SM_CYSIZE) - 4;
-    SIZE FrameSize;
-    
-    if (!(Style & WS_SYSMENU))
-    {
-        return;
-    }
-    
-    ExStyle = GetWindowLongW(hWnd, GWL_EXSTYLE);
-    UserGetFrameSize(Style, ExStyle, &FrameSize);
-
-    GetWindowRect(hWnd, &rect);
-
-    rect.right = rect.right - rect.left;
-    rect.bottom = rect.bottom - rect.top;
-    rect.left = rect.top = 0;
-
-    switch(Type)
-    {
-        case DFCS_CAPTIONMIN:
-        {
-            if ((ExStyle & WS_EX_TOOLWINDOW) == TRUE)
-                return; /* ToolWindows don't have min/max buttons */
-
-            SetRect(&rect, rect.right - FrameSize.cx - (iBmpWidth * 3) - 4,
-                    FrameSize.cy + 2, rect.right - (iBmpWidth * 2) - FrameSize.cx - 4,
-                    rect.top + iBmpHeight + FrameSize.cy + 2);
-            DrawFrameControl(hDC, &rect, DFC_CAPTION,
-                             DFCS_CAPTIONMIN | (bDown ? DFCS_PUSHED : 0) |
-                             ((Style & WS_MINIMIZEBOX) ? 0 : DFCS_INACTIVE));
-            break;
-        }
-        case DFCS_CAPTIONMAX:
-        {
-            if ((ExStyle & WS_EX_TOOLWINDOW) == TRUE)
-                return; /* ToolWindows don't have min/max buttons */
-
-            SetRect(&rect, rect.right - FrameSize.cx - (iBmpWidth * 2) - 4,
-                    FrameSize.cy + 2, rect.right - iBmpWidth - FrameSize.cx - 4,
-                    rect.top + iBmpHeight + FrameSize.cy + 2);
-            DrawFrameControl(hDC, &rect, DFC_CAPTION,
-                             (IsZoomed(hWnd) ? DFCS_CAPTIONRESTORE : DFCS_CAPTIONMAX) |
-                             (bDown ? DFCS_PUSHED : 0) |
-                             ((Style & WS_MAXIMIZEBOX) ? 0 : DFCS_INACTIVE));
-            break;
-        }
-        case DFCS_CAPTIONCLOSE:
-        {
-            SetRect(&rect, rect.right - FrameSize.cx - iBmpWidth - 2,
-                    FrameSize.cy + 2,  rect.right - FrameSize.cx - 2,
-                    rect.top + iBmpHeight + FrameSize.cy + 2 );      
-            DrawFrameControl(hDC, &rect, DFC_CAPTION,
-                             (DFCS_CAPTIONCLOSE | (bDown ? DFCS_PUSHED : 0) |
-                             ((Style & WS_SYSMENU) ? 0 : DFCS_INACTIVE)));
-            break;
-        }
-    }
-}
-
-// Enabling this will cause captions to draw smoother, but slower:
-// #define DOUBLE_BUFFER_CAPTION
-// NOTE: Double buffering appears to be broken for this at the moment
-
-/*
- * @implemented
- */
-WINBOOL STDCALL
-DrawCaption(
-  HWND hWnd,
-  HDC hDC,
-  LPRECT lprc,
-  UINT uFlags)
-{
-    NONCLIENTMETRICSW nclm;
-    BOOL result = FALSE;
-    RECT r = *lprc;
-    UINT VCenter = 0, Padding = 0, Height;
-    ULONG Style;
-    WCHAR buffer[256];
-    HFONT hFont = NULL;
-    HFONT hOldFont = NULL;
-    HBRUSH OldBrush = NULL;
-    HDC MemDC = NULL;
-    int ButtonWidth;
-    COLORREF OldTextColor;
-
-#ifdef DOUBLE_BUFFER_CAPTION
-    HBITMAP MemBMP = NULL, OldBMP = NULL;
-
-    MemDC = CreateCompatibleDC(hDC);
-    if (! MemDC) goto cleanup;
-    MemBMP = CreateCompatibleBitmap(hDC, lprc->right - lprc->left, lprc->bottom - lprc->top);
-    if (! MemBMP) goto cleanup;
-    OldBMP = SelectObject(MemDC, MemBMP);
-    if (! OldBMP) goto cleanup;
-#else
-    MemDC = hDC;
-
-    OffsetViewportOrgEx(MemDC, lprc->left, lprc->top, NULL);
-#endif
-
-    // If DC_GRADIENT is specified, a Win 98/2000 style caption gradient should
-    // be painted. For now, that flag is ignored:
-    // Windows 98/Me, Windows 2000/XP: When this flag is set, the function uses
-    // COLOR_GRADIENTACTIVECAPTION (if the DC_ACTIVE flag was set) or
-    // COLOR_GRADIENTINACTIVECAPTION for the title-bar color. 
-
-    // Draw the caption background
-    if (uFlags & DC_INBUTTON)
-    {
-        OldBrush = SelectObject(MemDC, GetSysColorBrush(uFlags & DC_ACTIVE ? COLOR_BTNFACE : COLOR_BTNSHADOW) );
-        if (! OldBrush) goto cleanup;
-        if (! PatBlt(MemDC, 0, 0, lprc->right - lprc->left, lprc->bottom - lprc->top, PATCOPY )) goto cleanup;
-    }
-    else
-    {
-        // DC_GRADIENT check should go here somewhere
-        OldBrush = SelectObject(MemDC, GetSysColorBrush(uFlags & DC_ACTIVE ? COLOR_ACTIVECAPTION : COLOR_INACTIVECAPTION) );
-        if (! OldBrush) goto cleanup;
-        if (! PatBlt(MemDC, 0, 0, lprc->right - lprc->left, lprc->bottom - lprc->top, PATCOPY )) goto cleanup;
-    }
-    
-    Style = GetWindowLongW(hWnd, GWL_STYLE);
-    
-    /* Windows behaves like this */
-    Height = GetSystemMetrics(SM_CYCAPTION) - 1;
-
-    VCenter = (lprc->bottom - lprc->top) / 2;
-    Padding = VCenter - (Height / 2);
-
-    r.left = Padding;
-    r.right = r.left + (lprc->right - lprc->left);
-    r.top = Padding;
-    r.bottom = r.top + (Height / 2);
-
-    if ((uFlags & DC_ICON) && (Style & WS_SYSMENU))
-    {
-        // For some reason the icon isn't centered correctly...
-        r.top --;
-        UserDrawSysMenuButton(hWnd, MemDC, &r, FALSE);
-        r.top ++;
-    }
-
-    r.top ++;
-    r.left += 2;
-
-  if ((uFlags & DC_TEXT) && (GetWindowTextW( hWnd, buffer, sizeof(buffer)/sizeof(buffer[0]) )))
-  {
-    // Duplicate odd behaviour from Windows:
-    if ((! uFlags & DC_SMALLCAP) || (uFlags & DC_ICON) || (uFlags & DC_INBUTTON) ||
-        (! uFlags & DC_ACTIVE))
-        r.left += GetSystemMetrics(SM_CXSIZE) + Padding;
-
-    r.right = (lprc->right - lprc->left);
-    ButtonWidth = GetSystemMetrics(SM_CXSIZE) - 2;
-
-    if (Style & WS_SYSMENU)
-    {
-      r.right -= 3 + ButtonWidth;
-      if (! (GetWindowLongW(hWnd, GWL_EXSTYLE) & WS_EX_TOOLWINDOW))
-      {
-        if(Style & (WS_MAXIMIZEBOX | WS_MINIMIZEBOX))
-             r.right -= 2 + 2 * ButtonWidth;
-        else
-             r.right -= 2;
-      }
-    }
-    r.right -= 2;
-
-    nclm.cbSize = sizeof(nclm);
-    if (! SystemParametersInfoW(SPI_GETNONCLIENTMETRICS, sizeof(NONCLIENTMETRICSW), &nclm, 0)) goto cleanup;
-
-    SetBkMode( MemDC, TRANSPARENT );
-    if (Style & WS_EX_TOOLWINDOW)
-//    if (uFlags & DC_SMALLCAP) // incorrect
-        hFont = CreateFontIndirectW(&nclm.lfSmCaptionFont);
-    else
-        hFont = CreateFontIndirectW(&nclm.lfCaptionFont);
-
-    if (! hFont) goto cleanup;
-
-    hOldFont = SelectObject(MemDC, hFont);
-    if (! hOldFont) goto cleanup;
-    
-    if (uFlags & DC_INBUTTON)
-        OldTextColor = SetTextColor(MemDC, SysColours[ uFlags & DC_ACTIVE ? COLOR_BTNTEXT : COLOR_GRAYTEXT]);
-    else
-        OldTextColor = SetTextColor(MemDC, SysColours[ uFlags & DC_ACTIVE ? COLOR_CAPTIONTEXT : COLOR_INACTIVECAPTIONTEXT]);
-
-    DrawTextW(MemDC, buffer, wcslen(buffer), &r, DT_VCENTER | DT_END_ELLIPSIS);
-    
-    SetTextColor(MemDC, OldTextColor);
-  }
-
-    if (uFlags & DC_BUTTONS)
-    {
-        // Windows XP draws the caption buttons with DC_BUTTONS
-//        r.left += GetSystemMetrics(SM_CXSIZE) + 1;
-//        UserDrawCaptionButton( hWnd, hDC, FALSE, DFCS_CAPTIONCLOSE);
-//        r.right -= GetSystemMetrics(SM_CXSMSIZE) + 1;
-//        UserDrawCaptionButton( hWnd, hDC, FALSE, DFCS_CAPTIONMIN);
-//        UserDrawCaptionButton( hWnd, hDC, FALSE, DFCS_CAPTIONMAX);
-    }
-
-#ifdef DOUBLE_BUFFER_CAPTION
-    if (! BitBlt(hDC, lprc->left, lprc->top, lprc->right - lprc->left, lprc->bottom - lprc->top,
-            MemDC, 0, 0, SRCCOPY)) goto cleanup;
-#endif
-
-    result = TRUE;
-
-    cleanup :
-        if (MemDC)
-        {
-            if (OldBrush) SelectObject(MemDC, OldBrush);
-            if (hOldFont) SelectObject(MemDC, hOldFont);
-            if (hFont) DeleteObject(hFont);
-#ifdef DOUBLE_BUFFER_CAPTION
-            if (OldBMP) SelectObject(MemDC, OldBMP);
-            if (MemBMP) DeleteObject(MemBMP);
-            DeleteDC(MemDC);
-#else
-            OffsetViewportOrgEx(MemDC, -lprc->left, -lprc->top, NULL);
-#endif
-        }
-
-        return result;
-}
-
-static void
-UserDrawCaptionNC (
-       HDC hDC,
-       RECT *rect,
-       HWND hWnd,
-       DWORD style,
-       BOOL active )
-{
-  POINT OldPos;
-  HPEN lPen, oPen;
-  RECT r = *rect;
-  ULONG ExStyle;
-  UINT capflags = 0;
-  SIZE FrameSize;
-  
-  ExStyle = GetWindowLongW(hWnd, GWL_EXSTYLE);
-  
-  capflags = DC_ICON | DC_TEXT;
-  capflags |= (active & DC_ACTIVE);
-  
-  if(style & WS_EX_TOOLWINDOW)
-    capflags |= DC_SMALLCAP;
-  
-  UserGetFrameSize(style, ExStyle, &FrameSize);
-  
-  r.left += FrameSize.cx;
-  r.top += FrameSize.cy;
-  r.right -= FrameSize.cx;
-  r.bottom = r.top + GetSystemMetrics(SM_CYCAPTION) - 1;
-  
-  DrawCaption(hWnd, hDC, &r, capflags);
-  
-  /* draw line below caption */
-  lPen = GetSysColorPen(COLOR_MENU);
-  oPen = SelectObject(hDC, lPen);
-  MoveToEx(hDC, r.left, r.bottom, &OldPos);
-  LineTo(hDC, r.right, r.bottom);
-  MoveToEx(hDC, OldPos.x, OldPos.y, NULL);
-  SelectObject(hDC, oPen);
-  r.bottom++;
-  
-  if (style & WS_SYSMENU)
-  {
-    r.left += GetSystemMetrics(SM_CXSIZE) + 1;
-    UserDrawCaptionButton( hWnd, hDC, FALSE, DFCS_CAPTIONCLOSE);
-    r.right -= GetSystemMetrics(SM_CXSMSIZE) + 1;
-    if((style & (WS_MAXIMIZEBOX | WS_MINIMIZEBOX)) && !(ExStyle & WS_EX_TOOLWINDOW))
-    {
-      UserDrawCaptionButton( hWnd, hDC, FALSE, DFCS_CAPTIONMIN);
-      UserDrawCaptionButton( hWnd, hDC, FALSE, DFCS_CAPTIONMAX);
-    }
-  }
-}
-
-
-static VOID
-UserDrawFrameNC(HDC hDC, RECT* rect, BOOL dlgFrame, BOOL active)
-{
-  DrawEdge(hDC, rect, EDGE_RAISED, BF_RECT | BF_MIDDLE);
-}
-
-
-void
-SCROLL_DrawScrollBar (HWND hWnd, HDC hDC, INT nBar, BOOL arrows, BOOL interior);
 
 VOID
-DefWndDoPaintNC(HWND hWnd, HRGN clip)
-{
-  BOOL Active = FALSE;
-  HDC hDC;
-  RECT rect, clientrect;
-  ULONG Style;
-  ULONG ExStyle;
-  SIZE FrameSize;
-  HGDIOBJ OldObj;
-
-  if (GetActiveWindow() == hWnd) Active = TRUE;
-
-  hDC = GetDCEx(hWnd, (clip > (HRGN)1) ? clip : 0, DCX_USESTYLE | DCX_WINDOW |
-               ((clip > (HRGN)1) ? (DCX_INTERSECTRGN | DCX_KEEPCLIPRGN) : 0));
-  if (hDC == 0)
-    {
-      return;
-    }
-    
-  Style = GetWindowLongW(hWnd, GWL_STYLE);
-  ExStyle = GetWindowLongW(hWnd, GWL_EXSTYLE);
-
-  /* FIXME: Test whether we need to draw anything at all. */
-
-  GetWindowRect(hWnd, &rect);
-  GetClientRect(hWnd, &clientrect);
-  
-  rect.right -= rect.left;
-  rect.bottom -= rect.top;
-  rect.top = rect.left = 0;
-  
-  UserGetFrameSize(Style, ExStyle, &FrameSize);
-
-  OldObj = SelectObject(hDC, GetSysColorPen(COLOR_WINDOWFRAME));
-  
-  if(UserHasThickFrameStyle(Style, ExStyle))
-    UserDrawFrameNC(hDC, &rect, FALSE, Active);
-  else if (UserHasDlgFrameStyle(Style, ExStyle))
-    UserDrawFrameNC(hDC, &rect, TRUE, Active);
-    
-  if (Style & WS_CAPTION)
-    {
-      RECT r = rect;
-      r.bottom = rect.top + GetSystemMetrics(SM_CYSIZE);
-      rect.top += GetSystemMetrics(SM_CYCAPTION) + FrameSize.cy;
-      DbgPrint("1. rect.top == %d\n", rect.top);
-      UserDrawCaptionNC(hDC, &r, hWnd, Style, Active);
-    }
-
-  /*  Draw menu bar.  */
-  if (UserHasMenu(hWnd, Style))
-    {DbgPrint("2. rect.top == %d\n", rect.top);
-      RECT r = rect;
-      r.bottom = rect.top + GetSystemMetrics(SM_CYMENU);
-      r.left += FrameSize.cx;
-      r.right -= FrameSize.cx;
-      rect.top += MenuDrawMenuBar(hDC, &r, hWnd, FALSE);
-      DbgPrint("3. rect.top == %d\n", rect.top);
-    }
-
-  /*  Draw scrollbars */
-  if((Style & WS_VSCROLL) && (clientrect.right < rect.right - (2 * FrameSize.cx)))
-    SCROLL_DrawScrollBar(hWnd, hDC, SB_VERT, TRUE, TRUE);
-  DbgPrint("HSCROLL: %d < %d - %d - %d\n", clientrect.bottom, rect.bottom, rect.top, FrameSize.cy);
-  if((Style & WS_HSCROLL) && (clientrect.bottom < rect.bottom - rect.top - FrameSize.cy))
-    SCROLL_DrawScrollBar(hWnd, hDC, SB_HORZ, TRUE, TRUE);
-
-  /* FIXME: Draw size box.*/
-  SelectObject(hDC, OldObj);
-
-  ReleaseDC(hWnd, hDC);
-}
-
-
-LRESULT
-DefWndPaintNC(HWND hWnd, HRGN clip)
-{
-  if (IsWindowVisible(hWnd))
-    {
-      if (IsIconic(hWnd))
-       {
-         DefWndRedrawIconTitle(hWnd);
-       }
-      else
-       {
-         DefWndDoPaintNC(hWnd, clip);
-       }
-    }
-  return(0);
-}
-
-
-LRESULT
-DefWndHitTestNC(HWND hWnd, POINT Point)
-{
-  RECT WindowRect, ClientRect, WndRect;
-  LONG ScrollXY;
-  SIZE FrameSize;
-  ULONG Style = GetWindowLongW(hWnd, GWL_STYLE);
-  ULONG ExStyle = GetWindowLongW(hWnd, GWL_EXSTYLE);
-
-  GetWindowRect(hWnd, &WindowRect);
-  WndRect = WindowRect;
-  if (!PtInRect(&WindowRect, Point))
-    {      
-      return(HTNOWHERE);
-    }
-  if (Style & WS_MINIMIZE)
-    {
-      return(HTCAPTION);
-    }
-  if (UserHasThickFrameStyle(Style, ExStyle))
-    {
-      FrameSize.cx = GetSystemMetrics(SM_CXFRAME);
-      FrameSize.cy = GetSystemMetrics(SM_CYFRAME);
-      InflateRect(&WindowRect, -FrameSize.cx, -FrameSize.cy);
-      if (!PtInRect(&WindowRect, Point))
-       {
-         if (Point.y < WindowRect.top)
-           {
-             if (Point.x < (WindowRect.left + GetSystemMetrics(SM_CXSIZE)))
-               {
-                 return(HTTOPLEFT);
-               }
-             if (Point.x >= (WindowRect.right - GetSystemMetrics(SM_CXSIZE)))
-               {
-                 return(HTTOPRIGHT);
-               }
-             return(HTTOP);
-           }
-         if (Point.y >= WindowRect.bottom)
-           {
-             if (Point.x < (WindowRect.left + GetSystemMetrics(SM_CXSIZE)))
-               {
-                 return(HTBOTTOMLEFT);
-               }
-             if (Point.x >= (WindowRect.right - GetSystemMetrics(SM_CXSIZE)))
-               {
-                 return(HTBOTTOMRIGHT);
-               }
-             return(HTBOTTOM);
-           }
-         if (Point.x < WindowRect.left)
-           {
-             if (Point.y < (WindowRect.top + GetSystemMetrics(SM_CYSIZE)))
-               {
-                 return(HTTOPLEFT);
-               }
-             if (Point.y >= (WindowRect.bottom - GetSystemMetrics(SM_CYSIZE)))
-               {
-                 return(HTBOTTOMLEFT);
-               }
-             return(HTLEFT);
-           }
-         if (Point.x >= WindowRect.right)
-           {
-             if (Point.y < (WindowRect.top + GetSystemMetrics(SM_CYSIZE)))
-               {
-                 return(HTTOPRIGHT);
-               }
-             if (Point.y >= (WindowRect.bottom - GetSystemMetrics(SM_CYSIZE)))
-               {
-                 return(HTBOTTOMRIGHT);
-               }
-             return(HTRIGHT);
-           }
-       }
-    }
-  else
-    {
-      if (UserHasDlgFrameStyle(Style, ExStyle))
-       {
-      FrameSize.cx = GetSystemMetrics(SM_CXDLGFRAME);
-      FrameSize.cy = GetSystemMetrics(SM_CYDLGFRAME);
-         InflateRect(&WindowRect, -FrameSize.cx, -FrameSize.cy);
-       }
-      else if (UserHasThinFrameStyle(Style, ExStyle))
-       {
-      FrameSize.cx = GetSystemMetrics(SM_CXBORDER);
-      FrameSize.cy = GetSystemMetrics(SM_CYBORDER);
-         InflateRect(&WindowRect, -FrameSize.cx, -FrameSize.cy);
-       }
-      if (!PtInRect(&WindowRect, Point))
-       {
-         return(HTBORDER);
-       }
-    }
-
-  if ((Style & WS_CAPTION) == WS_CAPTION)
-    {
-      WindowRect.top += (GetSystemMetrics(SM_CYCAPTION));
-      if (!PtInRect(&WindowRect, Point))
-       {
-         if ((Style & WS_SYSMENU) && !(ExStyle & WS_EX_TOOLWINDOW))
-           {
-             WindowRect.left += GetSystemMetrics(SM_CXSIZE);
-             WindowRect.right -= GetSystemMetrics(SM_CXSIZE);
-           }
-         if (Point.x <= WindowRect.left)
-           {
-             return(HTSYSMENU);
-           }
-         if (WindowRect.right <= Point.x)
-           {
-             return(HTCLOSE);
-           }
-
-         if (Style & WS_MAXIMIZEBOX || Style & WS_MINIMIZEBOX)
-           {
-             WindowRect.right -= GetSystemMetrics(SM_CXSIZE);
-           }
-         if (Point.x >= WindowRect.right)
-           {
-             return(HTMAXBUTTON);
-           }
-
-         if (Style & WS_MINIMIZEBOX)
-           {
-             WindowRect.right -= GetSystemMetrics(SM_CXSIZE);
-           }
-         if (Point.x >= WindowRect.right)
-           {
-             return(HTMINBUTTON);
-           }
-         return(HTCAPTION);
-       }
-    }
-
-  ScreenToClient(hWnd, &Point);
-  GetClientRect(hWnd, &ClientRect);
-  WndRect.right -= WndRect.left;
-  WndRect.bottom -= WndRect.top;
-  WndRect.left = WndRect.top = 0;
-
-  if (PtInRect(&ClientRect, Point))
-    {
-      return(HTCLIENT);
-    }
-    
-  if (UserHasMenu(hWnd, Style))
-  {
-    if (Point.y < 0 && Point.x >= 0 && Point.x <= WindowRect.right)
-       {
-         return(HTMENU);
-       }
-  }
-
-  if (Style & WS_VSCROLL)
-  {
-    ScrollXY = GetSystemMetrics(SM_CXVSCROLL);
-    ClientRect.left = ClientRect.right;
-    ClientRect.right += ScrollXY;
-    if (PtInRect(&ClientRect, Point) && PtInRect(&WndRect, Point))
-    {
-      return(HTVSCROLL);
-    }
-  }
-  else
-    ScrollXY = 0;
-  
-  if (Style & WS_HSCROLL)
-  {
-    GetClientRect(hWnd, &ClientRect);
-    ClientRect.top = ClientRect.bottom;
-    ClientRect.bottom = ClientRect.top + GetSystemMetrics(SM_CXVSCROLL);
-    if (PtInRect(&ClientRect, Point) && PtInRect(&WndRect, Point))
-    {
-      return(HTHSCROLL);
-    }
-    if (ScrollXY)
-    {
-      ClientRect.left = ClientRect.right;
-      ClientRect.right += ScrollXY;
-      if(PtInRect(&WndRect, Point) && PtInRect(&ClientRect, Point))
-      {
-        return(HTBOTTOMRIGHT);
-      }
-    }
-  }
-  
-  return(HTNOWHERE);
-}
-
-VOID STATIC
-DefWndDoButton(HWND hWnd, WPARAM wParam)
-{
-  MSG Msg;
-  BOOL InBtn, HasBtn = FALSE;
-  ULONG Btn, Style;
-  WPARAM SCMsg, CurBtn = wParam, OrigBtn = wParam;
-  
-  Style = GetWindowLongW(hWnd, GWL_STYLE);
-  switch(wParam)
-  {
-    case HTCLOSE:
-      Btn = DFCS_CAPTIONCLOSE;
-      SCMsg = SC_CLOSE;
-      HasBtn = (Style & WS_SYSMENU);
-      break;
-    case HTMINBUTTON:
-      Btn = DFCS_CAPTIONMIN;
-      SCMsg = SC_MINIMIZE;
-      HasBtn = (Style & WS_MINIMIZEBOX);
-      break;
-    case HTMAXBUTTON:
-      Btn = DFCS_CAPTIONMAX;
-      SCMsg = SC_MAXIMIZE;
-      HasBtn = (Style & WS_MAXIMIZEBOX);
-      break;
-    default:
-      return;
-  }
-  
-  InBtn = HasBtn;
-  
-  SetCapture(hWnd);
-  
-  if(HasBtn)
-    UserDrawCaptionButton( hWnd, GetWindowDC(hWnd), HasBtn , Btn);
-  
-  while(1)
-  {
-    GetMessageW(&Msg, 0, 0, 0);
-    switch(Msg.message)
-    {
-      case WM_NCLBUTTONUP:
-      case WM_LBUTTONUP:
-        if(InBtn)
-          goto done;
-        else
-        {
-          ReleaseCapture();
-          return;
-        }
-      case WM_NCMOUSEMOVE:
-      case WM_MOUSEMOVE:
-        if(HasBtn)
-        {
-          CurBtn = DefWndHitTestNC(hWnd, Msg.pt);
-          if(InBtn != (CurBtn == OrigBtn))
-          {
-            UserDrawCaptionButton( hWnd, GetWindowDC(hWnd), (CurBtn == OrigBtn) , Btn);
-          }
-          InBtn = CurBtn == OrigBtn;
-        }
-        break;
-    }
-  }
-  
-done:
-  UserDrawCaptionButton( hWnd, GetWindowDC(hWnd), FALSE , Btn);
-  ReleaseCapture();
-  SendMessageA(hWnd, WM_SYSCOMMAND, SCMsg, 0);
-  return;
-}
-
-VOID STATIC
-DefWndDoScrollBarDown(HWND hWnd, UINT Msg, WPARAM wParam, LPARAM lParam)
-{
-  POINT Point;
-  DWORD hit;
-  Point.x = SLOWORD(lParam);
-  Point.y = SHIWORD(lParam);
-  
-  hit = SCROLL_HitTest(hWnd, (wParam == HTHSCROLL) ? SB_HORZ : SB_VERT, Point, FALSE);
-  
-  if(hit)
-    DPRINT("SCROLL_HitTest() == 0x%x\n", hit);
-  
-  SendMessageA(hWnd, WM_SYSCOMMAND, Msg + (UINT)wParam, lParam);
-}
-
-LRESULT
-DefWndHandleLButtonDownNC(HWND hWnd, WPARAM wParam, LPARAM lParam)
+DefWndSetRedraw(HWND hWnd, WPARAM wParam)
 {
-    switch (wParam)
+  if ((BOOL) wParam && 0 == (GetWindowLong(hWnd, GWL_STYLE) & WS_VISIBLE))
     {
-        case HTCAPTION:
-        {
-               HWND hTopWnd = GetAncestor(hWnd, GA_ROOT);
-               if (SetActiveWindow(hTopWnd) || GetActiveWindow() == hTopWnd)
-               {
-                   SendMessageA(hWnd, WM_SYSCOMMAND, SC_MOVE + HTCAPTION, lParam);
-               }
-               break;
-        }
-        case HTSYSMENU:
-        {
-         if (GetWindowLongW(hWnd, GWL_STYLE) & WS_SYSMENU)
-            {
-             if (!(GetWindowLongW(hWnd, GWL_STYLE) & WS_MINIMIZE))
-               {
-                 HDC hDC = GetWindowDC(hWnd);
-//               UserDrawSysMenuButton(hWnd, hDC, TRUE);
-                 ReleaseDC(hWnd, hDC);
-               }
-             SendMessageA(hWnd, WM_SYSCOMMAND, SC_MOUSEMENU + HTSYSMENU,
-                          lParam);
-           }
-         break;
-        }
-        case HTMENU:
-        {
-            SendMessageA(hWnd, WM_SYSCOMMAND, SC_MOUSEMENU + HTMENU, lParam);
-            break;
-        }
-        case HTHSCROLL:
-        {
-            DefWndDoScrollBarDown(hWnd, SC_HSCROLL, HTHSCROLL, lParam);
-            //SendMessageA(hWnd, WM_SYSCOMMAND, SC_HSCROLL + HTHSCROLL, lParam);
-            break;
-        }
-        case HTVSCROLL:
-        {
-            DefWndDoScrollBarDown(hWnd, SC_VSCROLL, HTVSCROLL, lParam);
-            //SendMessageA(hWnd, WM_SYSCOMMAND, SC_VSCROLL + HTVSCROLL, lParam);
-            break;
-        }
-        case HTMINBUTTON:
-        case HTMAXBUTTON:
-        case HTCLOSE:
-        {
-          DefWndDoButton(hWnd, wParam);
-          break;
-        }
-        case HTLEFT:
-        case HTRIGHT:
-        case HTTOP:
-        case HTBOTTOM:
-        case HTTOPLEFT:
-        case HTTOPRIGHT:
-        case HTBOTTOMLEFT:
-        case HTBOTTOMRIGHT:
-        {
-            SendMessageA(hWnd, WM_SYSCOMMAND, SC_SIZE + wParam - 2, lParam);
-            break;
-        }
+      ShowWindow(hWnd, SW_NORMAL);
     }
-    return(0);
-}
-
 
-LRESULT
-DefWndHandleLButtonDblClkNC(HWND hWnd, WPARAM wParam, LPARAM lParam)
-{
   UNIMPLEMENTED;
-  return(0);
 }
 
 
 LRESULT
-DefWndHandleLButtonUpNC(HWND hWnd, WPARAM wParam, LPARAM lParam)
-{
-  UNIMPLEMENTED;
-  return(0);
-}
-
-
-LRESULT
-DefWndHandleActiveNC(HWND hWnd, WPARAM wParam)
-{
-  UNIMPLEMENTED;
-  return(0);
-}
-
-
-VOID
-DefWndSetRedraw(HWND hWnd, WPARAM wParam)
-{
-  UNIMPLEMENTED;
-}
-
-
-LRESULT
-DefWndHandleSetCursor(HWND hWnd, WPARAM wParam, LPARAM lParam)
+DefWndHandleSetCursor(HWND hWnd, WPARAM wParam, LPARAM lParam, ULONG Style)
 {
   /* Not for child windows. */
   if (hWnd != (HWND)wParam)
@@ -1132,7 +210,7 @@ DefWndHandleSetCursor(HWND hWnd, WPARAM wParam, LPARAM lParam)
       return(0);
     }
 
-  switch(LOWORD(lParam))
+  switch((INT_PTR) LOWORD(lParam))
     {
     case HTERROR:
       {
@@ -1159,39 +237,55 @@ DefWndHandleSetCursor(HWND hWnd, WPARAM wParam, LPARAM lParam)
     case HTLEFT:
     case HTRIGHT:
       {
+        if (Style & WS_MAXIMIZE)
+        {
+          break;
+        }
        return((LRESULT)SetCursor(LoadCursorW(0, IDC_SIZEWE)));
       }
 
     case HTTOP:
     case HTBOTTOM:
       {
+        if (Style & WS_MAXIMIZE)
+        {
+          break;
+        }
        return((LRESULT)SetCursor(LoadCursorW(0, IDC_SIZENS)));
       }
 
     case HTTOPLEFT:
     case HTBOTTOMRIGHT:
       {
+        if (Style & WS_MAXIMIZE)
+        {
+          break;
+        }
        return((LRESULT)SetCursor(LoadCursorW(0, IDC_SIZENWSE)));
       }
 
     case HTBOTTOMLEFT:
     case HTTOPRIGHT:
       {
+        if (GetWindowLongW(hWnd, GWL_STYLE) & WS_MAXIMIZE)
+        {
+          break;
+        }
        return((LRESULT)SetCursor(LoadCursorW(0, IDC_SIZENESW)));
       }
     }
   return((LRESULT)SetCursor(LoadCursorW(0, IDC_ARROW)));
 }
 
-static LONG 
+static LONG
 DefWndStartSizeMove(HWND hWnd, WPARAM wParam, POINT *capturePoint)
 {
   LONG hittest = 0;
   POINT pt;
   MSG msg;
   RECT rectWindow;
-  ULONG Style = GetWindowLongW(hWnd, GWL_STYLE); 
-  
+  ULONG Style = GetWindowLongW(hWnd, GWL_STYLE);
+
   GetWindowRect(hWnd, &rectWindow);
 
   if ((wParam & 0xfff0) == SC_MOVE)
@@ -1212,20 +306,22 @@ DefWndStartSizeMove(HWND hWnd, WPARAM wParam, POINT *capturePoint)
     }
   else  /* SC_SIZE */
     {
+      pt.x = pt.y = 0;
       while(!hittest)
        {
-         GetMessageW(&msg, NULL, 0, 0);
+         if (GetMessageW(&msg, NULL, 0, 0) <= 0)
+           break;
          switch(msg.message)
            {
            case WM_MOUSEMOVE:
-             hittest = DefWndHitTestNC(hWnd, msg.pt);
+             hittest = DefWndNCHitTest(hWnd, msg.pt);
              if ((hittest < HTLEFT) || (hittest > HTBOTTOMRIGHT))
                hittest = 0;
              break;
-             
+
            case WM_LBUTTONUP:
              return 0;
-             
+
            case WM_KEYDOWN:
              switch(msg.wParam)
                {
@@ -1257,7 +353,7 @@ DefWndStartSizeMove(HWND hWnd, WPARAM wParam, POINT *capturePoint)
       *capturePoint = pt;
     }
     SetCursorPos( pt.x, pt.y );
-    DefWndHandleSetCursor(hWnd, (WPARAM)hWnd, MAKELONG(hittest, WM_MOUSEMOVE));
+    DefWndHandleSetCursor(hWnd, (WPARAM)hWnd, MAKELONG(hittest, WM_MOUSEMOVE), Style);
     return hittest;
 }
 
@@ -1270,66 +366,82 @@ DefWndStartSizeMove(HWND hWnd, WPARAM wParam, POINT *capturePoint)
 #define ON_BOTTOM_BORDER(hit) \
  (((hit) == HTBOTTOM) || ((hit) == HTBOTTOMLEFT) || ((hit) == HTBOTTOMRIGHT))
 
-VOID STATIC 
+VOID STATIC
 UserDrawWindowFrame(HDC hdc, const RECT *rect,
-                   ULONG width, ULONG height, DWORD rop )
+                   ULONG width, ULONG height)
 {
-  HBRUSH hbrush = SelectObject( hdc, GetStockObject( GRAY_BRUSH ) );
+  static HBRUSH hDraggingRectBrush = NULL;
+  HBRUSH hbrush;
+
+  if(!hDraggingRectBrush)
+  {
+    static HBITMAP hDraggingPattern = NULL;
+    const DWORD Pattern[4] = {0x5555AAAA, 0x5555AAAA, 0x5555AAAA, 0x5555AAAA};
+
+    hDraggingPattern = CreateBitmap(8, 8, 1, 1, Pattern);
+    hDraggingRectBrush = CreatePatternBrush(hDraggingPattern);
+  }
+
+  hbrush = SelectObject( hdc, hDraggingRectBrush );
   PatBlt( hdc, rect->left, rect->top,
-         rect->right - rect->left - width, height, rop );
+         rect->right - rect->left - width, height, PATINVERT );
   PatBlt( hdc, rect->left, rect->top + height, width,
-         rect->bottom - rect->top - height, rop );
+         rect->bottom - rect->top - height, PATINVERT );
   PatBlt( hdc, rect->left + width, rect->bottom - 1,
-         rect->right - rect->left - width, -height, rop );
+         rect->right - rect->left - width, -height, PATINVERT );
   PatBlt( hdc, rect->right - 1, rect->top, -width,
-         rect->bottom - rect->top - height, rop );
+         rect->bottom - rect->top - height, PATINVERT );
   SelectObject( hdc, hbrush );
 }
 
 VOID STATIC
 UserDrawMovingFrame(HDC hdc, RECT *rect, BOOL thickframe)
 {
-  if (thickframe)
-    {
-      UserDrawWindowFrame(hdc, rect, GetSystemMetrics(SM_CXFRAME),
-                         GetSystemMetrics(SM_CYFRAME), PATINVERT );
-    }
-  else DrawFocusRect( hdc, rect );
+  if(thickframe)
+  {
+    UserDrawWindowFrame(hdc, rect, GetSystemMetrics(SM_CXFRAME), GetSystemMetrics(SM_CYFRAME));
+  }
+  else
+  {
+    UserDrawWindowFrame(hdc, rect, 1, 1);
+  }
 }
 
 VOID STATIC
 DefWndDoSizeMove(HWND hwnd, WORD wParam)
 {
+  HRGN DesktopRgn;
   MSG msg;
-  RECT sizingRect, mouseRect, origRect;
+  RECT sizingRect, mouseRect, origRect, clipRect, unmodRect;
   HDC hdc;
   LONG hittest = (LONG)(wParam & 0x0f);
   HCURSOR hDragCursor = 0, hOldCursor = 0;
   POINT minTrack, maxTrack;
   POINT capturePoint, pt;
   ULONG Style = GetWindowLongW(hwnd, GWL_STYLE);
-  ULONG ExStyle = GetWindowLongW(hwnd, GWL_EXSTYLE); 
-  BOOL thickframe = UserHasThickFrameStyle(Style, ExStyle);
+  ULONG ExStyle = GetWindowLongW(hwnd, GWL_EXSTYLE);
+  BOOL thickframe;
   BOOL iconic = Style & WS_MINIMIZE;
   BOOL moved = FALSE;
   DWORD dwPoint = GetMessagePos();
   BOOL DragFullWindows = FALSE;
-  HWND hWndParent;
+  HWND hWndParent = NULL;
 
   SystemParametersInfoA(SPI_GETDRAGFULLWINDOWS, 0, &DragFullWindows, 0);
-  
-  pt.x = SLOWORD(dwPoint);
-  pt.y = SHIWORD(dwPoint);
+
+  pt.x = GET_X_LPARAM(dwPoint);
+  pt.y = GET_Y_LPARAM(dwPoint);
   capturePoint = pt;
-  
+
   if (IsZoomed(hwnd) || !IsWindowVisible(hwnd))
     {
       return;
     }
-  
+
+  thickframe = UserHasThickFrameStyle(Style, ExStyle) && !(Style & WS_MINIMIZE);
   if ((wParam & 0xfff0) == SC_MOVE)
     {
-      if (!hittest) 
+      if (!hittest)
        {
          hittest = DefWndStartSizeMove(hwnd, wParam, &capturePoint);
        }
@@ -1344,9 +456,9 @@ DefWndDoSizeMove(HWND hwnd, WORD wParam)
        {
          return;
        }
-      if (hittest && hittest != HTSYSMENU) 
+      if (hittest && ((wParam & 0xfff0) != SC_MOUSEMENU))
        {
-         hittest += 2;
+          hittest += (HTLEFT - WMSZ_LEFT);
        }
       else
        {
@@ -1360,25 +472,35 @@ DefWndDoSizeMove(HWND hwnd, WORD wParam)
        }
     }
 
-  if (Style & WS_CHILD)
-    {
-      hWndParent = GetParent(hwnd);
-    }
-  
   /* Get min/max info */
-  
+
   WinPosGetMinMaxInfo(hwnd, NULL, NULL, &minTrack, &maxTrack);
   GetWindowRect(hwnd, &sizingRect);
   if (Style & WS_CHILD)
     {
+      hWndParent = GetParent(hwnd);
       MapWindowPoints( 0, hWndParent, (LPPOINT)&sizingRect, 2 );
+      unmodRect = sizingRect;
       GetClientRect(hWndParent, &mouseRect );
+      clipRect = mouseRect;
+      MapWindowPoints(hWndParent, HWND_DESKTOP, (LPPOINT)&clipRect, 2);
     }
-  else 
+  else
     {
-      SetRect(&mouseRect, 0, 0, GetSystemMetrics(SM_CXSCREEN), 
-             GetSystemMetrics(SM_CYSCREEN));
+      if(!(ExStyle & WS_EX_TOPMOST))
+      {
+        SystemParametersInfoW(SPI_GETWORKAREA, 0, &clipRect, 0);
+        mouseRect = clipRect;
+      }
+      else
+      {
+        SetRect(&mouseRect, 0, 0, GetSystemMetrics(SM_CXSCREEN), GetSystemMetrics(SM_CYSCREEN));
+        clipRect = mouseRect;
+      }
+      unmodRect = sizingRect;
     }
+  ClipCursor(&clipRect);
+
   origRect = sizingRect;
   if (ON_LEFT_BORDER(hittest))
     {
@@ -1401,23 +523,28 @@ DefWndDoSizeMove(HWND hwnd, WORD wParam)
       mouseRect.bottom = min( mouseRect.bottom, sizingRect.top+maxTrack.y );
     }
   if (Style & WS_CHILD)
-    {      
+    {
       MapWindowPoints( hWndParent, 0, (LPPOINT)&mouseRect, 2 );
     }
+
   SendMessageA( hwnd, WM_ENTERSIZEMOVE, 0, 0 );
-  
-  if (GetCapture() != hwnd) SetCapture( hwnd );    
-  
+  NtUserSetGUIThreadHandle(MSQ_STATE_MOVESIZE, hwnd);
+  if (GetCapture() != hwnd) SetCapture( hwnd );
+
   if (Style & WS_CHILD)
     {
       /* Retrieve a default cache DC (without using the window style) */
       hdc = GetDCEx(hWndParent, 0, DCX_CACHE);
+      DesktopRgn = NULL;
     }
   else
     {
       hdc = GetDC( 0 );
+      DesktopRgn = CreateRectRgnIndirect(&clipRect);
     }
-  
+
+  SelectObject(hdc, DesktopRgn);
+
   if( iconic ) /* create a cursor for dragging */
     {
       HICON hIcon = (HICON)GetClassLongW(hwnd, GCL_HICON);
@@ -1425,24 +552,25 @@ DefWndDoSizeMove(HWND hwnd, WORD wParam)
       if( hIcon ) hDragCursor = CursorIconToCursor( hIcon, TRUE );
       if( !hDragCursor ) iconic = FALSE;
     }
-  
+
   /* invert frame if WIN31_LOOK to indicate mouse click on caption */
   if( !iconic && !DragFullWindows)
     {
-      UserDrawMovingFrame( hdc, &sizingRect, thickframe );
+      UserDrawMovingFrame( hdc, &sizingRect, thickframe);
     }
-  
-  while(1)
+
+  for(;;)
     {
       int dx = 0, dy = 0;
 
-      GetMessageW(&msg, 0, 0, 0);
-      
+      if (GetMessageW(&msg, 0, 0, 0) <= 0)
+        break;
+
       /* Exit on button-up, Return, or Esc */
       if ((msg.message == WM_LBUTTONUP) ||
-         ((msg.message == WM_KEYDOWN) && 
+         ((msg.message == WM_KEYDOWN) &&
           ((msg.wParam == VK_RETURN) || (msg.wParam == VK_ESCAPE)))) break;
-      
+
       if (msg.message == WM_PAINT)
         {
          if(!iconic && !DragFullWindows) UserDrawMovingFrame( hdc, &sizingRect, thickframe );
@@ -1450,48 +578,47 @@ DefWndDoSizeMove(HWND hwnd, WORD wParam)
          if(!iconic && !DragFullWindows) UserDrawMovingFrame( hdc, &sizingRect, thickframe );
          continue;
         }
-      
+
       if ((msg.message != WM_KEYDOWN) && (msg.message != WM_MOUSEMOVE))
        continue;  /* We are not interested in other messages */
-      
+
       pt = msg.pt;
-      
+
       if (msg.message == WM_KEYDOWN) switch(msg.wParam)
        {
        case VK_UP:    pt.y -= 8; break;
        case VK_DOWN:  pt.y += 8; break;
        case VK_LEFT:  pt.x -= 8; break;
-       case VK_RIGHT: pt.x += 8; break;                
+       case VK_RIGHT: pt.x += 8; break;
        }
-      
+
       pt.x = max( pt.x, mouseRect.left );
       pt.x = min( pt.x, mouseRect.right );
       pt.y = max( pt.y, mouseRect.top );
       pt.y = min( pt.y, mouseRect.bottom );
-      
+
       dx = pt.x - capturePoint.x;
       dy = pt.y - capturePoint.y;
-      
+
       if (dx || dy)
        {
          if( !moved )
            {
              moved = TRUE;
-             
+
                if( iconic ) /* ok, no system popup tracking */
                  {
                    hOldCursor = SetCursor(hDragCursor);
                    ShowCursor( TRUE );
-                   WinPosShowIconTitle( hwnd, FALSE );
-                 } 
+                 }
            }
-         
+
          if (msg.message == WM_KEYDOWN) SetCursorPos( pt.x, pt.y );
          else
            {
-             RECT newRect = sizingRect;
+             RECT newRect = unmodRect;
              WPARAM wpSizingHit = 0;
-             
+
              if (hittest == HTCAPTION) OffsetRect( &newRect, dx, dy );
              if (ON_LEFT_BORDER(hittest)) newRect.left += dx;
              else if (ON_RIGHT_BORDER(hittest)) newRect.right += dx;
@@ -1499,12 +626,13 @@ DefWndDoSizeMove(HWND hwnd, WORD wParam)
              else if (ON_BOTTOM_BORDER(hittest)) newRect.bottom += dy;
              if(!iconic && !DragFullWindows) UserDrawMovingFrame( hdc, &sizingRect, thickframe );
              capturePoint = pt;
-             
+
              /* determine the hit location */
              if (hittest >= HTLEFT && hittest <= HTBOTTOMRIGHT)
                wpSizingHit = WMSZ_LEFT + (hittest - HTLEFT);
+             unmodRect = newRect;
              SendMessageA( hwnd, WM_SIZING, wpSizingHit, (LPARAM)&newRect );
-             
+
              if (!iconic)
                {
                  if(!DragFullWindows)
@@ -1522,8 +650,9 @@ DefWndDoSizeMove(HWND hwnd, WORD wParam)
            }
        }
     }
-  
+
   ReleaseCapture();
+  ClipCursor(NULL);
   if( iconic )
     {
       if( moved ) /* restore cursors, show icon title later on */
@@ -1535,15 +664,21 @@ DefWndDoSizeMove(HWND hwnd, WORD wParam)
     }
   else if(!DragFullWindows)
       UserDrawMovingFrame( hdc, &sizingRect, thickframe );
-  
+
   if (Style & WS_CHILD)
     ReleaseDC( hWndParent, hdc );
   else
+  {
     ReleaseDC( 0, hdc );
-  
+    if(DesktopRgn)
+    {
+      DeleteObject(DesktopRgn);
+    }
+  }
+  NtUserSetGUIThreadHandle(MSQ_STATE_MOVESIZE, NULL);
   SendMessageA( hwnd, WM_EXITSIZEMOVE, 0, 0 );
   SendMessageA( hwnd, WM_SETVISIBLE, !IsIconic(hwnd), 0L);
-  
+
   /* window moved or resized */
   if (moved)
     {
@@ -1565,43 +700,103 @@ DefWndDoSizeMove(HWND hwnd, WORD wParam)
                        origRect.right - origRect.left,
                        origRect.bottom - origRect.top,
                        ( hittest == HTCAPTION ) ? SWP_NOSIZE : 0 );
-      }      
+      }
     }
-  
+
   if( IsWindow(hwnd) )
     if( Style & WS_MINIMIZE )
       {
        /* Single click brings up the system menu when iconized */
-       
-       if( !moved ) 
+
+       if( !moved )
          {
-           if( Style & WS_SYSMENU ) 
+           if( Style & WS_SYSMENU )
              SendMessageA( hwnd, WM_SYSCOMMAND,
                            SC_MOUSEMENU + HTSYSMENU, MAKELONG(pt.x,pt.y));
          }
-       else WinPosShowIconTitle( hwnd, TRUE );
       }
 }
 
 
+/***********************************************************************
+ *           DefWndTrackScrollBar
+ *
+ * Track a mouse button press on the horizontal or vertical scroll-bar.
+ */
+STATIC VOID
+DefWndTrackScrollBar(HWND Wnd, WPARAM wParam, POINT Pt)
+{
+  INT ScrollBar;
+
+  if (SC_HSCROLL == (wParam & 0xfff0))
+    {
+      if (HTHSCROLL != (wParam & 0x0f))
+        {
+          return;
+        }
+      ScrollBar = SB_HORZ;
+    }
+  else  /* SC_VSCROLL */
+    {
+      if (HTVSCROLL != (wParam & 0x0f))
+        {
+          return;
+        }
+      ScrollBar = SB_VERT;
+    }
+  ScrollTrackScrollBar(Wnd, ScrollBar, Pt );
+}
+
+
 LRESULT
 DefWndHandleSysCommand(HWND hWnd, WPARAM wParam, POINT Pt)
 {
+  WINDOWPLACEMENT wp;
+
   switch (wParam & 0xfff0)
     {
       case SC_MOVE:
       case SC_SIZE:
        DefWndDoSizeMove(hWnd, wParam);
        break;
+      case SC_MINIMIZE:
+        wp.length = sizeof(WINDOWPLACEMENT);
+        if(GetWindowPlacement(hWnd, &wp))
+        {
+          wp.showCmd = SW_MINIMIZE;
+          SetWindowPlacement(hWnd, &wp);
+        }
+        break;
+      case SC_MAXIMIZE:
+        wp.length = sizeof(WINDOWPLACEMENT);
+        if(GetWindowPlacement(hWnd, &wp))
+        {
+          wp.showCmd = SW_MAXIMIZE;
+          SetWindowPlacement(hWnd, &wp);
+        }
+        break;
+      case SC_RESTORE:
+        wp.length = sizeof(WINDOWPLACEMENT);
+        if(GetWindowPlacement(hWnd, &wp))
+        {
+          wp.showCmd = SW_RESTORE;
+          SetWindowPlacement(hWnd, &wp);
+        }
+        break;
       case SC_CLOSE:
         SendMessageA(hWnd, WM_CLOSE, 0, 0);
         break;
       case SC_MOUSEMENU:
-        MenuTrackMouseMenuBar(hWnd, wParam, Pt);
+        MenuTrackMouseMenuBar(hWnd, wParam & 0x000f, Pt);
        break;
       case SC_KEYMENU:
         MenuTrackKbdMenuBar(hWnd, wParam, Pt.x);
        break;
+      case SC_VSCROLL:
+      case SC_HSCROLL:
+        DefWndTrackScrollBar(hWnd, wParam, Pt);
+       break;
+
       default:
        /* FIXME: Implement */
         UNIMPLEMENTED;
@@ -1611,134 +806,29 @@ DefWndHandleSysCommand(HWND hWnd, WPARAM wParam, POINT Pt)
   return(0);
 }
 
-
-VOID
-DefWndAdjustRect(HWND hWnd, RECT* Rect, ULONG Style, BOOL Menu, ULONG ExStyle)
-{
-  SIZE FrameSize;
-  
-  if(Style & WS_ICONIC)
-    return;
-  
-  UserGetFrameSize(Style, ExStyle, &FrameSize);
-  
-  InflateRect(Rect, FrameSize.cx, FrameSize.cy);
-  
-  if(Style & WS_CAPTION)
-  {
-    Rect->top -= GetSystemMetrics(SM_CYCAPTION);
-  }
-  if(Menu)
-  {
-    Rect->top -= MenuGetMenuBarHeight(hWnd, Rect->right - Rect->left, -Rect->left, -Rect->top);
-  }
-}
-
-LRESULT STDCALL
-DefWndNCCalcSize(HWND hWnd, BOOL CalcSizeStruct, RECT* Rect)
-{
-    LRESULT Result = 0;
-    LONG ScrollXY;
-    SIZE FrameSize;
-    NCCALCSIZE_PARAMS *SizeStruct = (NCCALCSIZE_PARAMS *)Rect;
-    RECT NewRect, TmpRect = {0, 0, 0, 0};
-    ULONG ExStyle = GetWindowLongW(hWnd, GWL_EXSTYLE);
-    LONG Style = GetClassLongW(hWnd, GCL_STYLE);
-
-    if (Style & CS_VREDRAW)
-    {
-        Result |= WVR_VREDRAW;
-    }
-    if (Style & CS_HREDRAW)
-    {
-        Result |= WVR_HREDRAW;
-    }
-    
-    Style = GetWindowLongW(hWnd, GWL_STYLE);
-
-    if (!(Style & WS_MINIMIZE))
-    {
-        if(!(Style & WS_ICONIC))
-        {
-            UserGetFrameSize(Style, ExStyle, &FrameSize);
-            InflateRect(&TmpRect, FrameSize.cx, FrameSize.cy);
-            if(Style & WS_CAPTION)
-                TmpRect.top -= GetSystemMetrics(SM_CYCAPTION);
-        }
-
-        if(CalcSizeStruct)
-        {
-          Rect = &(SizeStruct->rgrc[0]);
-        }
-        else
-        {
-          Result = 0;
-        }
-        
-        NewRect.left = Rect->left - TmpRect.left;
-        NewRect.top = Rect->top - TmpRect.top;
-        NewRect.right = Rect->right - TmpRect.right;
-        NewRect.bottom = Rect->bottom - TmpRect.bottom;
-        if(NewRect.top > NewRect.bottom)
-            NewRect.bottom = NewRect.top;
-        if(NewRect.left > NewRect.right)
-            NewRect.right = NewRect.left;
-            
-        if(UserHasMenu(hWnd, Style))
-            NewRect.top += MenuGetMenuBarHeight(hWnd, NewRect.right - NewRect.left, NewRect.left, NewRect.top);
-        
-        if (Style & WS_VSCROLL)
-        {
-          ScrollXY = GetSystemMetrics(SM_CXVSCROLL);
-          if(NewRect.right - NewRect.left > ScrollXY)
-          {
-            NewRect.right -= ScrollXY + 1;
-            if (UserHasAnyFrameStyle(Style, ExStyle))
-            {
-              NewRect.right++;
-            }
-          }
-        }
-        if (Style & WS_HSCROLL)
-        {
-          ScrollXY = GetSystemMetrics(SM_CYHSCROLL);
-          if(NewRect.bottom - NewRect.top > ScrollXY)
-          {
-            NewRect.bottom -= ScrollXY + 1;
-            if (UserHasAnyFrameStyle(Style, ExStyle))
-            {
-              NewRect.bottom++;
-            }
-          }
-        }
-        
-        Rect->left = NewRect.left;
-        Rect->top = NewRect.top;
-        Rect->right = NewRect.right;
-        Rect->bottom = NewRect.bottom;
-        
-    }
-    return Result;
-}
-
 LRESULT
 DefWndHandleWindowPosChanging(HWND hWnd, WINDOWPOS* Pos)
 {
-    POINT maxSize, minTrack;
+    POINT maxTrack, minTrack;
     LONG style = GetWindowLongA(hWnd, GWL_STYLE);
 
     if (Pos->flags & SWP_NOSIZE) return 0;
     if ((style & WS_THICKFRAME) || ((style & (WS_POPUP | WS_CHILD)) == 0))
     {
-        WinPosGetMinMaxInfo(hWnd, &maxSize, NULL, &minTrack, NULL);
-        Pos->cx = min(Pos->cx, maxSize.x);
-        Pos->cy = min(Pos->cy, maxSize.y);
+        WinPosGetMinMaxInfo(hWnd, NULL, NULL, &minTrack, &maxTrack);
+        Pos->cx = min(Pos->cx, maxTrack.x);
+        Pos->cy = min(Pos->cy, maxTrack.y);
         if (!(style & WS_MINIMIZE))
         {
             if (Pos->cx < minTrack.x) Pos->cx = minTrack.x;
             if (Pos->cy < minTrack.y) Pos->cy = minTrack.y;
         }
     }
+    else
+    {
+        Pos->cx = max(Pos->cx, 0);
+        Pos->cy = max(Pos->cy, 0);
+    }
     return 0;
 }
 
@@ -1783,7 +873,7 @@ DefWndHandleWindowPosChanged(HWND hWnd, WINDOWPOS* Pos)
  *
  * Default colors for control painting.
  */
-static HBRUSH
+HBRUSH
 DefWndControlColor(HDC hDC, UINT ctlType)
 {
   if (CTLCOLOR_SCROLLBAR == ctlType)
@@ -1799,11 +889,19 @@ DefWndControlColor(HDC hDC, UINT ctlType)
        */
       if (bk == GetSysColor(COLOR_WINDOW))
        {
-#if 0 /* FIXME */
-         return CACHE_GetPattern55AABrush();
-#else
-         return NULL;
-#endif
+          static const WORD wPattern55AA[] =
+          {
+              0x5555, 0xaaaa, 0x5555, 0xaaaa,
+              0x5555, 0xaaaa, 0x5555, 0xaaaa
+          };
+          static HBITMAP hPattern55AABitmap = NULL;
+          static HBRUSH hPattern55AABrush = NULL;
+          if (hPattern55AABrush == NULL)
+            {
+              hPattern55AABitmap = CreateBitmap(8, 8, 1, 1, wPattern55AA);
+              hPattern55AABrush = CreatePatternBrush(hPattern55AABitmap);
+            }
+          return hPattern55AABrush;
        }
       UnrealizeObject(hb);
       return hb;
@@ -1824,6 +922,11 @@ DefWndControlColor(HDC hDC, UINT ctlType)
   return GetSysColorBrush(COLOR_WINDOW);
 }
 
+VOID FASTCALL
+DefWndScreenshot(HWND hWnd)
+{
+
+}
 
 LRESULT STDCALL
 User32DefWindowProc(HWND hWnd,
@@ -1834,57 +937,47 @@ User32DefWindowProc(HWND hWnd,
 {
     switch (Msg)
     {
-        case WM_NCPAINT:
-        {
-            return (DefWndPaintNC(hWnd, (HRGN)wParam));
+       case WM_NCPAINT:
+       {
+            return DefWndNCPaint(hWnd, (HRGN)wParam, -1);
         }
 
         case WM_NCCALCSIZE:
         {
-            return (DefWndNCCalcSize(hWnd, (BOOL)wParam, (RECT*)lParam));
-        }
-
-        case WM_WINDOWPOSCHANGING:
-        {
-            return (DefWndHandleWindowPosChanging(hWnd, (WINDOWPOS*)lParam));
+            return DefWndNCCalcSize(hWnd, (BOOL)wParam, (RECT*)lParam);
         }
 
-        case WM_WINDOWPOSCHANGED:
+        case WM_NCACTIVATE:
         {
-            return (DefWndHandleWindowPosChanged(hWnd, (WINDOWPOS*)lParam));
+            return DefWndNCActivate(hWnd, wParam);
         }
 
         case WM_NCHITTEST:
         {
             POINT Point;
-            Point.x = SLOWORD(lParam);
-            Point.y = SHIWORD(lParam);
-            return (DefWndHitTestNC(hWnd, Point));
+            Point.x = GET_X_LPARAM(lParam);
+            Point.y = GET_Y_LPARAM(lParam);
+            return (DefWndNCHitTest(hWnd, Point));
         }
 
         case WM_NCLBUTTONDOWN:
         {
-            return (DefWndHandleLButtonDownNC(hWnd, wParam, lParam));
+            return (DefWndNCLButtonDown(hWnd, wParam, lParam));
         }
 
-        case WM_NCLBUTTONUP:
+        case WM_NCLBUTTONDBLCLK:
         {
-            return (DefWndHandleLButtonUpNC(hWnd, wParam, lParam));
+            return (DefWndNCLButtonDblClk(hWnd, wParam, lParam));
         }
 
-        case WM_LBUTTONDBLCLK:
-        case WM_NCLBUTTONDBLCLK:
+        case WM_WINDOWPOSCHANGING:
         {
-            return (DefWndHandleLButtonDblClkNC(hWnd, wParam, lParam));
+            return (DefWndHandleWindowPosChanging(hWnd, (WINDOWPOS*)lParam));
         }
 
-        case WM_NCRBUTTONDOWN:
+        case WM_WINDOWPOSCHANGED:
         {
-            if (wParam == HTCAPTION)
-            {
-                SetCapture(hWnd);
-            }
-            break;
+            return (DefWndHandleWindowPosChanged(hWnd, (WINDOWPOS*)lParam));
         }
 
         case WM_RBUTTONUP:
@@ -1894,8 +987,8 @@ User32DefWindowProc(HWND hWnd,
             {
                 ReleaseCapture();
             }
-            Pt.x = SLOWORD(lParam);
-            Pt.y = SHIWORD(lParam);
+            Pt.x = GET_X_LPARAM(lParam);
+            Pt.y = GET_Y_LPARAM(lParam);
             ClientToScreen(hWnd, &Pt);
             lParam = MAKELPARAM(Pt.x, Pt.y);
             if (bUnicode)
@@ -1924,33 +1017,44 @@ User32DefWindowProc(HWND hWnd,
             }
             else
             {
-                LONG HitCode;
                 POINT Pt;
+                DWORD Style;
+                LONG HitCode;
 
-                Pt.x = SLOWORD(lParam);
-                Pt.y = SHIWORD(lParam);
-                if (GetWindowLongW(hWnd, GWL_STYLE) & WS_CHILD)
+                Style = GetWindowLongW(hWnd, GWL_STYLE);
+
+                Pt.x = GET_X_LPARAM(lParam);
+                Pt.y = GET_Y_LPARAM(lParam);
+                if (Style & WS_CHILD)
                 {
                     ScreenToClient(GetParent(hWnd), &Pt);
                 }
 
-                HitCode = DefWndHitTestNC(hWnd, Pt);
+                HitCode = DefWndNCHitTest(hWnd, Pt);
 
                 if (HitCode == HTCAPTION || HitCode == HTSYSMENU)
                 {
-                    TrackPopupMenu(GetSystemMenu(hWnd, FALSE),
-                                   TPM_LEFTBUTTON | TPM_RIGHTBUTTON,
-                                   Pt.x, Pt.y, 0, hWnd, NULL);
+                    HMENU SystemMenu;
+                    UINT Flags;
+
+                    if((SystemMenu = GetSystemMenu(hWnd, FALSE)))
+                    {
+                      MenuInitSysMenuPopup(SystemMenu, GetWindowLongW(hWnd, GWL_STYLE),
+                                           GetClassLongW(hWnd, GCL_STYLE), HitCode);
+
+                      if(HitCode == HTCAPTION)
+                        Flags = TPM_LEFTBUTTON | TPM_RIGHTBUTTON;
+                      else
+                        Flags = TPM_LEFTBUTTON;
+
+                      TrackPopupMenu(SystemMenu, Flags,
+                                     Pt.x, Pt.y, 0, hWnd, NULL);
+                    }
                 }
-               }
+           }
             break;
         }
 
-        case WM_NCACTIVATE:
-        {
-            return (DefWndHandleActiveNC(hWnd, wParam));
-        }
-
         case WM_PRINT:
         {
             /* FIXME: Implement. */
@@ -1963,25 +1067,19 @@ User32DefWindowProc(HWND hWnd,
             PAINTSTRUCT Ps;
             HDC hDC = BeginPaint(hWnd, &Ps);
             if (hDC)
-            {          
+            {
                 HICON hIcon;
                 if (GetWindowLongW(hWnd, GWL_STYLE) & WS_MINIMIZE &&
                     (hIcon = (HICON)GetClassLongW(hWnd, GCL_HICON)) != NULL)
                 {
-                    RECT WindowRect;
+                    RECT ClientRect;
                     INT x, y;
-                    GetWindowRect(hWnd, &WindowRect);
-                    x = (WindowRect.right - WindowRect.left -
+                    GetClientRect(hWnd, &ClientRect);
+                    x = (ClientRect.right - ClientRect.left -
                          GetSystemMetrics(SM_CXICON)) / 2;
-                    y = (WindowRect.bottom - WindowRect.top -
+                    y = (ClientRect.bottom - ClientRect.top -
                          GetSystemMetrics(SM_CYICON)) / 2;
                     DrawIcon(hDC, x, y, hIcon);
-                } 
-                if (GetWindowLongW(hWnd, GWL_EXSTYLE) & WS_EX_CLIENTEDGE)
-                {
-                    RECT WindowRect;
-                    GetClientRect(hWnd, &WindowRect);
-                    DrawEdge(hDC, &WindowRect, EDGE_SUNKEN, BF_RECT);
                 }
                 EndPaint(hWnd, &Ps);
             }
@@ -2040,7 +1138,7 @@ User32DefWindowProc(HWND hWnd,
         case WM_ACTIVATE:
         {
             /* Check if the window is minimized. */
-            if (LOWORD(lParam) != WA_INACTIVE &&
+            if (LOWORD(wParam) != WA_INACTIVE &&
                 !(GetWindowLongW(hWnd, GWL_STYLE) & WS_MINIMIZE))
             {
                 SetFocus(hWnd);
@@ -2076,11 +1174,16 @@ User32DefWindowProc(HWND hWnd,
             {
                 return 0;
             }
-            if (0 == (((DWORD) hBrush) & 0xffff0000))
+            if (GetClassLongW(hWnd, GCL_STYLE) & CS_PARENTDC)
+            {
+                /* can't use GetClipBox with a parent DC or we fill the whole parent */
+                GetClientRect(hWnd, &Rect);
+                DPtoLP((HDC)wParam, (LPPOINT)&Rect, 2);
+            }
+            else
             {
-                hBrush = GetSysColorBrush((DWORD) hBrush - 1);
+                GetClipBox((HDC)wParam, &Rect);
             }
-            GetClipBox((HDC)wParam, &Rect);
             FillRect((HDC)wParam, &Rect, hBrush);
             return (1);
         }
@@ -2096,7 +1199,9 @@ User32DefWindowProc(HWND hWnd,
 
         case WM_SETCURSOR:
         {
-            if (GetWindowLongW(hWnd, GWL_STYLE) & WS_CHILD)
+            ULONG Style = GetWindowLongW(hWnd, GWL_STYLE);
+
+            if (Style & WS_CHILD)
             {
                 if (LOWORD(lParam) < HTLEFT || LOWORD(lParam) > HTBOTTOMRIGHT)
                 {
@@ -2117,14 +1222,14 @@ User32DefWindowProc(HWND hWnd,
                     }
                 }
             }
-            return (DefWndHandleSetCursor(hWnd, wParam, lParam));
+            return (DefWndHandleSetCursor(hWnd, wParam, lParam, Style));
         }
 
         case WM_SYSCOMMAND:
         {
             POINT Pt;
-            Pt.x = SLOWORD(lParam);
-            Pt.y = SHIWORD(lParam);
+            Pt.x = GET_X_LPARAM(lParam);
+            Pt.y = GET_Y_LPARAM(lParam);
             return (DefWndHandleSysCommand(hWnd, wParam, Pt));
         }
 
@@ -2151,11 +1256,15 @@ User32DefWindowProc(HWND hWnd,
                         else
                             PostMessageA(top, WM_SYSCOMMAND, SC_CLOSE, 0);
                     }
-                   }
+                }
+                else if (wParam == VK_SNAPSHOT)
+                {
+                    DefWndScreenshot(hWnd);
+                }
             }
             break;
         }
-        
+
         case WM_SHOWWINDOW:
         {
             LONG Style;
@@ -2163,14 +1272,15 @@ User32DefWindowProc(HWND hWnd,
             if (!lParam)
                 return 0;
             Style = GetWindowLongW(hWnd, GWL_STYLE);
-            if (!(Style & WS_POPUP))
-                return 0;
+//            if (!(Style & WS_POPUP))
+//                return 0;
             if ((Style & WS_VISIBLE) && wParam)
                 return 0;
             if (!(Style & WS_VISIBLE) && !wParam)
                 return 0;
             if (!GetWindow(hWnd, GW_OWNER))
                 return 0;
+            NtUserCallTwoParam((DWORD) hWnd, (DWORD) wParam, TWOPARAM_ROUTINE_ROS_SHOWWINDOW);
             ShowWindow(hWnd, wParam ? SW_SHOWNA : SW_HIDE);
             break;
         }
@@ -2188,11 +1298,11 @@ User32DefWindowProc(HWND hWnd,
         case WM_VKEYTOITEM:
         case WM_CHARTOITEM:
             return (-1);
-
+/*
         case WM_DROPOBJECT:
-            /* FIXME: Implement this. */
-            break;
 
+            break;
+*/
         case WM_QUERYDROPOBJECT:
         {
             if (GetWindowLongW(hWnd, GWL_EXSTYLE) & WS_EX_ACCEPTFILES)
@@ -2249,7 +1359,7 @@ User32DefWindowProc(HWND hWnd,
 
         case WM_GETICON:
         {
-            INT Index = (wParam != 0) ? GCL_HICON : GCL_HICONSM;
+            INT Index = (wParam == ICON_BIG) ? GCL_HICON : GCL_HICONSM;
             return (GetClassLongW(hWnd, Index));
         }
 
@@ -2266,6 +1376,22 @@ User32DefWindowProc(HWND hWnd,
             break;
         }
 
+        case WM_SYSTIMER:
+        {
+          THRDCARETINFO CaretInfo;
+          switch(wParam)
+          {
+            case 0xffff: /* Caret timer */
+              /* switch showing byte in win32k and get information about the caret */
+              if(NtUserSwitchCaretShowing(&CaretInfo) && (CaretInfo.hWnd == hWnd))
+              {
+                DrawCaret(hWnd, &CaretInfo);
+              }
+              break;
+          }
+          break;
+        }
+
         case WM_QUERYOPEN:
         case WM_QUERYENDSESSION:
         {
@@ -2282,75 +1408,64 @@ DefWindowProcA(HWND hWnd,
               WPARAM wParam,
               LPARAM lParam)
 {
-    static LPSTR WindowTextAtom = 0;
-    PSTR WindowText;
-
     switch (Msg)
     {
         case WM_NCCREATE:
         {
-            CREATESTRUCTA *Cs = (CREATESTRUCTA*)lParam;
-            if (HIWORD(Cs->lpszName))
-            {
-                if (0 == WindowTextAtom)
-                {
-                    WindowTextAtom =
-                        (LPSTR)(ULONG)GlobalAddAtomA("USER32!WindowTextAtomA");
-                }
-                WindowText = RtlAllocateHeap(RtlGetProcessHeap(), 0,
-                    (strlen(Cs->lpszName) + 1) * sizeof(CHAR));
-                strcpy(WindowText, Cs->lpszName);
-                SetPropA(hWnd, WindowTextAtom, WindowText);
-               }
-            return (1);
+            return TRUE;
         }
 
         case WM_GETTEXTLENGTH:
         {
-            if (WindowTextAtom == 0 ||
-                (WindowText = GetPropA(hWnd, WindowTextAtom)) == NULL)
-            {
-                return(0);
-            }
-            return (strlen(WindowText));
+            return (LRESULT)NtUserInternalGetWindowText(hWnd, NULL, 0);
         }
 
         case WM_GETTEXT:
         {
-            if (WindowTextAtom == 0 ||
-                (WindowText = GetPropA(hWnd, WindowTextAtom)) == NULL)
+            LPWSTR Buffer;
+            LPSTR AnsiBuffer = (LPSTR)lParam;
+            INT Length;
+
+            if (wParam > 1)
             {
-                if (wParam > 1)
-                   {
-                    *((PSTR)lParam) = '\0';
-                }
-                return (0);
+                *((PWSTR)lParam) = '\0';
+            }
+            Buffer = HeapAlloc(GetProcessHeap(), 0, wParam * sizeof(WCHAR));
+            if (!Buffer)
+                return FALSE;
+            Length = NtUserInternalGetWindowText(hWnd, Buffer, wParam);
+            if (Length > 0 && wParam > 0 &&
+                !WideCharToMultiByte(CP_ACP, 0, Buffer, -1,
+                AnsiBuffer, wParam, NULL, NULL))
+            {
+                AnsiBuffer[0] = '\0';
             }
-            strncpy((LPSTR)lParam, WindowText, wParam);
-            return (min(wParam, strlen(WindowText)));
+
+            HeapFree(GetProcessHeap(), 0, Buffer);
+
+            return (LRESULT)Length;
         }
 
         case WM_SETTEXT:
         {
-            if (0 == WindowTextAtom)
+            ANSI_STRING AnsiString;
+            UNICODE_STRING UnicodeString;
+
+            if(lParam)
             {
-                WindowTextAtom =
-                    (LPSTR)(DWORD)GlobalAddAtomA("USER32!WindowTextAtomA");
-               }
-            if (WindowTextAtom != 0 &&
-                (WindowText = GetPropA(hWnd, WindowTextAtom)) == NULL)
-               {
-                RtlFreeHeap(RtlGetProcessHeap(), 0, WindowText);
+              RtlInitAnsiString(&AnsiString, (LPSTR)lParam);
+              RtlAnsiStringToUnicodeString(&UnicodeString, &AnsiString, TRUE);
+              NtUserDefSetText(hWnd, &UnicodeString);
+              RtlFreeUnicodeString(&UnicodeString);
             }
-            WindowText = RtlAllocateHeap(RtlGetProcessHeap(), 0,
-                (strlen((PSTR)lParam) + 1) * sizeof(CHAR));
-            strcpy(WindowText, (PSTR)lParam);
-            SetPropA(hWnd, WindowTextAtom, WindowText);
-            if (0 != (GetWindowLongW(hWnd, GWL_STYLE) & WS_CAPTION))
-               {
-                DefWndPaintNC(hWnd, (HRGN) 1);
+            else
+              NtUserDefSetText(hWnd, NULL);
+
+            if ((GetWindowLongW(hWnd, GWL_STYLE) & WS_CAPTION) == WS_CAPTION)
+            {
+                DefWndNCPaint(hWnd, (HRGN)1, -1);
             }
-            return (1);
+            return TRUE;
         }
 
 /*
@@ -2364,16 +1479,6 @@ DefWindowProcA(HWND hWnd,
         case WM_IME_SELECT:
         case WM_IME_SETCONTEXT:
 */
-
-        case WM_NCDESTROY:
-        {
-            if (WindowTextAtom != 0 &&
-                (WindowText = RemovePropA(hWnd, WindowTextAtom)) == NULL)
-            {
-                RtlFreeHeap(GetProcessHeap(), 0, WindowText);
-            }
-            return(0);
-        }
     }
 
     return User32DefWindowProc(hWnd, Msg, wParam, lParam, FALSE);
@@ -2386,73 +1491,39 @@ DefWindowProcW(HWND hWnd,
               WPARAM wParam,
               LPARAM lParam)
 {
-    static LPWSTR WindowTextAtom = 0;
-    PWSTR WindowText;
-
     switch (Msg)
     {
         case WM_NCCREATE:
         {
-            CREATESTRUCTW* CreateStruct = (CREATESTRUCTW*)lParam;
-            if (HIWORD(CreateStruct->lpszName))
-            {
-                if (0 == WindowTextAtom)
-                {
-                    WindowTextAtom =
-                        (LPWSTR)(DWORD)GlobalAddAtomW(L"USER32!WindowTextAtomW");
-                }
-                WindowText = RtlAllocateHeap(RtlGetProcessHeap(), 0,
-                               (wcslen(CreateStruct->lpszName) + 1) * sizeof(WCHAR));
-                wcscpy(WindowText, CreateStruct->lpszName);
-                SetPropW(hWnd, WindowTextAtom, WindowText);
-            }
-            return (1);
+            return TRUE;
         }
 
         case WM_GETTEXTLENGTH:
         {
-            if (WindowTextAtom == 0 ||
-                (WindowText = GetPropW(hWnd, WindowTextAtom)) == NULL)
-            {
-                return(0);
-            }
-            return (wcslen(WindowText));
+            return (LRESULT)NtUserInternalGetWindowText(hWnd, NULL, 0);
         }
 
         case WM_GETTEXT:
         {
-            if (WindowTextAtom == 0 ||
-                (WindowText = GetPropW(hWnd, WindowTextAtom)) == NULL)
+            if (wParam > 1)
             {
-               if (wParam > 1)
-               {
-                   ((PWSTR)lParam) = '\0';
-               }
-               return (0);
+                *((PWSTR)lParam) = L'\0';
             }
-            wcsncpy((PWSTR)lParam, WindowText, wParam);
-            return (min(wParam, wcslen(WindowText)));
+            return (LRESULT)NtUserInternalGetWindowText(hWnd, (PWSTR)lParam, wParam);
         }
 
         case WM_SETTEXT:
         {
-            if (WindowTextAtom == 0)
-            {
-                WindowTextAtom =
-                    (LPWSTR)(DWORD)GlobalAddAtomW(L"USER32!WindowTextAtomW");
-            }
-            if (WindowTextAtom != 0 &&
-                (WindowText = GetPropW(hWnd, WindowTextAtom)) == NULL)
-            {
-                RtlFreeHeap(RtlGetProcessHeap(), 0, WindowText);
-            }
-            WindowText = RtlAllocateHeap(RtlGetProcessHeap(), 0,
-                           (wcslen((PWSTR)lParam) + 1) * sizeof(WCHAR));
-            wcscpy(WindowText, (PWSTR)lParam);
-            SetPropW(hWnd, WindowTextAtom, WindowText);
+            UNICODE_STRING UnicodeString;
+
+            if(lParam)
+              RtlInitUnicodeString(&UnicodeString, (LPWSTR)lParam);
+
+            NtUserDefSetText(hWnd, (lParam ? &UnicodeString : NULL));
+
             if ((GetWindowLongW(hWnd, GWL_STYLE) & WS_CAPTION) == WS_CAPTION)
-               {
-                DefWndPaintNC(hWnd, (HRGN)1);
+            {
+                DefWndNCPaint(hWnd, (HRGN)1, -1);
             }
             return (1);
         }
@@ -2468,16 +1539,6 @@ DefWindowProcW(HWND hWnd,
             /* FIXME */
             return (0);
         }
-
-        case WM_NCDESTROY:
-        {
-            if (WindowTextAtom != 0 &&
-                (WindowText = RemovePropW(hWnd, WindowTextAtom)) == NULL)
-            {
-                RtlFreeHeap(RtlGetProcessHeap(), 0, WindowText);
-            }
-            return (0);
-        }
     }
 
     return User32DefWindowProc(hWnd, Msg, wParam, lParam, TRUE);