Moved scrollbar tracking code to scroll.c.
Avoid unnecessary coordinates conversion in NC_HandleSysCommand.

diff --git a/controls/menu.c b/controls/menu.c
index 50abd2e..931d438 100644
--- a/controls/menu.c
+++ b/controls/menu.c
@@ -2944,6 +2944,10 @@
 
     if (IsMenu(hMenu))
     {
+        /* map point to parent client coordinates */
+        HWND parent = GetAncestor( hWnd, GA_PARENT );
+        if (parent != GetDesktopWindow()) ScreenToClient( parent, &pt );
+
 	MENU_InitTracking( hWnd, hMenu, FALSE, wFlags );
 	MENU_TrackMenu( hMenu, wFlags, pt.x, pt.y, hWnd, NULL );
 	MENU_ExitTracking(hWnd);
diff --git a/controls/scroll.c b/controls/scroll.c
index 60d8ce6..55b330d 100644
--- a/controls/scroll.c
+++ b/controls/scroll.c
@@ -895,7 +895,7 @@
  * 'pt' is the location of the mouse event in client (for SB_CTL) or
  * windows coordinates.
  */
-void SCROLL_HandleScrollEvent( HWND hwnd, INT nBar, UINT msg, POINT pt)
+static void SCROLL_HandleScrollEvent( HWND hwnd, INT nBar, UINT msg, POINT pt)
 {
       /* Previous mouse position for timer events */
     static POINT prevPt;
@@ -1110,6 +1110,58 @@
 
 
 /***********************************************************************
+ *           SCROLL_TrackScrollBar
+ *
+ * Track a mouse button press on a scroll-bar.
+ * pt is in screen-coordinates for non-client scroll bars.
+ */
+void SCROLL_TrackScrollBar( HWND hwnd, INT scrollbar, POINT pt )
+{
+    MSG msg;
+    INT xoffset = 0, yoffset = 0;
+
+    if (scrollbar != SB_CTL)
+    {
+        WND *wndPtr = WIN_GetPtr( hwnd );
+        if (!wndPtr || wndPtr == WND_OTHER_PROCESS) return;
+        xoffset = wndPtr->rectClient.left - wndPtr->rectWindow.left;
+        yoffset = wndPtr->rectClient.top - wndPtr->rectWindow.top;
+        WIN_ReleasePtr( wndPtr );
+        ScreenToClient( hwnd, &pt );
+        pt.x += xoffset;
+        pt.y += yoffset;
+    }
+
+    SCROLL_HandleScrollEvent( hwnd, scrollbar, WM_LBUTTONDOWN, pt );
+
+    do
+    {
+        if (!GetMessageW( &msg, 0, 0, 0 )) break;
+        if (CallMsgFilterW( &msg, MSGF_SCROLLBAR )) continue;
+        switch(msg.message)
+        {
+        case WM_LBUTTONUP:
+        case WM_MOUSEMOVE:
+        case WM_SYSTIMER:
+            pt.x = LOWORD(msg.lParam) + xoffset;
+            pt.y = HIWORD(msg.lParam) + yoffset;
+            SCROLL_HandleScrollEvent( hwnd, scrollbar, msg.message, pt );
+            break;
+        default:
+            TranslateMessage( &msg );
+            DispatchMessageW( &msg );
+            break;
+        }
+        if (!IsWindow( hwnd ))
+        {
+            ReleaseCapture();
+            break;
+        }
+    } while (msg.message != WM_LBUTTONUP);
+}
+
+
+/***********************************************************************
  *           ScrollBarWndProc
  */
 static LRESULT WINAPI ScrollBarWndProc( HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam )
@@ -1156,38 +1208,9 @@
     case WM_LBUTTONDOWN:
         {
 	    POINT pt;
-	    MSG msg;
-
 	    pt.x = SLOWORD(lParam);
 	    pt.y = SHIWORD(lParam);
-	    SetCapture( hwnd );
-	    SCROLL_HandleScrollEvent( hwnd, SB_CTL, message, pt );
-
-	    TRACE("Doing LBUTTONDOWN loop hwnd=%08x\n", hwnd);
-	    do {
-		if (!GetMessageW( &msg, 0, 0, 0 )) break;
-		if (CallMsgFilterW( &msg, MSGF_SCROLLBAR )) continue;
-		switch(msg.message)
-		    {
-		    case WM_LBUTTONUP:
-		    case WM_MOUSEMOVE:
-		    case WM_SYSTIMER:
-			pt.x = LOWORD(msg.lParam);
-			pt.y = HIWORD(msg.lParam);
-			SCROLL_HandleScrollEvent( hwnd, SB_CTL, msg.message, pt );
-			break;
-		    default:
-			TranslateMessage( &msg );
-			DispatchMessageW( &msg );
-			break;
-		    }
-		if (!IsWindow( hwnd ))
-		    {
-			ReleaseCapture();
-			break;
-		    }
-	    } while (msg.message != WM_LBUTTONUP);
-	    TRACE("Out ofLBUTTON loop hwnd=%08x\n", hwnd);
+            SCROLL_TrackScrollBar( hwnd, SB_CTL, pt );
 	}
         break;
     case WM_LBUTTONUP:
diff --git a/dlls/user/controls.h b/dlls/user/controls.h
index 11f257d..5492836 100644
--- a/dlls/user/controls.h
+++ b/dlls/user/controls.h
@@ -50,7 +50,7 @@
 
 /* scrollbar */
 extern void SCROLL_DrawScrollBar( HWND hwnd, HDC hdc, INT nBar, BOOL arrows, BOOL interior );
-extern void SCROLL_HandleScrollEvent( HWND hwnd, INT nBar, UINT msg, POINT pt );
+extern void SCROLL_TrackScrollBar( HWND hwnd, INT scrollbar, POINT pt );
 extern INT SCROLL_SetNCSbState( HWND hwnd, int vMin, int vMax, int vPos,
                                 int hMin, int hMax, int hPos );
 
diff --git a/include/nonclient.h b/include/nonclient.h
index 0b95d2a..2d928a4 100644
--- a/include/nonclient.h
+++ b/include/nonclient.h
@@ -15,7 +15,7 @@
 extern LONG NC_HandleNCHitTest( HWND hwnd, POINT pt );
 extern LONG NC_HandleNCLButtonDown( HWND hwnd, WPARAM wParam, LPARAM lParam );
 extern LONG NC_HandleNCLButtonDblClk( HWND hwnd, WPARAM wParam, LPARAM lParam);
-extern LONG NC_HandleSysCommand( HWND hwnd, WPARAM wParam, POINT pt );
+extern LONG NC_HandleSysCommand( HWND hwnd, WPARAM wParam, LPARAM lParam );
 extern LONG NC_HandleSetCursor( HWND hwnd, WPARAM wParam, LPARAM lParam );
 extern void NC_DrawSysButton( HWND hwnd, HDC hdc, BOOL down );
 extern BOOL NC_DrawSysButton95( HWND hwnd, HDC hdc, BOOL down );
diff --git a/windows/defwnd.c b/windows/defwnd.c
index f7573d6..69649cc 100644
--- a/windows/defwnd.c
+++ b/windows/defwnd.c
@@ -500,12 +500,7 @@
 	return NC_HandleSetCursor( hwnd, wParam, lParam );
 
     case WM_SYSCOMMAND:
-        {
-            POINT pt;
-            pt.x = SLOWORD(lParam);
-            pt.y = SHIWORD(lParam);
-            return NC_HandleSysCommand( hwnd, wParam, pt );
-        }
+        return NC_HandleSysCommand( hwnd, wParam, lParam );
 
     case WM_KEYDOWN:
 	if(wParam == VK_F10) iF10Key = VK_F10;
diff --git a/windows/nonclient.c b/windows/nonclient.c
index 111568d..66bb6eb 100644
--- a/windows/nonclient.c
+++ b/windows/nonclient.c
@@ -1954,54 +1954,22 @@
  */
 static void NC_TrackScrollBar( HWND hwnd, WPARAM wParam, POINT pt )
 {
-    MSG msg;
     INT scrollbar;
-    WND *wndPtr = WIN_FindWndPtr( hwnd );
 
     if ((wParam & 0xfff0) == SC_HSCROLL)
     {
-	if ((wParam & 0x0f) != HTHSCROLL) goto END;
+        if ((wParam & 0x0f) != HTHSCROLL) return;
 	scrollbar = SB_HORZ;
     }
     else  /* SC_VSCROLL */
     {
-	if ((wParam & 0x0f) != HTVSCROLL) goto END;
+        if ((wParam & 0x0f) != HTVSCROLL) return;
 	scrollbar = SB_VERT;
     }
-
-    pt.x -= wndPtr->rectWindow.left;
-    pt.y -= wndPtr->rectWindow.top;
-    SetCapture( hwnd );
-    SCROLL_HandleScrollEvent( hwnd, scrollbar, WM_LBUTTONDOWN, pt );
-
-    do
-    {
-        if (!GetMessageW( &msg, 0, 0, 0 )) break;
-        if (CallMsgFilterW( &msg, MSGF_SCROLLBAR )) continue;
-	switch(msg.message)
-	{
-	case WM_LBUTTONUP:
-	case WM_MOUSEMOVE:
-        case WM_SYSTIMER:
-            pt.x = LOWORD(msg.lParam) + wndPtr->rectClient.left - wndPtr->rectWindow.left;
-            pt.y = HIWORD(msg.lParam) + wndPtr->rectClient.top - wndPtr->rectWindow.top;
-            SCROLL_HandleScrollEvent( hwnd, scrollbar, msg.message, pt );
-	    break;
-        default:
-            TranslateMessage( &msg );
-            DispatchMessageW( &msg );
-            break;
-	}
-        if (!IsWindow( hwnd ))
-        {
-            ReleaseCapture();
-            break;
-        }
-    } while (msg.message != WM_LBUTTONUP);
-END:
-    WIN_ReleaseWndPtr(wndPtr);
+    SCROLL_TrackScrollBar( hwnd, scrollbar, pt );
 }
 
+
 /***********************************************************************
  *           NC_HandleNCLButtonDown
  *
@@ -2130,20 +2098,11 @@
  *
  * Handle a WM_SYSCOMMAND message. Called from DefWindowProc().
  */
-LONG NC_HandleSysCommand( HWND hwnd, WPARAM wParam, POINT pt )
+LONG NC_HandleSysCommand( HWND hwnd, WPARAM wParam, LPARAM lParam )
 {
-    WND *wndPtr = WIN_FindWndPtr( hwnd );
-    UINT16 uCommand = wParam & 0xFFF0;
+    TRACE("Handling WM_SYSCOMMAND %x %lx\n", wParam, lParam );
 
-    TRACE("Handling WM_SYSCOMMAND %x %ld,%ld\n", wParam, pt.x, pt.y );
-
-    if (uCommand != SC_KEYMENU)
-    {
-        HWND parent = GetAncestor( hwnd, GA_PARENT );
-        if (parent != GetDesktopWindow()) ScreenToClient( parent, &pt );
-    }
-
-    switch (uCommand)
+    switch (wParam & 0xfff0)
     {
     case SC_SIZE:
     case SC_MOVE:
@@ -2170,22 +2129,31 @@
 	break;
 
     case SC_CLOSE:
-        WIN_ReleaseWndPtr(wndPtr);
 	return SendMessageA( hwnd, WM_CLOSE, 0, 0 );
 
     case SC_VSCROLL:
     case SC_HSCROLL:
-	NC_TrackScrollBar( hwnd, wParam, pt );
+        {
+            POINT pt;
+            pt.x = SLOWORD(lParam);
+            pt.y = SHIWORD(lParam);
+            NC_TrackScrollBar( hwnd, wParam, pt );
+        }
 	break;
 
     case SC_MOUSEMENU:
-        MENU_TrackMouseMenuBar( hwnd, wParam & 0x000F, pt );
+        {
+            POINT pt;
+            pt.x = SLOWORD(lParam);
+            pt.y = SHIWORD(lParam);
+            MENU_TrackMouseMenuBar( hwnd, wParam & 0x000F, pt );
+        }
 	break;
 
     case SC_KEYMENU:
-	MENU_TrackKbdMenuBar( hwnd, wParam , pt.x );
+        MENU_TrackKbdMenuBar( hwnd, wParam, LOWORD(lParam) );
 	break;
-	
+
     case SC_TASKLIST:
 	WinExec( "taskman.exe", SW_SHOWNORMAL ); 
 	break;
@@ -2213,7 +2181,6 @@
  	FIXME("unimplemented!\n");
         break;
     }
-    WIN_ReleaseWndPtr(wndPtr);
     return 0;
 }