Author: jimtabor Date: Mon Aug 20 00:26:08 2012 New Revision: 57111
URL: http://svn.reactos.org/svn/reactos?rev=57111&view=rev Log: [Win32SS] - Active, Focus and Foreground. Fixes many of the the wine tests and including the todos. Fix bug 7089. - Get ATI support points in place, include code support for ptiSysLock which will be rewritten soon. - Move Desktop Proc to Win32k. This will allow the access checks to work. Note: DesktopBG.c creates a Win32 thread every time a Desktop is created. Please keep the file and code intact for historical purposes. - Get code close to wine.
References: Focus test ROS passes: http://www.winehq.org/pipermail/wine-patches/2012-August/116887.html Install acts and looks better: http://www.resmap.com/instructions/plug-ins/ERViewer7_0_RC.exe
Modified: trunk/reactos/win32ss/gdi/ntgdi/device.c trunk/reactos/win32ss/user/ntuser/caret.c trunk/reactos/win32ss/user/ntuser/desktop.c trunk/reactos/win32ss/user/ntuser/desktop.h trunk/reactos/win32ss/user/ntuser/focus.c trunk/reactos/win32ss/user/ntuser/focus.h trunk/reactos/win32ss/user/ntuser/kbdlayout.c trunk/reactos/win32ss/user/ntuser/message.c trunk/reactos/win32ss/user/ntuser/msgqueue.c trunk/reactos/win32ss/user/ntuser/painting.c trunk/reactos/win32ss/user/ntuser/simplecall.c trunk/reactos/win32ss/user/ntuser/win32.h trunk/reactos/win32ss/user/ntuser/window.c trunk/reactos/win32ss/user/ntuser/window.h trunk/reactos/win32ss/user/ntuser/winpos.c trunk/reactos/win32ss/user/user32/controls/regcontrol.c trunk/reactos/win32ss/user/user32/include/controls.h trunk/reactos/win32ss/user/user32/misc/desktop.c trunk/reactos/win32ss/user/user32/windows/message.c trunk/reactos/win32ss/user/win32csr/desktopbg.c
Modified: trunk/reactos/win32ss/gdi/ntgdi/device.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/gdi/ntgdi/device.c?... ============================================================================== --- trunk/reactos/win32ss/gdi/ntgdi/device.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/gdi/ntgdi/device.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -30,6 +30,7 @@ { SIZEL SurfSize; SURFOBJ *pso; + PDESKTOP rpDesk;
/* Attach monitor */ UserAttachMonitor((HDEV)gppdevPrimary); @@ -45,7 +46,18 @@ gpsi->ptCursor.x = pso->sizlBitmap.cx / 2; gpsi->ptCursor.y = pso->sizlBitmap.cy / 2;
- co_IntShowDesktop(IntGetActiveDesktop(), SurfSize.cx, SurfSize.cy); + rpDesk = IntGetActiveDesktop(); + if (!rpDesk) + { /* First time going in from winlogon and starting up application desktop and + haven't switch to winlogon desktop. Also still in WM_CREATE. */ + PTHREADINFO pti = PsGetCurrentThreadWin32Thread(); + rpDesk = pti->rpdesk; + if (!rpDesk) + { + DPRINT1("No DESKTOP Window!!!!!\n"); + } + } + co_IntShowDesktop(rpDesk, SurfSize.cx, SurfSize.cy);
// Init Primary Displays Device Capabilities. PDEVOBJ_vGetDeviceCaps(gppdevPrimary, &GdiHandleTable->DevCaps);
Modified: trunk/reactos/win32ss/user/ntuser/caret.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/caret.c... ============================================================================== --- trunk/reactos/win32ss/user/ntuser/caret.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/caret.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -202,11 +202,11 @@ return FALSE; }
- if(!ThreadQueue->CaretInfo->Visible && ThreadQueue->CaretInfo->hWnd) + if (!ThreadQueue->CaretInfo->Visible) { ThreadQueue->CaretInfo->Visible = 1; - pWnd = UserGetWindowObject(ThreadQueue->CaretInfo->hWnd); - if (!ThreadQueue->CaretInfo->Showing) + pWnd = ValidateHwndNoErr(ThreadQueue->CaretInfo->hWnd); + if (!ThreadQueue->CaretInfo->Showing && pWnd) { co_IntSendMessage(ThreadQueue->CaretInfo->hWnd, WM_SYSTIMER, IDCARETTIMER, 0); IntNotifyWinEvent(EVENT_OBJECT_SHOW, pWnd, OBJID_CARET, OBJID_CARET, 0);
Modified: trunk/reactos/win32ss/user/ntuser/desktop.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/desktop... ============================================================================== --- trunk/reactos/win32ss/user/ntuser/desktop.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/desktop.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -550,6 +550,8 @@ LRESULT FASTCALL DesktopWindowProc(PWND Wnd, UINT Msg, WPARAM wParam, LPARAM lParam) { + ULONG Value; + //ERR("DesktopWindowProc\n"); switch (Msg) { case WM_NCCREATE: @@ -558,6 +560,20 @@ Wnd->fnid = FNID_DESKTOP; } return (LRESULT)TRUE; + + case WM_CREATE: + Value = HandleToULong(PsGetCurrentProcessId()); + // Save Process ID + co_UserSetWindowLong(UserHMGetHandle(Wnd), DT_GWL_PROCESSID, Value, FALSE); + Value = HandleToULong(PsGetCurrentThreadId()); + // Save Thread ID + co_UserSetWindowLong(UserHMGetHandle(Wnd), DT_GWL_THREADID, Value, FALSE); + case WM_CLOSE: + return 0; + + case WM_DISPLAYCHANGE: + co_WinPosSetWindowPos(Wnd, 0, 0, 0, LOWORD(lParam), HIWORD(lParam), SWP_NOZORDER | SWP_NOACTIVATE); + break; } return 0; } @@ -605,17 +621,6 @@ NTSTATUS FASTCALL co_IntShowDesktop(PDESKTOP Desktop, ULONG Width, ULONG Height) { -//#if 0 - CSR_API_MESSAGE Request; - - Request.Type = MAKE_CSR_API(SHOW_DESKTOP, CSR_GUI); - Request.Data.ShowDesktopRequest.DesktopWindow = Desktop->DesktopWindow; - Request.Data.ShowDesktopRequest.Width = Width; - Request.Data.ShowDesktopRequest.Height = Height; - - return co_CsrNotify(&Request); -//#endif -#if 0 // DESKTOPWNDPROC PWND Window;
Window = IntGetWindowObject(Desktop->DesktopWindow); @@ -629,7 +634,6 @@
co_UserRedrawWindow( Window, NULL, 0, RDW_UPDATENOW | RDW_ALLCHILDREN); return STATUS_SUCCESS; -#endif }
NTSTATUS FASTCALL @@ -680,7 +684,7 @@ * notifications. The lParam contents depend on the Message. See * MSDN for more details (RegisterShellHookWindow) */ -VOID co_IntShellHookNotify(WPARAM Message, LPARAM lParam) +VOID co_IntShellHookNotify(WPARAM Message, WPARAM wParam, LPARAM lParam) { PDESKTOP Desktop = IntGetActiveDesktop(); HWND* HwndList; @@ -699,6 +703,8 @@ TRACE("IntShellHookNotify: No desktop!\n"); return; } + + // FIXME: System Tray Support.
HwndList = UserBuildShellHookHwndList(Desktop); if (HwndList) @@ -711,12 +717,16 @@ co_IntPostOrSendMessage(*cursor, gpsi->uiShellMsg, Message, - lParam); + (Message == HSHELL_LANGUAGE ? lParam : (LPARAM)wParam) ); }
ExFreePool(HwndList); }
+ if (ISITHOOKED(WH_SHELL)) + { + co_HOOK_CallHooks(WH_SHELL, Message, wParam, lParam); + } }
/* @@ -996,7 +1006,6 @@ return TRUE; }
- /* SYSCALLS *******************************************************************/
/* @@ -1069,6 +1078,8 @@ ptiCurrent->TIF_flags |= TIF_DISABLEHOOKS; ptiCurrent->pClientInfo->dwTIFlags = ptiCurrent->TIF_flags; } + /*else + {ERR("NtUserCreateDesktop: No ptiCurrent\n");}*/ DesktopName.Buffer = NULL;
/* @@ -1169,9 +1180,9 @@ { InitializeListHead(&DesktopObject->pDeskInfo->aphkStart[i]); } -//#if 0 + /* - * Create a handle for CSRSS and notify CSRSS for Creating Desktop Background Window. + * Create a handle for CSRSS and notify CSRSS for Creating Desktop Background Windows and Threads. */ Request.Type = MAKE_CSR_API(CREATE_DESKTOP, CSR_GUI); Status = CsrInsertObject(Desktop, @@ -1194,51 +1205,9 @@ SetLastNtError(Status); RETURN( NULL); } -//#endif + if (ptiCurrent && !ptiCurrent->rpdesk) IntSetThreadDesktop(Desktop,FALSE);
- /* - Based on wine/server/window.c in get_desktop_window. - */ - -#if 0 // DESKTOPWNDPROC from Revision 6908 Dedicated to GvG! - // Turn on when server side proc is ready. - // - // Create desktop window. - // - /* - Currently this works but it hangs in - co_IntShowDesktop->co_UserRedrawWindow->co_IntPaintWindows->co_IntSendMessage - Commenting out co_UserRedrawWindow will allow it to run with gui issues. - */ - ClassName.Buffer = ((PWSTR)((ULONG_PTR)(WORD)(gpsi->atomSysClass[ICLS_DESKTOP]))); - ClassName.Length = 0; - RtlZeroMemory(&WindowName, sizeof(WindowName)); - - RtlZeroMemory(&Cs, sizeof(Cs)); - Cs.x = UserGetSystemMetrics(SM_XVIRTUALSCREEN); - Cs.y = UserGetSystemMetrics(SM_YVIRTUALSCREEN); - Cs.cx = UserGetSystemMetrics(SM_CXVIRTUALSCREEN); - Cs.cy = UserGetSystemMetrics(SM_CYVIRTUALSCREEN); - Cs.style = WS_POPUP|WS_CLIPCHILDREN; - Cs.hInstance = hModClient; // Experimental mode... hModuleWin; // Server side winproc! - Cs.lpszName = (LPCWSTR) &WindowName; - Cs.lpszClass = (LPCWSTR) &ClassName; - - pWnd = co_UserCreateWindowEx(&Cs, &ClassName, &WindowName, NULL); - if (!pWnd) - { - ERR("Failed to create Desktop window handle\n"); - } - else - { // Should be set in window.c, Justin Case, - if (!DesktopObject->DesktopWindow) - { - DesktopObject->pDeskInfo->spwnd = pWnd; - DesktopObject->DesktopWindow = UserHMGetHandle(pWnd); - } - } -#endif ClassName.Buffer = ((PWSTR)((ULONG_PTR)(WORD)(gpsi->atomSysClass[ICLS_HWNDMESSAGE]))); ClassName.Length = 0; RtlZeroMemory(&WindowName, sizeof(WindowName));
Modified: trunk/reactos/win32ss/user/ntuser/desktop.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/desktop... ============================================================================== --- trunk/reactos/win32ss/user/ntuser/desktop.h [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/desktop.h [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -39,6 +39,10 @@ #define DF_DESKWNDDESTROYED 0x00010000 #define DF_DYING 0x00020000
+// Index offset for Desktop data. Should these be global? +#define DT_GWL_PROCESSID 0 +#define DT_GWL_THREADID 4 + #define DESKTOP_READ STANDARD_RIGHTS_READ | \ DESKTOP_ENUMERATE | \ DESKTOP_READOBJECTS @@ -146,7 +150,7 @@ VOID APIENTRY UserRedrawDesktop(VOID); BOOL IntRegisterShellHookWindow(HWND hWnd); BOOL IntDeRegisterShellHookWindow(HWND hWnd); -VOID co_IntShellHookNotify(WPARAM Message, LPARAM lParam); +VOID co_IntShellHookNotify(WPARAM Message, WPARAM wParam, LPARAM lParam); HDC FASTCALL UserGetDesktopDC(ULONG,BOOL,BOOL);
#define IntIsActiveDesktop(Desktop) \ @@ -277,6 +281,6 @@
PWND FASTCALL IntGetThreadDesktopWindow(PTHREADINFO); PWND FASTCALL co_GetDesktopWindow(PWND); - +BOOL FASTCALL IntPaintDesktop(HDC); LRESULT FASTCALL DesktopWindowProc(PWND, UINT, WPARAM, LPARAM); /* EOF */
Modified: trunk/reactos/win32ss/user/ntuser/focus.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/focus.c... ============================================================================== --- trunk/reactos/win32ss/user/ntuser/focus.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/focus.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -45,18 +45,35 @@ return ThreadQueue->spwndFocus ? UserHMGetHandle(ThreadQueue->spwndFocus) : 0; }
-VOID FASTCALL +BOOL FASTCALL co_IntSendDeactivateMessages(HWND hWndPrev, HWND hWnd) { - PWND WndPrev ; - - if (hWndPrev && (WndPrev = UserGetWindowObject(hWndPrev))) - { - co_IntSendMessageNoWait(hWndPrev, WM_NCACTIVATE, FALSE, 0); - co_IntSendMessageNoWait(hWndPrev, WM_ACTIVATE, - MAKEWPARAM(WA_INACTIVE, WndPrev->style & WS_MINIMIZE), - (LPARAM)hWnd); - } + USER_REFERENCE_ENTRY RefPrev; + PWND WndPrev; + BOOL Ret = TRUE; + + if (hWndPrev && (WndPrev = ValidateHwndNoErr(hWndPrev))) + { + UserRefObjectCo(WndPrev, &RefPrev); + + if (co_IntSendMessageNoWait(hWndPrev, WM_NCACTIVATE, FALSE, 0)) //(LPARAM)hWnd)) + { + co_IntSendMessageNoWait(hWndPrev, WM_ACTIVATE, + MAKEWPARAM(WA_INACTIVE, WndPrev->style & WS_MINIMIZE), + (LPARAM)hWnd); + + if (WndPrev) + WndPrev->state &= ~WNDS_ACTIVEFRAME; + } + else + { + ERR("Application is keeping itself Active to prevent the change!\n"); + Ret = FALSE; + } + + UserDerefObjectCo(WndPrev); + } + return Ret; }
BOOL FASTCALL @@ -65,99 +82,103 @@ PWND spwndOwner; if (Window) { // Set last active for window and it's owner. - Window->spwndLastActive = Window; - spwndOwner = Window->spwndOwner; - while (spwndOwner) + spwndOwner = Window; + while (spwndOwner->spwndOwner) { - spwndOwner->spwndLastActive = Window; spwndOwner = spwndOwner->spwndOwner; } + spwndOwner->spwndLastActive = Window; return TRUE; } ERR("MakeWindowActive Failed!\n"); return FALSE; }
-VOID FASTCALL -co_IntSendActivateMessages(HWND hWndPrev, HWND hWnd, BOOL MouseActivate) +BOOL FASTCALL +co_IntSendActivateMessages(PWND WindowPrev, PWND Window, BOOL MouseActivate, BOOL Async) { USER_REFERENCE_ENTRY Ref, RefPrev; - PWND Window, WindowPrev = NULL; HANDLE OldTID, NewTID; - PTHREADINFO ptiOld, ptiNew; - - if ((Window = UserGetWindowObject(hWnd))) - { + PTHREADINFO pti, ptiOld, ptiNew; + BOOL InAAPM = FALSE; + + if (Window) + { + pti = PsGetCurrentThreadWin32Thread(); + UserRefObjectCo(Window, &Ref); - - WindowPrev = UserGetWindowObject(hWndPrev);
if (WindowPrev) UserRefObjectCo(WindowPrev, &RefPrev);
/* Send palette messages */ if (gpsi->PUSIFlags & PUSIF_PALETTEDISPLAY && - co_IntPostOrSendMessage(hWnd, WM_QUERYNEWPALETTE, 0, 0)) + co_IntPostOrSendMessage(UserHMGetHandle(Window), WM_QUERYNEWPALETTE, 0, 0)) { UserSendNotifyMessage( HWND_BROADCAST, WM_PALETTEISCHANGING, - (WPARAM)hWnd, + (WPARAM)UserHMGetHandle(Window), 0); } - - if (Window->spwndPrev != NULL) - co_WinPosSetWindowPos(Window, HWND_TOP, 0, 0, 0, 0, - SWP_NOSIZE | SWP_NOMOVE); - - if (!Window->spwndOwner && !IntGetParent(Window)) - { - co_IntShellHookNotify(HSHELL_WINDOWACTIVATED, (LPARAM) hWnd); - } - - if (Window) - { - Window->state |= WNDS_ACTIVEFRAME; - - if (Window->style & WS_MINIMIZE) - { - TRACE("Widow was minimized\n"); - } - } - - if (WindowPrev) - WindowPrev->state &= ~WNDS_ACTIVEFRAME; - + //// Fixes bug 7089. + if (!(Window->style & WS_CHILD)) + { + PWND pwndTemp = co_GetDesktopWindow(Window)->spwndChild; + + while (pwndTemp && !(pwndTemp->style & WS_VISIBLE)) pwndTemp = pwndTemp->spwndNext; + + if (Window != pwndTemp || (WindowPrev && !IntIsWindowVisible(WindowPrev))) + { + if (!Async || pti->MessageQueue == gpqForeground) + { + UINT flags = SWP_NOSIZE | SWP_NOMOVE; + if (Window == pwndTemp) flags |= SWP_NOACTIVATE; + co_WinPosSetWindowPos(Window, HWND_TOP, 0, 0, 0, 0, flags); + } + } + } + //// OldTID = WindowPrev ? IntGetWndThreadId(WindowPrev) : NULL; - NewTID = Window ? IntGetWndThreadId(Window) : NULL; + NewTID = IntGetWndThreadId(Window); ptiOld = WindowPrev ? WindowPrev->head.pti : NULL; - ptiNew = Window ? Window->head.pti : NULL; - - TRACE("SendActiveMessage Old -> %x, New -> %x\n", OldTID, NewTID); - - if (OldTID != NewTID) + ptiNew = Window->head.pti; + + //ERR("SendActivateMessage Old -> %x, New -> %x\n", OldTID, NewTID); + + if (!(pti->TIF_flags & TIF_INACTIVATEAPPMSG) && + (!WindowPrev || OldTID != NewTID) ) { PWND cWindow; HWND *List, *phWnd;
- List = IntWinListChildren(UserGetWindowObject(IntGetDesktopWindow())); + List = IntWinListChildren(UserGetDesktopWindow()); if ( List ) { - if ( OldTID ) + if ( OldTID ) { + ptiOld->TIF_flags |= TIF_INACTIVATEAPPMSG; + ptiOld->pClientInfo->dwTIFlags = ptiOld->TIF_flags; + for (phWnd = List; *phWnd; ++phWnd) { - cWindow = UserGetWindowObject(*phWnd); + cWindow = ValidateHwndNoErr(*phWnd); if (cWindow && cWindow->head.pti == ptiOld) { // FALSE if the window is being deactivated, // ThreadId that owns the window being activated. co_IntSendMessageNoWait(*phWnd, WM_ACTIVATEAPP, FALSE, (LPARAM)NewTID); } } + ptiOld->TIF_flags &= ~TIF_INACTIVATEAPPMSG; + ptiOld->pClientInfo->dwTIFlags = ptiOld->TIF_flags; } if ( NewTID ) - { + { //// Prevents a resource crash due to reentrance! + InAAPM = TRUE; + pti->TIF_flags |= TIF_INACTIVATEAPPMSG; + pti->pClientInfo->dwTIFlags = pti->TIF_flags; + //// for (phWnd = List; *phWnd; ++phWnd) { - cWindow = UserGetWindowObject(*phWnd); + cWindow = ValidateHwndNoErr(*phWnd); if (cWindow && cWindow->head.pti == ptiNew) { // TRUE if the window is being activated, // ThreadId that owns the window being deactivated. @@ -171,38 +192,81 @@ if (WindowPrev) UserDerefObjectCo(WindowPrev); // Now allow the previous window to die.
+ if (Window->state & WNDS_ACTIVEFRAME) + { // If already active frame do not allow NCPaint. + //ERR("SendActivateMessage Is Active Frame!\n"); + Window->state |= WNDS_NONCPAINT; + } + + if (Window->style & WS_MINIMIZE) + { + TRACE("Widow was minimized\n"); + } + + co_IntMakeWindowActive(Window); + UserDerefObjectCo(Window);
/* FIXME: IntIsWindow */ - co_IntSendMessageNoWait(hWnd, WM_NCACTIVATE, (WPARAM)(hWnd == UserGetForegroundWindow()), 0); - /* FIXME: WA_CLICKACTIVE */ - co_IntSendMessageNoWait(hWnd, WM_ACTIVATE, - MAKEWPARAM(MouseActivate ? WA_CLICKACTIVE : WA_ACTIVE, - Window->style & WS_MINIMIZE), - (LPARAM)hWndPrev); - } + co_IntSendMessageNoWait( UserHMGetHandle(Window), + WM_NCACTIVATE, + (WPARAM)(Window == gpqForeground->spwndActive), + 0); //(LPARAM)hWndPrev); + + co_IntSendMessageNoWait( UserHMGetHandle(Window), + WM_ACTIVATE, + MAKEWPARAM(MouseActivate ? WA_CLICKACTIVE : WA_ACTIVE, Window->style & WS_MINIMIZE), + (LPARAM)(WindowPrev ? UserHMGetHandle(WindowPrev) : 0)); + + if (!Window->spwndOwner && !IntGetParent(Window)) + { + // FIXME lParam; The value is TRUE if the window is in full-screen mode, or FALSE otherwise. + co_IntShellHookNotify(HSHELL_WINDOWACTIVATED, (WPARAM) UserHMGetHandle(Window), FALSE); + } + + Window->state &= ~WNDS_NONCPAINT; + + } + return InAAPM; }
VOID FASTCALL -co_IntSendKillFocusMessages(HWND hWndPrev, HWND hWnd) -{ - if (hWndPrev) - { - IntNotifyWinEvent(EVENT_OBJECT_FOCUS, NULL, OBJID_CLIENT, CHILDID_SELF, 0); - co_IntPostOrSendMessage(hWndPrev, WM_KILLFOCUS, (WPARAM)hWnd, 0); - } -} - -VOID FASTCALL -co_IntSendSetFocusMessages(HWND hWndPrev, HWND hWnd) -{ - if (hWnd) - { - PWND pWnd = UserGetWindowObject(hWnd); - if (pWnd) +IntSendFocusMessages( PTHREADINFO pti, PWND pWnd) +{ + PWND pWndPrev; + PUSER_MESSAGE_QUEUE ThreadQueue = pti->MessageQueue; // Queue can change... + + ThreadQueue->QF_flags &= ~QF_FOCUSNULLSINCEACTIVE; + if (!pWnd && ThreadQueue->spwndActive) + { + ThreadQueue->QF_flags |= QF_FOCUSNULLSINCEACTIVE; + } + + pWndPrev = ThreadQueue->spwndFocus; + + /* check if the specified window can be set in the input data of a given queue */ + if (!pWnd || ThreadQueue == pWnd->head.pti->MessageQueue) + /* set the current thread focus window */ + ThreadQueue->spwndFocus = pWnd; + + if (pWnd) + { + if (pWndPrev) + { + co_IntPostOrSendMessage(UserHMGetHandle(pWndPrev), WM_KILLFOCUS, (WPARAM)UserHMGetHandle(pWnd), 0); + } + if (ThreadQueue->spwndFocus == pWnd) { IntNotifyWinEvent(EVENT_OBJECT_FOCUS, pWnd, OBJID_CLIENT, CHILDID_SELF, 0); - co_IntPostOrSendMessage(hWnd, WM_SETFOCUS, (WPARAM)hWndPrev, 0); + co_IntPostOrSendMessage(UserHMGetHandle(pWnd), WM_SETFOCUS, (WPARAM)(pWndPrev ? UserHMGetHandle(pWndPrev) : NULL), 0); + } + } + else + { + if (pWndPrev) + { + IntNotifyWinEvent(EVENT_OBJECT_FOCUS, NULL, OBJID_CLIENT, CHILDID_SELF, 0); + co_IntPostOrSendMessage(UserHMGetHandle(pWndPrev), WM_KILLFOCUS, 0, 0); } } } @@ -304,25 +368,29 @@
ASSERT_REFS_CO(Wnd);
- TRACE("SetForegroundAndFocusWindow(%x, %x, %s)\n", hWnd, MouseActivate ? "TRUE" : "FALSE"); + TRACE("SetForegroundAndFocusWindow(%x, %s)\n", hWnd, (MouseActivate ? "TRUE" : "FALSE"));
PrevForegroundQueue = IntGetFocusMessageQueue(); // Use this active desktop. pti = PsGetCurrentThreadWin32Thread();
if (PrevForegroundQueue) { // Same Window Q as foreground just do active. + //ERR("Same Window Q as foreground just do active.\n"); if (Wnd && Wnd->head.pti->MessageQueue == PrevForegroundQueue) { if (pti->MessageQueue == PrevForegroundQueue) { // Same WQ and TQ go active. - Ret = co_IntSetActiveWindow(Wnd, NULL, MouseActivate, TRUE); + //ERR("Same WQ and TQ go active.\n"); + Ret = co_IntSetActiveWindow(Wnd, NULL, MouseActivate, TRUE, FALSE); } else if (Wnd->head.pti->MessageQueue->spwndActive == Wnd) { // Same WQ and it is active. + //ERR("Same WQ and it is active.\n"); Ret = TRUE; } else { // Same WQ as FG but not the same TQ send active. + //ERR("Same WQ as FG but not the same TQ send active.\n"); co_IntSendMessageNoWait(hWnd, WM_ASYNC_SETACTIVEWINDOW, (WPARAM)Wnd, (LPARAM)MouseActivate ); Ret = TRUE; } @@ -339,6 +407,7 @@ { IntSetFocusMessageQueue(Wnd->head.pti->MessageQueue); gptiForeground = Wnd->head.pti; + TRACE("Set Foreground pti 0x%p Q 0x%p\n",Wnd->head.pti, Wnd->head.pti->MessageQueue); /* Henri Verbeet, What happens is that we get the WM_WINE_SETACTIVEWINDOW message sent by the @@ -361,7 +430,7 @@ if (pti->MessageQueue == PrevForegroundQueue) { //ERR("SFGW: TI same as Prev TI\n"); - co_IntSetActiveWindow(NULL, NULL, FALSE, TRUE); + co_IntSetActiveWindow(NULL, NULL, FALSE, TRUE, FALSE); } else co_IntSendMessageNoWait(hWndPrev, WM_ASYNC_SETACTIVEWINDOW, 0, 0 ); @@ -370,7 +439,7 @@
if (pti->MessageQueue == Wnd->head.pti->MessageQueue) { - Ret = co_IntSetActiveWindow(Wnd, NULL, MouseActivate, TRUE); + Ret = co_IntSetActiveWindow(Wnd, NULL, MouseActivate, TRUE, FALSE); } else if (Wnd->head.pti->MessageQueue->spwndActive == Wnd) { @@ -398,11 +467,11 @@ { BOOL Ret; PWND TopWnd; - PWND DesktopWindow = UserGetWindowObject(IntGetDesktopWindow()); + PWND DesktopWindow = UserGetDesktopWindow(); if (DesktopWindow) { Top = IntFindChildWindowToOwner(DesktopWindow, Wnd); - if ((TopWnd = UserGetWindowObject(Top))) + if ((TopWnd = ValidateHwndNoErr(Top))) { UserRefObjectCo(TopWnd, &Ref); Ret = co_IntMouseActivateWindow(TopWnd); @@ -415,31 +484,33 @@ }
TopWindow = UserGetAncestor(Wnd, GA_ROOT); + //if (TopWindow) {ERR("MAW 2 pWnd %p hWnd %p\n",TopWindow,TopWindow->head.h);} if (!TopWindow) return FALSE;
- /* TMN: Check return valud from this function? */ + /* TMN: Check return value from this function? */ UserRefObjectCo(TopWindow, &Ref); - co_IntSetForegroundAndFocusWindow(TopWindow, TRUE); - UserDerefObjectCo(TopWindow); - return TRUE; }
BOOL FASTCALL -co_IntSetActiveWindow(PWND Wnd OPTIONAL, HWND * Prev, BOOL bMouse, BOOL bFocus) +co_IntSetActiveWindow(PWND Wnd OPTIONAL, HWND * Prev, BOOL bMouse, BOOL bFocus, BOOL Async) { PTHREADINFO pti; PUSER_MESSAGE_QUEUE ThreadQueue; + PWND pWndChg, WndPrev; // State changes. HWND hWndPrev; HWND hWnd = 0; + BOOL InAAPM; CBTACTIVATESTRUCT cbt;
if (Wnd) { ASSERT_REFS_CO(Wnd); hWnd = UserHMGetHandle(Wnd); + if ((Wnd->style & (WS_POPUP|WS_CHILD)) == WS_CHILD) return FALSE; + if (Wnd == UserGetDesktopWindow()) return FALSE; }
pti = PsGetCurrentThreadWin32Thread(); @@ -449,6 +520,8 @@ hWndPrev = ThreadQueue->spwndActive ? UserHMGetHandle(ThreadQueue->spwndActive) : NULL; if (Prev) *Prev = hWndPrev; if (hWndPrev == hWnd) return TRUE; + + pWndChg = ThreadQueue->spwndActive; // Keep to notify of a preemptive switch.
if (Wnd) { @@ -470,11 +543,36 @@ cbt.hWndActive = hWndPrev; if (co_HOOK_CallHooks( WH_CBT, HCBT_ACTIVATE, (WPARAM)hWnd, (LPARAM)&cbt)) { - ERR("SetActiveWindow WH_CBT Call Hook return!\n"); + ERR("SetActiveWindow: WH_CBT Call Hook return!\n"); return FALSE; }
- co_IntSendDeactivateMessages(hWndPrev, hWnd); + if ( ThreadQueue->spwndActive && ThreadQueue->spwndActive->state & WNDS_DESTROYED ) + ThreadQueue->spwndActive = NULL; + else + ThreadQueue->spwndActivePrev = ThreadQueue->spwndActive; + + WndPrev = ThreadQueue->spwndActive; // Keep to save changing active. + + if (WndPrev) + { + if (ThreadQueue == gpqForeground) gpqForegroundPrev = ThreadQueue; + if (!co_IntSendDeactivateMessages(hWndPrev, hWnd)) return FALSE; + } + + // While in calling message proc or hook: + // Fail if a preemptive switch was made, current active not made previous, + // focus window is dead or no longer the same thread queue. + if ( ThreadQueue->spwndActivePrev != ThreadQueue->spwndActive || + pWndChg != ThreadQueue->spwndActive || + (Wnd && !VerifyWnd(Wnd)) || + ThreadQueue != pti->MessageQueue ) + { + ERR("SetActiveWindow: Summery ERROR, active state changed!\n"); + return FALSE; + } + + if (!WndPrev) ThreadQueue->QF_flags &= ~QF_FOCUSNULLSINCEACTIVE;
if (Wnd) Wnd->state |= WNDS_BEINGACTIVATED;
@@ -484,32 +582,36 @@ if ( !Wnd || ThreadQueue == Wnd->head.pti->MessageQueue) { /* set the current thread active window */ - if (!Wnd || co_IntMakeWindowActive(Wnd)) - { - ThreadQueue->spwndActivePrev = ThreadQueue->spwndActive; - ThreadQueue->spwndActive = Wnd; - } - } - - co_IntSendActivateMessages(hWndPrev, hWnd, bMouse); + ThreadQueue->spwndActive = Wnd; + } + + InAAPM = co_IntSendActivateMessages(WndPrev, Wnd, bMouse, Async);
/* now change focus if necessary */ - if (bFocus) + if (bFocus && !(ThreadQueue->QF_flags & QF_FOCUSNULLSINCEACTIVE)) { /* Do not change focus if the window is no longer active */ - if (ThreadQueue->spwndActive == Wnd) - { - if (!ThreadQueue->spwndFocus || - !Wnd || - UserGetAncestor(ThreadQueue->spwndFocus, GA_ROOT) != Wnd) - { - co_UserSetFocus(Wnd); - } - } - } + if ( !Wnd || IntGetNonChildAncestor(ThreadQueue->spwndFocus) != ThreadQueue->spwndActive) + { + PWND pWndTemp = Wnd; + if (ThreadQueue->spwndActive && ThreadQueue->spwndActive->style & WS_MINIMIZE) + pWndTemp = NULL; + TRACE("SAW is setting Focus! 0x%p Temp 0x%p\n",Wnd, pWndTemp); + IntSendFocusMessages(pti, pWndTemp); + } + } + + if (InAAPM) + { + pti->TIF_flags &= ~TIF_INACTIVATEAPPMSG; + pti->pClientInfo->dwTIFlags = pti->TIF_flags; + } + + // FIXME: Used in the menu loop!!! + //ThreadQueue->QF_flags |= QF_ACTIVATIONCHANGE;
if (Wnd) Wnd->state &= ~WNDS_BEINGACTIVATED; - return TRUE; + return (ThreadQueue->spwndActive == Wnd); }
HWND FASTCALL @@ -527,13 +629,15 @@ ThreadQueue = pti->MessageQueue; ASSERT(ThreadQueue != 0);
+ TRACE("Enter SetFocus hWnd 0x%p pti 0x%p\n",Window ? UserHMGetHandle(Window) : 0, pti ); + hWndPrev = ThreadQueue->spwndFocus ? UserHMGetHandle(ThreadQueue->spwndFocus) : 0;
if (Window != 0) { if (hWndPrev == UserHMGetHandle(Window)) { - return hWndPrev; /* Nothing to do */ + return hWndPrev ? (IntIsWindow(hWndPrev) ? hWndPrev : 0) : 0; /* Nothing to do */ }
if (Window->head.pti->MessageQueue != ThreadQueue) @@ -570,7 +674,7 @@ { if (!co_IntSetForegroundAndFocusWindow(pwndTop, FALSE)) { - ERR("SetFocus Set Foreground and Focus Failed!\n"); + ERR("SetFocus: Set Foreground and Focus Failed!\n"); return 0; } } @@ -578,9 +682,9 @@ /* Set Active when it is needed. */ if (pwndTop != ThreadQueue->spwndActive) { - if (!co_IntSetActiveWindow(pwndTop, NULL, FALSE, FALSE)) + if (!co_IntSetActiveWindow(pwndTop, NULL, FALSE, FALSE, FALSE)) { - ERR("SetFocus Set Active Failed!\n"); + ERR("SetFocus: Set Active Failed!\n"); return 0; } } @@ -590,7 +694,7 @@ /* Do not change focus if the window is no longer active */ if (pwndTop != ThreadQueue->spwndActive) { - ERR("SetFocus Top window did not go active!\n"); + ERR("SetFocus: Top window did not go active!\n"); return 0; } } @@ -598,29 +702,22 @@ // Check again! SetActiveWindow could have set the focus via WM_ACTIVATE. hWndPrev = ThreadQueue->spwndFocus ? UserHMGetHandle(ThreadQueue->spwndFocus) : 0;
- /* check if the specified window can be set in the input data of a given queue */ - if (ThreadQueue == Window->head.pti->MessageQueue) - /* set the current thread focus window */ - ThreadQueue->spwndFocus = Window; + IntSendFocusMessages( pti, Window);
TRACE("Focus: %d -> %d\n", hWndPrev, Window->head.h); - - co_IntSendKillFocusMessages(hWndPrev, Window->head.h); - co_IntSendSetFocusMessages(hWndPrev, Window->head.h); } else /* NULL hwnd passed in */ { - if (!hWndPrev) return 0; /* nothing to do */ +// if (!hWndPrev) return 0; /* nothing to do */ + if (co_HOOK_CallHooks( WH_CBT, HCBT_SETFOCUS, (WPARAM)0, (LPARAM)hWndPrev)) { - ERR("SetFocusWindow 2 WH_CBT Call Hook return!\n"); + ERR("SetFocus: 2 WH_CBT Call Hook return!\n"); return 0; }
/* set the current thread focus window null */ - ThreadQueue->spwndFocus = 0; - - co_IntSendKillFocusMessages(hWndPrev, 0); + IntSendFocusMessages( pti, NULL); } return hWndPrev ? (IntIsWindow(hWndPrev) ? hWndPrev : 0) : 0; } @@ -667,7 +764,7 @@ { PTHREADINFO pti; PUSER_MESSAGE_QUEUE ThreadQueue; - PWND Window, pWnd; + PWND pWnd, Window = NULL; HWND hWndPrev;
pti = PsGetCurrentThreadWin32Thread(); @@ -676,7 +773,7 @@ if (ThreadQueue->QF_flags & QF_CAPTURELOCKED) return NULL;
- if ((Window = UserGetWindowObject(hWnd))) + if (hWnd && (Window = UserGetWindowObject(hWnd))) { if (Window->head.pti->MessageQueue != ThreadQueue) { @@ -868,24 +965,24 @@ { if (!(Window = UserGetWindowObject(hWnd))) { - RETURN( 0); + ERR("NtUserSetActiveWindow: Invalid handle 0x%p!\n",hWnd); + RETURN( NULL); } }
if (!Window || Window->head.pti->MessageQueue == gptiCurrent->MessageQueue) { + hWndPrev = gptiCurrent->MessageQueue->spwndActive ? UserHMGetHandle(gptiCurrent->MessageQueue->spwndActive) : NULL; if (Window) UserRefObjectCo(Window, &Ref); - if (!co_IntSetActiveWindow(Window, &hWndPrev, FALSE, TRUE)) hWndPrev = NULL; + co_IntSetActiveWindow(Window, NULL, FALSE, TRUE, FALSE); if (Window) UserDerefObjectCo(Window); - } - else - hWndPrev = NULL; - - RETURN( hWndPrev ? (IntIsWindow(hWndPrev) ? hWndPrev : 0) : 0 ); + RETURN( hWndPrev ? (IntIsWindow(hWndPrev) ? hWndPrev : 0) : 0 ); + } + RETURN( NULL);
CLEANUP: - TRACE("Leave NtUserSetActiveWindow, ret=%i\n",_ret_); + TRACE("Leave NtUserSetActiveWindow, ret=%p\n",_ret_); UserLeave(); END_CLEANUP; } @@ -927,6 +1024,7 @@ { if (!(Window = UserGetWindowObject(hWnd))) { + ERR("NtUserSetFocus: Invalid handle 0x%p!\n",hWnd); RETURN(NULL); }
@@ -942,7 +1040,7 @@ }
CLEANUP: - TRACE("Leave NtUserSetFocus, ret=%i\n",_ret_); + TRACE("Leave NtUserSetFocus, ret=%p\n",_ret_); UserLeave(); END_CLEANUP; }
Modified: trunk/reactos/win32ss/user/ntuser/focus.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/focus.h... ============================================================================== --- trunk/reactos/win32ss/user/ntuser/focus.h [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/focus.h [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -18,6 +18,6 @@ HWND FASTCALL UserGetActiveWindow(VOID); BOOL FASTCALL co_IntMouseActivateWindow(PWND Window); BOOL FASTCALL co_IntSetForegroundWindow(PWND Window); -BOOL FASTCALL co_IntSetActiveWindow(PWND Window,HWND * Prev,BOOL bMouse,BOOL bFocus); +BOOL FASTCALL co_IntSetActiveWindow(PWND,HWND *,BOOL,BOOL,BOOL); BOOL FASTCALL IntLockSetForegroundWindow(UINT uLockCode); BOOL FASTCALL IntAllowSetForegroundWindow(DWORD dwProcessId);
Modified: trunk/reactos/win32ss/user/ntuser/kbdlayout.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/kbdlayo... ============================================================================== --- trunk/reactos/win32ss/user/ntuser/kbdlayout.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/kbdlayout.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -644,7 +644,7 @@
/* Send shell message */ if (!(Flags & KLF_NOTELLSHELL)) - co_IntShellHookNotify(HSHELL_LANGUAGE, (LPARAM)hkl); + co_IntShellHookNotify(HSHELL_LANGUAGE, 0, (LPARAM)hkl);
/* Return hkl on success */ hklRet = (HKL)hkl; @@ -713,7 +713,7 @@
/* Send shell message */ if (!(Flags & KLF_NOTELLSHELL)) - co_IntShellHookNotify(HSHELL_LANGUAGE, (LPARAM)hkl); + co_IntShellHookNotify(HSHELL_LANGUAGE, 0, (LPARAM)hkl); }
cleanup:
Modified: trunk/reactos/win32ss/user/ntuser/message.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/message... ============================================================================== --- trunk/reactos/win32ss/user/ntuser/message.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/message.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -632,7 +632,7 @@ { PWND Window = (PWND)wparam; if (wparam) UserRefObjectCo(Window, &Ref); - lRes = (LRESULT)co_IntSetActiveWindow(Window,NULL,(BOOL)lparam,TRUE); + lRes = (LRESULT)co_IntSetActiveWindow(Window,NULL,(BOOL)lparam,TRUE,TRUE); if (wparam) UserDerefObjectCo(Window); return lRes; } @@ -1807,11 +1807,9 @@ IntGetQueueStatus(DWORD Changes) { PTHREADINFO pti; - //PUSER_MESSAGE_QUEUE Queue; DWORD Result;
pti = PsGetCurrentThreadWin32Thread(); - //Queue = pti->MessageQueue; // wine: Changes &= (QS_ALLINPUT|QS_ALLPOSTMESSAGE|QS_SMRESULT);
@@ -2159,7 +2157,7 @@ } else { - ERR("No Window for Translate. hwnd 0x%p Msg %d\n",SafeMsg.hwnd,SafeMsg.message); + TRACE("No Window for Translate. hwnd 0x%p Msg %d\n",SafeMsg.hwnd,SafeMsg.message); Ret = FALSE; } UserLeave(); @@ -2190,6 +2188,12 @@ case FNID_SCROLLBAR: { lResult = ScrollBarWndProc(hWnd, Msg, wParam, lParam); + break; + } + case FNID_DESKTOP: + { + Window = UserGetWindowObject(hWnd); + if (Window) lResult = DesktopWindowProc(Window, Msg, wParam, lParam); break; } case FNID_DEFWINDOWPROC: @@ -2676,6 +2680,7 @@ case FNID_CALLWNDPROC: case FNID_CALLWNDPROCRET: case FNID_SCROLLBAR: + case FNID_DESKTOP: if (ResultInfo) { _SEH2_TRY
Modified: trunk/reactos/win32ss/user/ntuser/msgqueue.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/msgqueu... ============================================================================== --- trunk/reactos/win32ss/user/ntuser/msgqueue.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/msgqueue.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -997,6 +997,7 @@ PUSER_MESSAGE_QUEUE ThreadQueue; LARGE_INTEGER Timeout; PLIST_ENTRY Entry; + PWND pWnd; LRESULT Result = 0; //// Result could be trashed. ////
pti = PsGetCurrentThreadWin32Thread(); @@ -1015,14 +1016,27 @@
if ( HookMessage == MSQ_NORMAL ) { + pWnd = ValidateHwndNoErr(Wnd); + // These can not cross International Border lines! - if ( pti->ppi != ptirec->ppi ) + if ( pti->ppi != ptirec->ppi && pWnd ) { switch(Msg) { + // Handle the special case when working with password transfers across bordering processes. case EM_GETLINE: case EM_SETPASSWORDCHAR: case WM_GETTEXT: + // Look for edit controls setup for passwords. + if ( gpsi->atomSysClass[ICLS_EDIT] == pWnd->pcls->atomClassName && // Use atomNVClassName. + pWnd->style & ES_PASSWORD ) + { + if (uResult) *uResult = -1; + ERR("Running across the border without a passport!\n"); + EngSetLastError(ERROR_ACCESS_DENIED); + return STATUS_UNSUCCESSFUL; + } + break; case WM_NOTIFY: if (uResult) *uResult = -1; ERR("Running across the border without a passport!\n"); @@ -1551,13 +1565,12 @@
/* Activate the window if needed */
- if (pwndMsg != pti->MessageQueue->spwndActive) //msg->hwnd != UserGetForegroundWindow()) + if (pwndMsg != MessageQueue->spwndActive) { PWND pwndTop = pwndMsg; - while (pwndTop) + while (pwndTop && ((pwndTop->style & (WS_POPUP|WS_CHILD)) == WS_CHILD)) { - if ((pwndTop->style & (WS_POPUP|WS_CHILD)) != WS_CHILD) break; - pwndTop = IntGetParent( pwndTop ); + pwndTop = pwndTop->spwndParent; }
if (pwndTop && pwndTop != pwndDesktop) @@ -1673,10 +1686,23 @@ { BOOL AcceptMessage; MSG msg; + PTHREADINFO pti = PsGetCurrentThreadWin32Thread();
if(!(MessageQueue->MouseMoved)) return FALSE;
+ if (!MessageQueue->ptiSysLock) + { + MessageQueue->ptiSysLock = pti; + pti->pcti->CTI_flags |= CTI_THREADSYSLOCK; + } + + if (MessageQueue->ptiSysLock != pti) + { + ERR("MsqPeekMouseMove: Thread Q is locked to another pti!\n"); + return FALSE; + } + msg = MessageQueue->MouseMoveMsg;
AcceptMessage = co_IntProcessMouseMessage(&msg, &Remove, MsgFilterLow, MsgFilterHigh); @@ -1690,7 +1716,9 @@ MessageQueue->MouseMoved = FALSE; }
- return AcceptMessage; + MessageQueue->ptiSysLock = NULL; + pti->pcti->CTI_flags &= ~CTI_THREADSYSLOCK; + return AcceptMessage; }
/* check whether a message filter contains at least one potential hardware message */ @@ -1724,6 +1752,8 @@ PUSER_MESSAGE CurrentMessage; PLIST_ENTRY ListHead, CurrentEntry = NULL; MSG msg; + BOOL Ret = FALSE; + PTHREADINFO pti = PsGetCurrentThreadWin32Thread();
if (!filter_contains_hw_range( MsgFilterLow, MsgFilterHigh )) return FALSE;
@@ -1731,6 +1761,18 @@ CurrentEntry = ListHead->Flink;
if (IsListEmpty(CurrentEntry)) return FALSE; + + if (!MessageQueue->ptiSysLock) + { + MessageQueue->ptiSysLock = pti; + pti->pcti->CTI_flags |= CTI_THREADSYSLOCK; + } + + if (MessageQueue->ptiSysLock != pti) + { + ERR("MsqPeekHardwareMessage: Thread Q is locked to another pti!\n"); + return FALSE; + }
CurrentMessage = CONTAINING_RECORD(CurrentEntry, USER_MESSAGE, ListEntry); @@ -1766,7 +1808,8 @@ if (AcceptMessage) { *pMsg = msg; - return TRUE; + Ret = TRUE; + break; } } CurrentMessage = CONTAINING_RECORD(CurrentEntry, USER_MESSAGE, @@ -1774,7 +1817,9 @@ } while(CurrentEntry != ListHead);
- return FALSE; + MessageQueue->ptiSysLock = NULL; + pti->pcti->CTI_flags &= ~CTI_THREADSYSLOCK; + return Ret; }
BOOLEAN APIENTRY @@ -1789,11 +1834,25 @@ PLIST_ENTRY CurrentEntry; PUSER_MESSAGE CurrentMessage; PLIST_ENTRY ListHead; + BOOL Ret = FALSE; + PTHREADINFO pti = PsGetCurrentThreadWin32Thread();
CurrentEntry = MessageQueue->PostedMessagesListHead.Flink; ListHead = &MessageQueue->PostedMessagesListHead;
if (IsListEmpty(CurrentEntry)) return FALSE; + + if (!MessageQueue->ptiSysLock) + { + MessageQueue->ptiSysLock = pti; + pti->pcti->CTI_flags |= CTI_THREADSYSLOCK; + } + + if (MessageQueue->ptiSysLock != pti) + { + ERR("MsqPeekMessage: Thread Q is locked to another pti!\n"); + return FALSE; + }
CurrentMessage = CONTAINING_RECORD(CurrentEntry, USER_MESSAGE, ListEntry); @@ -1822,14 +1881,17 @@ ClearMsgBitsMask(MessageQueue, CurrentMessage->QS_Flags); MsqDestroyMessage(CurrentMessage); } - return(TRUE); + Ret = TRUE; + break; } CurrentMessage = CONTAINING_RECORD(CurrentEntry, USER_MESSAGE, ListEntry); } while (CurrentEntry != ListHead);
- return(FALSE); + MessageQueue->ptiSysLock = NULL; + pti->pcti->CTI_flags &= ~CTI_THREADSYSLOCK; + return Ret; }
NTSTATUS FASTCALL @@ -2190,15 +2252,15 @@ { case MSQ_STATE_CAPTURE: Prev = MessageQueue->spwndCapture ? UserHMGetHandle(MessageQueue->spwndCapture) : 0; - MessageQueue->spwndCapture = UserGetWindowObject(hWnd); + MessageQueue->spwndCapture = ValidateHwndNoErr(hWnd); return Prev; case MSQ_STATE_ACTIVE: Prev = MessageQueue->spwndActive ? UserHMGetHandle(MessageQueue->spwndActive) : 0; - MessageQueue->spwndActive = UserGetWindowObject(hWnd); + MessageQueue->spwndActive = ValidateHwndNoErr(hWnd); return Prev; case MSQ_STATE_FOCUS: Prev = MessageQueue->spwndFocus ? UserHMGetHandle(MessageQueue->spwndFocus) : 0; - MessageQueue->spwndFocus = UserGetWindowObject(hWnd); + MessageQueue->spwndFocus = ValidateHwndNoErr(hWnd); return Prev; case MSQ_STATE_MENUOWNER: Prev = MessageQueue->MenuOwner;
Modified: trunk/reactos/win32ss/user/ntuser/painting.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/paintin... ============================================================================== --- trunk/reactos/win32ss/user/ntuser/painting.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/painting.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -810,7 +810,7 @@ CaretInfo = ActiveMessageQueue->CaretInfo; hWndCaret = CaretInfo->hWnd;
- WndCaret = UserGetWindowObject(hWndCaret); + WndCaret = ValidateHwndNoErr(hWndCaret);
// FIXME: Check for WndCaret can be NULL if (WndCaret == Window || @@ -1720,7 +1720,7 @@ ((flags & SW_SCROLLCHILDREN) ? RDW_ALLCHILDREN : 0)); }
- if ((CaretWnd = UserGetWindowObject(hwndCaret))) + if (hwndCaret && (CaretWnd = UserGetWindowObject(hwndCaret))) { UserRefObjectCo(CaretWnd, &CaretRef);
@@ -1974,8 +1974,6 @@
return Ret; } - -BOOL FASTCALL IntPaintDesktop(HDC hDC);
INT FASTCALL
Modified: trunk/reactos/win32ss/user/ntuser/simplecall.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/simplec... ============================================================================== --- trunk/reactos/win32ss/user/ntuser/simplecall.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/simplecall.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -123,7 +123,7 @@ case NOPARAM_ROUTINE_ZAPACTIVEANDFOUS: { PTHREADINFO pti = PsGetCurrentThreadWin32Thread(); - ERR("Zapping the Active and Focus window out of the Queue!\n"); + TRACE("Zapping the Active and Focus window out of the Queue!\n"); pti->MessageQueue->spwndFocus = NULL; pti->MessageQueue->spwndActive = NULL; RETURN(0); @@ -572,7 +572,7 @@ SWP_FRAMECHANGED ); if (!Window->spwndOwner && !IntGetParent(Window)) { - co_IntShellHookNotify(HSHELL_REDRAW, (LPARAM) hWnd); + co_IntShellHookNotify(HSHELL_REDRAW, (WPARAM) hWnd, FALSE); // FIXME Flashing? } Ret = TRUE; break;
Modified: trunk/reactos/win32ss/user/ntuser/win32.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/win32.h... ============================================================================== --- trunk/reactos/win32ss/user/ntuser/win32.h [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/win32.h [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -32,7 +32,19 @@ #define W32PF_MANUALGUICHECK (0x02000000) #define W32PF_CREATEDWINORDC (0x04000000) #define W32PF_APIHOOKLOADED (0x08000000) - +/* +#define QSIDCOUNTS 6 + +typedef enum _QS_ROS_TYPES +{ + QSRosKey = 0, + QSRosMouseMove, + QSRosMouseButton, + QSRosPostMessage, + QSRosSendMessage, + QSRosHotKey, +}QS_ROS_TYPES,*PQS_ROS_TYPES; +*/ extern BOOL ClientPfnInit; extern HINSTANCE hModClient; extern HANDLE hModuleWin; // This Win32k Instance. @@ -77,10 +89,13 @@ PCLIENTINFO pClientInfo; FLONG TIF_flags; PUNICODE_STRING pstrAppName; + LIST_ENTRY psmsSent; // DispatchingMessagesHead struct _USER_SENT_MESSAGE *pusmCurrent; + LIST_ENTRY psmsReceiveList; // SentMessagesListHead LONG timeLast; ULONG_PTR idLast; - INT exitCode; + BOOLEAN QuitPosted; + INT exitCode; // QuitExitCode HDESK hdesk; UINT cPaintsReady; /* Count of paints pending. */ UINT cTimersReady; /* Count of timers pending. */ @@ -94,16 +109,27 @@ LPARAM lParamHkCurrent; WPARAM wParamHkCurrent; struct tagSBTRACK* pSBTrack; - HANDLE hEventQueueClient; - PKEVENT pEventQueueServer; + HANDLE hEventQueueClient; // NewMessagesHandle + PKEVENT pEventQueueServer; // NewMessages LIST_ENTRY PtiLink; INT iCursorLevel; POINT ptLast;
+ LIST_ENTRY mlPost; // PostedMessagesListHead + LIST_ENTRY aphkStart[NB_HOOKS]; CLIENTTHREADINFO cti; // Used only when no Desktop or pcti NULL.
/* ReactOS */ + + /* Queue state tracking */ + // Send list QS_SENDMESSAGE + // Post list QS_POSTMESSAGE|QS_HOTKEY|QS_PAINT|QS_TIMER|QS_KEY + // Hard list QS_MOUSE|QS_KEY only + // Accounting of queue bit sets, the rest are flags. QS_TIMER QS_PAINT counts are handled in thread information. + //DWORD nCntsQBits[QSIDCOUNTS]; // QS_KEY QS_MOUSEMOVE QS_MOUSEBUTTON QS_POSTMESSAGE QS_SENDMESSAGE QS_HOTKEY + + LIST_ENTRY LocalDispatchingMessagesHead; LIST_ENTRY WindowListHead; LIST_ENTRY W32CallbackListHead; SINGLE_LIST_ENTRY ReferencesList;
Modified: trunk/reactos/win32ss/user/ntuser/window.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/window.... ============================================================================== --- trunk/reactos/win32ss/user/ntuser/window.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/window.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -8,6 +8,8 @@
#include <win32k.h> DBG_DEFAULT_CHANNEL(UserWnd); + +INT gNestedWindowLimit = 50;
/* HELPER FUNCTIONS ***********************************************************/
@@ -147,7 +149,9 @@ PWND Window;
if (!(Window = UserGetWindowObject(hWnd))) + { return FALSE; + }
return TRUE; } @@ -217,6 +221,7 @@ /* Remove keyboard focus from that window if it had focus */ if (hWnd == IntGetThreadFocusWindow()) { + TRACE("IntEnableWindow SF NULL\n"); co_UserSetFocus(NULL); } IntSetStyle( pWnd, WS_DISABLED, 0 ); @@ -269,6 +274,39 @@ return List; }
+PWND FASTCALL +IntGetNonChildAncestor(PWND pWnd) +{ + if (pWnd) + { + while(pWnd && ((pWnd->style & (WS_CHILD | WS_POPUP)) != WS_CHILD)) + pWnd = pWnd->spwndParent; + } + return pWnd; +} + +BOOL FASTCALL +IntIsTopLevelWindow(PWND pWnd) +{ + if ( pWnd->spwndParent && + pWnd->spwndParent == co_GetDesktopWindow(pWnd) ) return TRUE; + return FALSE; +} + +BOOL FASTCALL +IntValidateOwnerDepth(PWND Wnd, PWND Owner) +{ + INT Depth = 1; + for (;;) + { + if ( !Owner ) return gNestedWindowLimit >= Depth; + if (Owner == Wnd) break; + Owner = Owner->spwndOwner; + Depth++; + } + return FALSE; +} + /*********************************************************************** * IntSendDestroyMsg */ @@ -297,7 +335,7 @@
if (!Window->spwndOwner && !IntGetParent(Window)) { - co_IntShellHookNotify(HSHELL_WINDOWDESTROYED, (LPARAM) hWnd); + co_IntShellHookNotify(HSHELL_WINDOWDESTROYED, (WPARAM) hWnd, 0); }
// UserDerefObjectCo(Window); @@ -696,6 +734,7 @@
if ((Wnd->style & (WS_CHILD | WS_POPUP)) == WS_CHILD) { + ERR("SetMenu: Invalid handle 0x%p!\n",UserHMGetHandle(Wnd)); EngSetLastError(ERROR_INVALID_WINDOW_HANDLE); return FALSE; } @@ -1037,6 +1076,36 @@ } } } + Wnd->ExStyle2 |= WS_EX2_LINKED; +} + +VOID FASTCALL +IntProcessOwnerSwap(PWND Wnd, PWND WndNewOwner, PWND WndOldOwner) +{ + if (WndOldOwner) + { + if (Wnd->head.pti != WndOldOwner->head.pti) + { + if (!WndNewOwner || + Wnd->head.pti == WndNewOwner->head.pti || + WndOldOwner->head.pti != WndNewOwner->head.pti ) + { + UserAttachThreadInput(Wnd->head.pti, WndOldOwner->head.pti, FALSE); + } + } + } + if (WndNewOwner) + { + if (Wnd->head.pti != WndNewOwner->head.pti) + { + if (!WndOldOwner || + WndOldOwner->head.pti != WndNewOwner->head.pti ) + { + UserAttachThreadInput(Wnd->head.pti, WndNewOwner->head.pti, TRUE); + } + } + } + // FIXME: System Tray checks. }
HWND FASTCALL @@ -1051,17 +1120,36 @@
WndOldOwner = Wnd->spwndOwner;
- ret = WndOldOwner ? WndOldOwner->head.h : 0; - - if((WndNewOwner = UserGetWindowObject(hWndNewOwner))) - { - Wnd->spwndOwner= WndNewOwner; + ret = WndOldOwner ? UserHMGetHandle(WndOldOwner) : 0; + WndNewOwner = UserGetWindowObject(hWndNewOwner); + + if (!WndNewOwner && hWndNewOwner) + { + EngSetLastError(ERROR_INVALID_PARAMETER); + ret = NULL; + goto Error; + } + + IntProcessOwnerSwap(Wnd, WndNewOwner, WndOldOwner); + + if (IntValidateOwnerDepth(Wnd, WndNewOwner)) + { + if (WndNewOwner) + { + Wnd->spwndOwner= WndNewOwner; + } + else + { + Wnd->spwndOwner = NULL; + } } else { - Wnd->spwndOwner = NULL; - } - + IntProcessOwnerSwap(Wnd, WndOldOwner, WndNewOwner); + EngSetLastError(ERROR_INVALID_PARAMETER); + ret = NULL; + } +Error: UserDereferenceObject(Wnd); return ret; } @@ -1129,6 +1217,7 @@ { /* Unlink the window from the siblings list */ IntUnlinkWindow(Wnd); + Wnd->ExStyle2 &= ~WS_EX2_LINKED;
/* Set the new parent */ Wnd->spwndParent = WndNewParent; @@ -1146,6 +1235,24 @@ ((0 == (Wnd->ExStyle & WS_EX_TOPMOST) && WndNewParent == UserGetDesktopWindow() ) ? HWND_TOP : HWND_TOPMOST ) );
+ } + + if ((Wnd->style & (WS_CHILD|WS_POPUP)) == WS_CHILD) + { + if ( Wnd->spwndParent != co_GetDesktopWindow(Wnd)) + { + if (Wnd->head.pti != WndOldParent->head.pti) + { + UserAttachThreadInput(Wnd->head.pti, WndOldParent->head.pti, FALSE); + } + } + if ( WndNewParent != co_GetDesktopWindow(Wnd)) + { + if (Wnd->head.pti != WndNewParent->head.pti) + { + UserAttachThreadInput(Wnd->head.pti, WndNewParent->head.pti, TRUE); + } + } }
if (WndOldParent == UserGetMessageWindow() || WndNewParent == UserGetMessageWindow()) @@ -1617,6 +1724,7 @@ if (NULL == pti->rpdesk->DesktopWindow) { /* HACK: Helper for win32csr/desktopbg.c */ /* If there is no desktop window yet, we must be creating it */ + TRACE("CreateWindow setting desktop.\n"); pti->rpdesk->DesktopWindow = hWnd; pti->rpdesk->pDeskInfo->spwnd = pWnd; } @@ -1809,6 +1917,31 @@ else // Not a child pWnd->IDMenu = (UINT) Cs->hMenu;
+ + if ( ParentWindow && + ParentWindow != ParentWindow->head.rpdesk->spwndMessage && + ParentWindow != ParentWindow->head.rpdesk->pDeskInfo->spwnd ) + { + PWND Owner = IntGetNonChildAncestor(ParentWindow); + + if (!IntValidateOwnerDepth(pWnd, Owner)) + { + EngSetLastError(ERROR_INVALID_PARAMETER); + goto Error; + } + if ( pWnd->spwndOwner && + pWnd->spwndOwner->ExStyle & WS_EX_TOPMOST ) + { + pWnd->ExStyle |= WS_EX_TOPMOST; + } + if ( pWnd->spwndOwner && + Class->atomClassName != gpsi->atomSysClass[ICLS_IME] && + pti != pWnd->spwndOwner->head.pti) + { + UserAttachThreadInput(pti, pWnd->spwndOwner->head.pti, TRUE); + } + } + /* Insert the window into the thread's window list. */ InsertTailList (&pti->WindowListHead, &pWnd->ThreadListEntry);
@@ -1826,10 +1959,10 @@
AllocError: ERR("IntCreateWindow Allocation Error.\n"); + SetLastNtError(STATUS_INSUFFICIENT_RESOURCES); +Error: if(pWnd) UserDereferenceObject(pWnd); - - SetLastNtError(STATUS_INSUFFICIENT_RESOURCES); return NULL; }
@@ -2082,6 +2215,17 @@ IntLinkHwnd(Window, hwndInsertAfter); }
+ if ((Window->style & (WS_CHILD | WS_POPUP)) == WS_CHILD) + { + if ( !IntIsTopLevelWindow(Window) ) + { + if (pti != Window->spwndParent->head.pti) + { + UserAttachThreadInput(pti, Window->spwndParent->head.pti, TRUE); + } + } + } + /* Send the NCCREATE message */ Result = co_IntSendMessage(UserHMGetHandle(Window), WM_NCCREATE, 0, (LPARAM) Cs); if (!Result) @@ -2143,7 +2287,7 @@ /* Notify the shell that a new window was created */ if ((!hWndParent) && (!hWndOwner)) { - co_IntShellHookNotify(HSHELL_WINDOWCREATED, (LPARAM)hWnd); + co_IntShellHookNotify(HSHELL_WINDOWCREATED, (WPARAM)hWnd, 0); }
/* Initialize and show the window's scrollbars */ @@ -2379,6 +2523,7 @@ BOOLEAN FASTCALL co_UserDestroyWindow(PWND Window) { HWND hWnd; + PWND pwndTemp; PTHREADINFO ti; MSG msg;
@@ -2404,6 +2549,17 @@ { ERR("Destroy Window WH_CBT Call Hook return!\n"); return FALSE; + } + } + + if (Window->pcls->atomClassName != gpsi->atomSysClass[ICLS_IME]) + { + if ((Window->style & (WS_POPUP|WS_CHILD)) != WS_CHILD) + { + if (Window->spwndOwner) + { + UserAttachThreadInput(Window->head.pti, Window->spwndOwner->head.pti, FALSE); + } } }
@@ -2419,8 +2575,29 @@ if (!co_WinPosShowWindow(Window, SW_HIDE)) { // Rule #1. if (ti->MessageQueue->spwndActive == Window && ti->MessageQueue == IntGetFocusMessageQueue()) - { //ERR("DestroyWindow AOW\n"); + { co_WinPosActivateOtherWindow(Window); + } + } + + // Adjust last active. + if ((pwndTemp = Window->spwndOwner)) + { + while (pwndTemp->spwndOwner) + pwndTemp = pwndTemp->spwndOwner; + + if (pwndTemp->spwndLastActive == Window) + pwndTemp->spwndLastActive = Window->spwndOwner; + } + + if (Window->spwndParent && IntIsWindow(Window->head.h)) + { + if ((Window->style & (WS_POPUP | WS_CHILD)) == WS_CHILD) + { + if (!IntIsTopLevelWindow(Window)) + { + UserAttachThreadInput(Window->head.pti, Window->spwndParent->head.pti, FALSE); + } } }
@@ -3298,12 +3475,6 @@ LONG OldValue; STYLESTRUCT Style;
- if (hWnd == IntGetDesktopWindow()) - { - EngSetLastError(STATUS_ACCESS_DENIED); - return( 0); - } - if (!(Window = UserGetWindowObject(hWnd))) { return( 0); @@ -3444,6 +3615,12 @@ TRACE("Enter NtUserSetWindowLong\n"); UserEnterExclusive();
+ if (hWnd == IntGetDesktopWindow()) + { + EngSetLastError(STATUS_ACCESS_DENIED); + RETURN( 0); + } + RETURN( co_UserSetWindowLong(hWnd, Index, NewValue, Ansi));
CLEANUP: @@ -3471,6 +3648,12 @@ TRACE("Enter NtUserSetWindowWord\n"); UserEnterExclusive();
+ if (hWnd == IntGetDesktopWindow()) + { + EngSetLastError(STATUS_ACCESS_DENIED); + RETURN( 0); + } + if (!(Window = UserGetWindowObject(hWnd))) { RETURN( 0); @@ -3481,7 +3664,7 @@ case GWL_ID: case GWL_HINSTANCE: case GWL_HWNDPARENT: - RETURN( (WORD)co_UserSetWindowLong(Window->head.h, Index, (UINT)NewValue, TRUE)); + RETURN( (WORD)co_UserSetWindowLong(UserHMGetHandle(Window), Index, (UINT)NewValue, TRUE)); default: if (Index < 0) { @@ -3836,7 +4019,7 @@ /* Send shell notifications */ if (!Wnd->spwndOwner && !IntGetParent(Wnd)) { - co_IntShellHookNotify(HSHELL_REDRAW, (LPARAM) hWnd); + co_IntShellHookNotify(HSHELL_REDRAW, (WPARAM) hWnd, FALSE); // FIXME Flashing? }
Ret = TRUE; @@ -3913,7 +4096,9 @@ END_CLEANUP; }
- +/* + API Call +*/ BOOL FASTCALL IntShowOwnedPopups(PWND OwnerWnd, BOOL fShow ) @@ -3924,7 +4109,8 @@
// ASSERT(OwnerWnd);
- win_array = IntWinListChildren(UserGetWindowObject(IntGetDesktopWindow())); + TRACE("Enter ShowOwnedPopups Show: %s\n", (fShow ? "TRUE" : "FALSE")); + win_array = IntWinListChildren(OwnerWnd);
if (!win_array) return TRUE; @@ -3933,7 +4119,7 @@ count++; while (--count >= 0) { - if (!(pWnd = UserGetWindowObject( win_array[count] ))) + if (!(pWnd = ValidateHwndNoErr( win_array[count] ))) continue; if (pWnd->spwndOwner != OwnerWnd) continue; @@ -3965,6 +4151,7 @@
} ExFreePool( win_array ); + TRACE("Leave ShowOwnedPopups\n"); return TRUE; }
Modified: trunk/reactos/win32ss/user/ntuser/window.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/window.... ============================================================================== --- trunk/reactos/win32ss/user/ntuser/window.h [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/window.h [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -49,8 +49,11 @@ VOID FASTCALL IntNotifyWinEvent(DWORD, PWND, LONG, LONG, DWORD); PWND FASTCALL co_UserCreateWindowEx(CREATESTRUCTW*, PUNICODE_STRING, PLARGE_STRING, PVOID); BOOL FASTCALL IntEnableWindow(HWND,BOOL); +BOOL FASTCALL IntIsWindowVisible(PWND); DWORD FASTCALL GetNCHitEx(PWND,POINT); ULONG FASTCALL IntSetStyle(PWND,ULONG,ULONG); PWND FASTCALL VerifyWnd(PWND); +PWND FASTCALL IntGetNonChildAncestor(PWND); +LONG FASTCALL co_UserSetWindowLong(HWND,DWORD,LONG,BOOL);
/* EOF */
Modified: trunk/reactos/win32ss/user/ntuser/winpos.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/winpos.... ============================================================================== --- trunk/reactos/win32ss/user/ntuser/winpos.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/ntuser/winpos.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -139,6 +139,121 @@ return MAKELONG(LOWORD(Delta.x), LOWORD(Delta.y)); }
+BOOL FASTCALL IsChildVisible(PWND pWnd) +{ + do + { + if ( (pWnd->style & (WS_POPUP|WS_CHILD)) != WS_CHILD || + !(pWnd = pWnd->spwndParent) ) + return TRUE; + } + while (pWnd->style & WS_VISIBLE); + return FALSE; +} + +PWND FASTCALL IntGetLastTopMostWindow(VOID) +{ + PWND pWnd; + PDESKTOP rpdesk = gptiCurrent->rpdesk; + + if ( rpdesk && + (pWnd = rpdesk->pDeskInfo->spwnd->spwndChild) && + pWnd->ExStyle & WS_EX_TOPMOST) + { + for (;;) + { + if (!pWnd->spwndNext) break; + if (!(pWnd->spwndNext->ExStyle & WS_EX_TOPMOST)) break; + pWnd = pWnd->spwndNext; + } + return pWnd; + } + return NULL; +} + +// +// This helps with bug 6751 forcing modal dialog active when another app is minimized or closed. +// +BOOL FASTCALL ActivateOtherWindowMin(PWND Wnd) +{ + BOOL ActivePrev, FindTopWnd; + PWND pWndTopMost, pWndChild, pWndSetActive, pWndTemp, pWndDesk; + USER_REFERENCE_ENTRY Ref; + PTHREADINFO pti = gptiCurrent; + + //ERR("AOWM 1\n"); + ActivePrev = (pti->MessageQueue->spwndActivePrev != NULL); + FindTopWnd = TRUE; + + if ((pWndTopMost = IntGetLastTopMostWindow())) + pWndChild = pWndTopMost->spwndNext; + else + pWndChild = Wnd->spwndParent->spwndChild; + + for (;;) + { + if ( ActivePrev ) + pWndSetActive = pti->MessageQueue->spwndActivePrev; + else + pWndSetActive = pWndChild; + + pWndTemp = NULL; + + while(pWndSetActive) + { + if ( VerifyWnd(pWndSetActive) && + !(pWndSetActive->ExStyle & WS_EX_NOACTIVATE) && + (pWndSetActive->style & (WS_VISIBLE|WS_DISABLED)) == WS_VISIBLE && + (!(pWndSetActive->style & WS_ICONIC) /* FIXME MinMax pos? */ ) ) + { + if (!(pWndSetActive->ExStyle & WS_EX_TOOLWINDOW) ) + { + UserRefObjectCo(pWndSetActive, &Ref); + co_IntSetForegroundWindow(pWndSetActive); + UserDerefObjectCo(pWndSetActive); + //ERR("AOWM 2 Exit Good\n"); + return TRUE; + } + if (!pWndTemp ) pWndTemp = pWndSetActive; + } + if ( ActivePrev ) + { + ActivePrev = FALSE; + pWndSetActive = pWndChild; + } + else + pWndSetActive = pWndSetActive->spwndNext; + } + + if ( !FindTopWnd ) break; + FindTopWnd = FALSE; + + if ( pWndChild ) + { + pWndChild = pWndChild->spwndParent->spwndChild; + continue; + } + + if (!(pWndDesk = IntGetThreadDesktopWindow(pti))) + { + pWndChild = NULL; + continue; + } + pWndChild = pWndDesk->spwndChild; + } + + if ((pWndSetActive = pWndTemp)) + { + UserRefObjectCo(pWndSetActive, &Ref); + co_IntSetForegroundWindow(pWndSetActive); + UserDerefObjectCo(pWndSetActive); + //ERR("AOWM 3 Exit Good\n"); + return TRUE; + } + //ERR("AOWM 4 Bad\n"); + return FALSE; +} + /******************************************************************* * can_activate_window * @@ -203,7 +318,7 @@ if (WndTo) UserRefObjectCo(WndTo, &Ref);
Fg = UserGetForegroundWindow(); - if ((!Fg || Wnd->head.h == Fg) && WndTo) // FIXME: Ok if WndTo is NULL?? + if ((!Fg || Wnd->head.h == Fg) && WndTo) // FIXME: Ok if WndTo is NULL?? No, rule #4. { /* FIXME: Wine can pass WndTo = NULL to co_IntSetForegroundWindow. Hmm... */ if (co_IntSetForegroundWindow(WndTo)) @@ -213,12 +328,14 @@ } }
- if (!co_IntSetActiveWindow(WndTo,&previous,FALSE,TRUE) || /* Ok for WndTo to be NULL here */ + if (!co_IntSetActiveWindow(WndTo,&previous,FALSE,TRUE,FALSE) || /* Ok for WndTo to be NULL here */ !previous) - co_IntSetActiveWindow(0,NULL,FALSE,TRUE); - + { + co_IntSetActiveWindow(0,NULL,FALSE,TRUE,FALSE); + } if (WndTo) UserDerefObjectCo(WndTo); } +
UINT FASTCALL @@ -250,7 +367,7 @@ { PWND Child;
- if (!(Child = UserGetWindowObject(List[i]))) + if (!(Child = ValidateHwndNoErr(List[i]))) continue;
if((Child->style & WS_MINIMIZE) != 0 ) @@ -295,6 +412,7 @@ pwndParent = Window->spwndParent; if (pwndParent == UserGetDesktopWindow()) { + //ERR("Parent is Desktop, Min off screen!\n"); /* ReactOS doesn't support iconic minimize to desktop */ Pos->x = Pos->y = -32000; Window->InternalPos.flags |= WPF_MININIT; @@ -413,8 +531,7 @@ Wnd->InternalPos.MaxPos.x, Rect.left, WorkArea.left, Wnd->InternalPos.MaxPos.y, - Rect.top, WorkArea.top); - */ + Rect.top, WorkArea.top);*/ } } else @@ -603,6 +720,7 @@ { POINT Size; WINDOWPLACEMENT wpl; + LONG old_style; UINT SwpFlags = 0;
ASSERT_REFS_CO(Wnd); @@ -617,8 +735,14 @@ } if (Wnd->style & WS_MINIMIZE) { - if (ShowFlag == SW_MINIMIZE) return SWP_NOSIZE | SWP_NOMOVE; - + switch (ShowFlag) + { + case SW_SHOWMINNOACTIVE: + case SW_SHOWMINIMIZED: + case SW_FORCEMINIMIZE: + case SW_MINIMIZE: + return SWP_NOSIZE | SWP_NOMOVE; + } if (!co_IntSendMessageNoWait(Wnd->head.h, WM_QUERYOPEN, 0, 0)) { return(SWP_NOSIZE | SWP_NOMOVE); @@ -627,24 +751,33 @@ } switch (ShowFlag) { + case SW_SHOWMINNOACTIVE: + case SW_SHOWMINIMIZED: + case SW_FORCEMINIMIZE: case SW_MINIMIZE: { + //ERR("MinMaximize Minimize\n"); if (Wnd->style & WS_MAXIMIZE) { Wnd->InternalPos.flags |= WPF_RESTORETOMAXIMIZED; - Wnd->style &= ~WS_MAXIMIZE; - SwpFlags |= SWP_STATECHANGED; } else { Wnd->InternalPos.flags &= ~WPF_RESTORETOMAXIMIZED; } + + old_style = IntSetStyle( Wnd, WS_MINIMIZE, WS_MAXIMIZE ); + co_UserRedrawWindow(Wnd, NULL, 0, RDW_VALIDATE | RDW_NOERASE | RDW_NOINTERNALPAINT); - Wnd->style |= WS_MINIMIZE; + if (!(Wnd->InternalPos.flags & WPF_SETMINPOSITION)) Wnd->InternalPos.flags &= ~WPF_MININIT; + WinPosFindIconPos(Wnd, &wpl.ptMinPosition); + + if (!(old_style & WS_MINIMIZE)) SwpFlags |= SWP_STATECHANGED; + /*ERR("Minimize: %d,%d %dx%d\n", wpl.ptMinPosition.x, wpl.ptMinPosition.y, UserGetSystemMetrics(SM_CXMINIMIZED), UserGetSystemMetrics(SM_CYMINIMIZED)); @@ -660,33 +793,42 @@
case SW_MAXIMIZE: { + //ERR("MinMaximize Maximize\n"); + if ((Wnd->style & WS_MAXIMIZE) && (Wnd->style & WS_VISIBLE)) + { + SwpFlags = SWP_NOSIZE | SWP_NOMOVE; + break; + } co_WinPosGetMinMaxInfo(Wnd, &Size, &wpl.ptMaxPosition, NULL, NULL);
/*ERR("Maximize: %d,%d %dx%d\n", wpl.ptMaxPosition.x, wpl.ptMaxPosition.y, Size.x, Size.y); */ - if (Wnd->style & WS_MINIMIZE) - { - SwpFlags |= SWP_STATECHANGED; - Wnd->style &= ~WS_MINIMIZE; - } - Wnd->style |= WS_MAXIMIZE; + old_style = IntSetStyle( Wnd, WS_MAXIMIZE, WS_MINIMIZE ); + + if (!(old_style & WS_MAXIMIZE)) SwpFlags |= SWP_STATECHANGED; RECTL_vSetRect(NewPos, wpl.ptMaxPosition.x, wpl.ptMaxPosition.y, // wpl.ptMaxPosition.x + Size.x, wpl.ptMaxPosition.y + Size.y); Size.x, Size.y); break; }
+ case SW_SHOWNOACTIVATE: + Wnd->InternalPos.flags &= ~WPF_RESTORETOMAXIMIZED; + /* fall through */ + case SW_SHOWNORMAL: case SW_RESTORE: + case SW_SHOWDEFAULT: /* FIXME: should have its own handler */ { - if (Wnd->style & WS_MINIMIZE) + //ERR("MinMaximize Restore\n"); + old_style = IntSetStyle( Wnd, 0, WS_MINIMIZE | WS_MAXIMIZE ); + if (old_style & WS_MINIMIZE) { - Wnd->style &= ~WS_MINIMIZE; if (Wnd->InternalPos.flags & WPF_RESTORETOMAXIMIZED) { co_WinPosGetMinMaxInfo(Wnd, &Size, &wpl.ptMaxPosition, NULL, NULL); + IntSetStyle( Wnd, WS_MAXIMIZE, 0 ); SwpFlags |= SWP_STATECHANGED; - Wnd->style |= WS_MAXIMIZE; /*ERR("Restore to Max: %d,%d %dx%d\n", wpl.ptMaxPosition.x, wpl.ptMaxPosition.y, Size.x, Size.y); */ @@ -708,11 +850,10 @@ } else { - if (!(Wnd->style & WS_MAXIMIZE)) + if (!(old_style & WS_MAXIMIZE)) { - return 0; + break; } - Wnd->style &= ~WS_MAXIMIZE; SwpFlags |= SWP_STATECHANGED; Wnd->InternalPos.flags &= ~WPF_RESTORETOMAXIMIZED; *NewPos = wpl.rcNormalPosition; @@ -1020,17 +1161,17 @@
if ((ClientRect->right - ClientRect->left != Window->rcClient.right - Window->rcClient.left) || - (ClientRect->bottom - ClientRect->top != - Window->rcClient.bottom - Window->rcClient.top)) + (ClientRect->bottom - ClientRect->top != + Window->rcClient.bottom - Window->rcClient.top)) { WinPos->flags &= ~SWP_NOCLIENTSIZE; } } else { - if (! (WinPos->flags & SWP_NOMOVE) - && (ClientRect->left != Window->rcClient.left || - ClientRect->top != Window->rcClient.top)) + if (!(WinPos->flags & SWP_NOMOVE) && + (ClientRect->left != Window->rcClient.left || + ClientRect->top != Window->rcClient.top)) { WinPos->flags &= ~SWP_NOCLIENTMOVE; } @@ -1118,7 +1259,7 @@
if (hWndInsertAfter != HWND_TOPMOST) { - DesktopWindow = UserGetWindowObject(IntGetDesktopWindow()); + DesktopWindow = UserGetDesktopWindow(); List = IntWinListChildren(DesktopWindow);
if (List != NULL) @@ -1163,10 +1304,10 @@ { PWND Wnd;
- if (List[i] == Window->head.h) + if (List[i] == UserHMGetHandle(Window)) break;
- if (!(Wnd = ValidateHwndNoErr(List[i]))) + if (!(Wnd = ValidateHwndNoErr(List[i]))) continue;
if (Wnd->style & WS_POPUP && Wnd->spwndOwner == Window) @@ -1288,7 +1429,7 @@ if (WinPos->hwndInsertAfter == HWND_NOTOPMOST) { if (!(Wnd->ExStyle & WS_EX_TOPMOST)) - WinPos->flags |= SWP_NOZORDER; + WinPos->flags |= SWP_NOZORDER;
WinPos->hwndInsertAfter = HWND_TOP; } @@ -1307,7 +1448,7 @@ { PWND InsAfterWnd;
- InsAfterWnd = ValidateHwndNoErr(WinPos->hwndInsertAfter); + InsAfterWnd = ValidateHwndNoErr(WinPos->hwndInsertAfter); if(!InsAfterWnd) { return TRUE; @@ -1375,16 +1516,6 @@ ASSERT_REFS_CO(Window);
/* FIXME: Get current active window from active queue. */ - /* - * Only allow CSRSS to mess with the desktop window - */ - - if ( Window->head.h == IntGetDesktopWindow() && - Window->head.pti->ppi != PsGetCurrentProcessWin32Process()) - { - ERR("Desktop Window...\n"); - return FALSE; - }
bPointerInWindow = IntPtInWindow(Window, gpsi->ptCursor.x, gpsi->ptCursor.y);
@@ -1559,7 +1690,7 @@ RDW_VALIDATE | RDW_NOFRAME | RDW_NOERASE | RDW_NOINTERNALPAINT | RDW_ALLCHILDREN);
if (Window->spwndParent == UserGetDesktopWindow()) - co_IntShellHookNotify(HSHELL_WINDOWDESTROYED, (LPARAM)Window->head.h); + co_IntShellHookNotify(HSHELL_WINDOWDESTROYED, (WPARAM)Window->head.h, 0);
Window->style &= ~WS_VISIBLE; //IntSetStyle( Window, 0, WS_VISIBLE ); IntNotifyWinEvent(EVENT_OBJECT_HIDE, Window, OBJID_WINDOW, CHILDID_SELF, WEF_SETBYWNDPTI); @@ -1567,7 +1698,7 @@ else if (WinPos.flags & SWP_SHOWWINDOW) { if (Window->spwndParent == UserGetDesktopWindow()) - co_IntShellHookNotify(HSHELL_WINDOWCREATED, (LPARAM)Window->head.h); + co_IntShellHookNotify(HSHELL_WINDOWCREATED, (WPARAM)Window->head.h, 0);
Window->style |= WS_VISIBLE; //IntSetStyle( Window, WS_VISIBLE, 0 ); IntNotifyWinEvent(EVENT_OBJECT_SHOW, Window, OBJID_WINDOW, CHILDID_SELF, WEF_SETBYWNDPTI); @@ -1795,7 +1926,7 @@ } else { - TRACE("SetWindowPos Set FG Window!\n"); + //ERR("SetWindowPos Set FG Window!\n"); co_IntSetForegroundWindow(Window); } } @@ -1891,15 +2022,18 @@ co_WinPosShowWindow(PWND Wnd, INT Cmd) { BOOLEAN WasVisible; - UINT Swp = 0; + UINT Swp = 0, EventMsg = 0; RECTL NewPos; BOOLEAN ShowFlag; LONG style; PWND Parent; + PTHREADINFO pti; + BOOL ShowOwned = FALSE; // HRGN VisibleRgn;
ASSERT_REFS_CO(Wnd);
+ pti = PsGetCurrentThreadWin32Thread(); WasVisible = (Wnd->style & WS_VISIBLE) != 0; style = Wnd->style;
@@ -1912,11 +2046,12 @@ return(FALSE); } Swp |= SWP_HIDEWINDOW | SWP_NOSIZE | SWP_NOMOVE; - if (Wnd->head.h != UserGetActiveWindow()) + if (Wnd != pti->MessageQueue->spwndActive) Swp |= SWP_NOACTIVATE | SWP_NOZORDER; break; }
+ case SW_FORCEMINIMIZE: /* FIXME: Does not work if thread is hung. */ case SW_SHOWMINNOACTIVE: Swp |= SWP_NOACTIVATE | SWP_NOZORDER; /* Fall through. */ @@ -1928,6 +2063,8 @@ Swp |= SWP_NOACTIVATE; if (!(style & WS_MINIMIZE)) { + //IntShowOwnedPopups(Wnd, FALSE ); + // Fix wine Win test_SetFocus todo #1 & #2, if (Cmd == SW_SHOWMINIMIZED) { @@ -1937,16 +2074,20 @@ co_UserSetFocus(0); }
- Swp |= co_WinPosMinMaximize(Wnd, SW_MINIMIZE, &NewPos) | + Swp |= co_WinPosMinMaximize(Wnd, Cmd, &NewPos) | SWP_FRAMECHANGED; + + EventMsg = EVENT_SYSTEM_MINIMIZESTART; } else { - Swp |= SWP_NOSIZE | SWP_NOMOVE; - if (! WasVisible) + if (!WasVisible) { Swp |= SWP_FRAMECHANGED; } + else //// + return TRUE; + Swp |= SWP_NOSIZE | SWP_NOMOVE; } break; } @@ -1956,68 +2097,87 @@ Swp |= SWP_SHOWWINDOW; if (!(style & WS_MAXIMIZE)) { + ShowOwned = TRUE; + Swp |= co_WinPosMinMaximize(Wnd, SW_MAXIMIZE, &NewPos) | SWP_FRAMECHANGED; + + EventMsg = EVENT_SYSTEM_MINIMIZEEND; } else { - Swp |= SWP_NOSIZE | SWP_NOMOVE; - if (! WasVisible) + if (!WasVisible) { Swp |= SWP_FRAMECHANGED; } + else //// + return TRUE; + Swp |= SWP_NOSIZE | SWP_NOMOVE; } break; }
case SW_SHOWNA: - Swp |= SWP_NOACTIVATE | SWP_NOZORDER; - /* Fall through. */ + Swp |= SWP_NOACTIVATE | SWP_SHOWWINDOW | SWP_NOSIZE | SWP_NOMOVE; + if (style & WS_CHILD && !(Wnd->ExStyle & WS_EX_MDICHILD)) Swp |= SWP_NOZORDER; + break; case SW_SHOW: - if (WasVisible) return(TRUE); // Nothing to do! + if (WasVisible) return(TRUE); // Nothing to do! Swp |= SWP_SHOWWINDOW | SWP_NOSIZE | SWP_NOMOVE; /* Don't activate the topmost window. */ - if (style & WS_CHILD) Swp |= SWP_NOACTIVATE | SWP_NOZORDER; + if (style & WS_CHILD && !(Wnd->ExStyle & WS_EX_MDICHILD)) Swp |= SWP_NOACTIVATE | SWP_NOZORDER; break;
case SW_SHOWNOACTIVATE: - Wnd->InternalPos.flags &= ~WPF_RESTORETOMAXIMIZED; - //Swp |= SWP_NOZORDER; Swp |= SWP_NOACTIVATE | SWP_NOZORDER; /* Fall through. */ case SW_SHOWNORMAL: case SW_SHOWDEFAULT: case SW_RESTORE: - Swp |= SWP_SHOWWINDOW; + if (!WasVisible) Swp |= SWP_SHOWWINDOW; if (style & (WS_MINIMIZE | WS_MAXIMIZE)) { - Swp |= co_WinPosMinMaximize(Wnd, SW_RESTORE, &NewPos) | + Swp |= co_WinPosMinMaximize(Wnd, Cmd, &NewPos) | SWP_FRAMECHANGED; + + if (style & WS_MINIMIZE) EventMsg = EVENT_SYSTEM_MINIMIZEEND; } else { - Swp |= SWP_NOSIZE | SWP_NOMOVE; - if (! WasVisible) + if (!WasVisible) { Swp |= SWP_FRAMECHANGED; } - } + else //// + return TRUE; + Swp |= SWP_NOSIZE | SWP_NOMOVE; + } + if ( style & WS_CHILD && + !(Wnd->ExStyle & WS_EX_MDICHILD) && + !(Swp & SWP_STATECHANGED)) + Swp |= SWP_NOACTIVATE | SWP_NOZORDER; break; + + default: + return WasVisible; }
ShowFlag = (Cmd != SW_HIDE);
- if (ShowFlag != WasVisible) + if ((ShowFlag != WasVisible || Cmd == SW_SHOWNA) && Cmd != SW_SHOWMAXIMIZED && !(Swp & SWP_STATECHANGED)) { co_IntSendMessageNoWait(Wnd->head.h, WM_SHOWWINDOW, ShowFlag, 0); if (!(Wnd->state2 & WNDS2_WIN31COMPAT)) co_IntSendMessageNoWait(Wnd->head.h, WM_SETVISIBLE, ShowFlag, 0); + if (!VerifyWnd(Wnd)) return WasVisible; }
/* We can't activate a child window */ if ((Wnd->style & WS_CHILD) && - !(Wnd->ExStyle & WS_EX_MDICHILD)) - { + !(Wnd->ExStyle & WS_EX_MDICHILD) && + Cmd != SW_SHOWNA) + { + //ERR("SWP Child No active and ZOrder\n"); Swp |= SWP_NOACTIVATE | SWP_NOZORDER; }
@@ -2026,11 +2186,16 @@ Wnd->pcls->style & CS_SAVEBITS && ((Cmd == SW_SHOW) || (Cmd == SW_NORMAL))) { - co_IntSetActiveWindow(Wnd,NULL,FALSE,TRUE); + co_IntSetActiveWindow(Wnd,NULL,FALSE,TRUE,FALSE); Swp |= SWP_NOACTIVATE | SWP_NOZORDER; } #endif
+ if (IsChildVisible(Wnd) || Swp & SWP_STATECHANGED) + { + TRACE("Child is Vis %s or State changed %s. ShowFlag %s\n", + (IsChildVisible(Wnd) ? "TRUE" : "FALSE"), (Swp & SWP_STATECHANGED ? "TRUE" : "FALSE"), + (ShowFlag ? "TRUE" : "FALSE")); co_WinPosSetWindowPos( Wnd, 0 != (Wnd->ExStyle & WS_EX_TOPMOST) ? HWND_TOPMOST : HWND_TOP, NewPos.left, @@ -2038,13 +2203,24 @@ NewPos.right, //NewPos.right - NewPos.left, NewPos.bottom, //NewPos.bottom - NewPos.top, LOWORD(Swp)); + } + else + { + TRACE("Parent Vis?\n"); + /* if parent is not visible simply toggle WS_VISIBLE and return */ + if (ShowFlag) IntSetStyle( Wnd, WS_VISIBLE, 0 ); + else IntSetStyle( Wnd, 0, WS_VISIBLE ); + } + + if ( EventMsg ) IntNotifyWinEvent(EventMsg, Wnd, OBJID_WINDOW, CHILDID_SELF, WEF_SETBYWNDPTI); + + //if ( ShowOwned ) IntShowOwnedPopups(Wnd, TRUE );
if ((Cmd == SW_HIDE) || (Cmd == SW_MINIMIZE)) { - PTHREADINFO pti = PsGetCurrentThreadWin32Thread(); - - // and Rule #1. - if (Wnd == pti->MessageQueue->spwndActive && pti->MessageQueue == IntGetFocusMessageQueue()) + if ( ( Wnd->spwndParent == UserGetDesktopWindow() && !ActivateOtherWindowMin(Wnd) ) || + // and Rule #1. + ( Wnd == pti->MessageQueue->spwndActive && pti->MessageQueue == IntGetFocusMessageQueue() ) ) { co_WinPosActivateOtherWindow(Wnd); } @@ -2649,8 +2825,6 @@ UINT cmd, // Wine SW_ commands BOOL Hide) { - RECTL NewPos; - UINT SwFlags; PWND pWnd;
TRACE("Enter NtUserMinMaximize\n"); @@ -2670,17 +2844,7 @@ goto Exit; }
- SwFlags = co_WinPosMinMaximize(pWnd, cmd, &NewPos); - - SwFlags |= Hide ? SWP_NOACTIVATE : 0; - - co_WinPosSetWindowPos( pWnd, - NULL, - NewPos.left, - NewPos.top, - NewPos.right, //NewPos.right - NewPos.left, - NewPos.bottom, //NewPos.bottom - NewPos.top, - SwFlags); + cmd |= Hide ? SW_HIDE : 0;
co_WinPosShowWindow(pWnd, cmd);
@@ -2749,8 +2913,7 @@ UserEnterExclusive();
if (!(Window = UserGetWindowObject(hWnd)) || // FIXME: -// Due to desktopbg.c -// Window == UserGetDesktopWindow() || // pWnd->fnid == FNID_DESKTOP + Window == UserGetDesktopWindow() || // pWnd->fnid == FNID_DESKTOP Window == UserGetMessageWindow() ) // pWnd->fnid == FNID_MESSAGEWND { ERR("NtUserSetWindowPos bad window handle!\n");
Modified: trunk/reactos/win32ss/user/user32/controls/regcontrol.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/user32/control... ============================================================================== --- trunk/reactos/win32ss/user/user32/controls/regcontrol.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/user32/controls/regcontrol.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -146,8 +146,8 @@ pfnClientW.pfnTitleWndProc = IconTitleWndProc; pfnClientA.pfnMenuWndProc = PopupMenuWndProcA; pfnClientW.pfnMenuWndProc = PopupMenuWndProcW; - pfnClientA.pfnDesktopWndProc = DesktopWndProc; - pfnClientW.pfnDesktopWndProc = DesktopWndProc; + pfnClientA.pfnDesktopWndProc = DesktopWndProcA; + pfnClientW.pfnDesktopWndProc = DesktopWndProcW; pfnClientA.pfnDefWindowProc = DefWindowProcA; pfnClientW.pfnDefWindowProc = DefWindowProcW; pfnClientA.pfnMessageWindowProc = MsgWindowProc;
Modified: trunk/reactos/win32ss/user/user32/include/controls.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/user32/include... ============================================================================== --- trunk/reactos/win32ss/user/user32/include/controls.h [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/user32/include/controls.h [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -90,7 +90,8 @@
HRGN set_control_clipping( HDC hdc, const RECT *rect );
-LRESULT WINAPI DesktopWndProc( HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam ); +LRESULT WINAPI DesktopWndProcA( HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam ); +LRESULT WINAPI DesktopWndProcW( HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam ); LRESULT WINAPI User32DefWindowProc(HWND,UINT,WPARAM,LPARAM,BOOL); BOOL WINAPI RegisterClientPFN(VOID); LRESULT WINAPI IconTitleWndProc( HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam );
Modified: trunk/reactos/win32ss/user/user32/misc/desktop.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/user32/misc/de... ============================================================================== --- trunk/reactos/win32ss/user/user32/misc/desktop.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/user32/misc/desktop.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -29,13 +29,61 @@ (HBRUSH)(COLOR_BACKGROUND+1) /* brush */ }; #endif + LRESULT WINAPI -DesktopWndProc( HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam ) -{ - TRACE("Desktop Class Atom! hWnd 0x%x, Msg %d\n", hwnd, message); - if (message == WM_NCCREATE) return TRUE; - return 0; /* all other messages are ignored */ +DesktopWndProcW(HWND Wnd, + UINT Msg, + WPARAM wParam, + LPARAM lParam) +{ + PAINTSTRUCT PS; + TRACE("Desktop W Class Atom! hWnd 0x%x, Msg %d\n", Wnd, Msg); + + switch(Msg) + { + case WM_NCCREATE: + case WM_CREATE: + case WM_CLOSE: + case WM_DISPLAYCHANGE: + { + LRESULT lResult; + NtUserMessageCall( Wnd, Msg, wParam, lParam, (ULONG_PTR)&lResult, FNID_DESKTOP, FALSE); + return lResult; + } + + case WM_ERASEBKGND: + PaintDesktop((HDC)wParam); + return 1; + + case WM_PAINT: + if (BeginPaint(Wnd, &PS)) + { + EndPaint(Wnd, &PS); + } + return 0; + + case WM_SYSCOLORCHANGE: + RedrawWindow(Wnd, NULL, NULL, RDW_INVALIDATE|RDW_ERASE|RDW_ALLCHILDREN); + break; + + case WM_PALETTECHANGED: + if (Wnd == (HWND)wParam) break; + case WM_QUERYNEWPALETTE: + { + HDC hdc = GetWindowDC( Wnd ); + PaintDesktop(hdc); + ReleaseDC( Wnd, hdc ); + break; + } + + case WM_SETCURSOR: + return (LRESULT)SetCursor(LoadCursorW(0, (LPCWSTR)IDC_ARROW)); + + default: + return DefWindowProcW(Wnd, Msg, wParam, lParam); + } + return 0; }
VOID
Modified: trunk/reactos/win32ss/user/user32/windows/message.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/user32/windows... ============================================================================== --- trunk/reactos/win32ss/user/user32/windows/message.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/user32/windows/message.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -1158,7 +1158,33 @@ return wparam; }
- ++LRESULT ++WINAPI +DesktopWndProcA( HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam ) +{ + LRESULT Result; + MSG AnsiMsg, UcMsg; + + TRACE("Desktop A Class Atom! hWnd 0x%x, Msg %d\n", hwnd, message); + + AnsiMsg.hwnd = hwnd; + AnsiMsg.message = message; + AnsiMsg.wParam = wParam; + AnsiMsg.lParam = lParam; + + // Desktop is always Unicode so convert Ansi here. + if (!MsgiAnsiToUnicodeMessage(hwnd, &UcMsg, &AnsiMsg)) + { + return FALSE; + } + + Result = DesktopWndProcW(hwnd, message, UcMsg.wParam, UcMsg.lParam); + + MsgiAnsiToUnicodeCleanup(&UcMsg, &AnsiMsg); + + return Result; + } + /* * @implemented */
Modified: trunk/reactos/win32ss/user/win32csr/desktopbg.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/win32csr/deskt... ============================================================================== --- trunk/reactos/win32ss/user/win32csr/desktopbg.c [iso-8859-1] (original) +++ trunk/reactos/win32ss/user/win32csr/desktopbg.c [iso-8859-1] Mon Aug 20 00:26:08 2012 @@ -1,10 +1,27 @@ -/* $Id$ - * - * reactos/subsys/csrss/win32csr/desktopbg.c +/* + * win32ss/user/win32csr/desktopbg.c * * Desktop background window functions * * ReactOS Operating System + * + * Looks as a hax fix to a problem of not having a proper class window proc support + * which ReactOS has now. + * + * Notes on reason why this is here: + * http://www.reactos.org/archives/public/ros-kernel/2003-November/000538.html + * http://www.reactos.org/archives/public/ros-kernel/2003-November/000545.html + * http://www.reactos.org/archives/public/ros-kernel/2003-November/000586.html + * http://www.reactos.org/archives/public/ros-kernel/2003-November/000674.html + * Revision 6908 Move desktop window proc from WIN32K to CSRSS + * Bugs 42, 48 and 57. + * + * http://www.reactos.org/archives/public/ros-kernel/2003-December/001186.html + * + + Now this is used to start Desktops Threads with TEB support. + These first three are Application, Winlogon and ScreenSaver desktops. + */
#define NDEBUG @@ -36,7 +53,7 @@
static BOOL BgInitialized = FALSE; static HWND VisibleDesktopWindow = NULL; - +#if 0 static LRESULT CALLBACK @@ -160,7 +177,7 @@
return TRUE; } - +#endif static DWORD WINAPI @@ -170,6 +187,8 @@ MSG msg; PDTBG_THREAD_DATA ThreadData = (PDTBG_THREAD_DATA)Data;
+ DPRINT("DtbgDesktopThread\n"); + if (!SetThreadDesktop(ThreadData->Desktop)) { DPRINT1("Failed to set thread desktop\n"); @@ -181,9 +200,12 @@ BackgroundWnd = CreateWindowW((LPCWSTR)DESKTOP_WINDOW_ATOM, L"", WS_POPUP | WS_CLIPCHILDREN, - 0, 0, 0, 0, + GetSystemMetrics(SM_XVIRTUALSCREEN), + GetSystemMetrics(SM_YVIRTUALSCREEN), + GetSystemMetrics(SM_CXVIRTUALSCREEN), + GetSystemMetrics(SM_CYVIRTUALSCREEN), NULL, NULL, - (HINSTANCE)GetModuleHandleW(NULL), + (HINSTANCE)GetModuleHandleW(L"user32.dll"), // Run in win32k/user32. NULL);
if (NULL == BackgroundWnd) @@ -194,15 +216,22 @@ return 1; }
+ DPRINT("BackgroundWnd 0x%p\n",BackgroundWnd); + ThreadData->Status = STATUS_SUCCESS; SetEvent(ThreadData->Event);
while (GetMessageW(&msg, NULL, 0, 0)) { + if (msg.message == WM_QUIT) + { + DPRINT1("DtbgDesktopThread WM_QUIT\n"); + } TranslateMessage(&msg); DispatchMessageW(&msg); }
+ DPRINT1("DtbgDesktopThread Exit\n"); return 1; }
@@ -217,8 +246,8 @@ { BgInitialized = TRUE;
- if (!DtbgInit()) - return STATUS_UNSUCCESSFUL; + // if (!DtbgInit()) + // return STATUS_UNSUCCESSFUL; }
/* @@ -259,6 +288,7 @@
CSR_API(CsrShowDesktop) { +#if 0 PRIVATE_NOTIFY_DESKTOP nmh; DPRINT("CsrShowDesktop\n");
@@ -276,12 +306,13 @@ { return STATUS_UNSUCCESSFUL; } - +#endif return STATUS_SUCCESS; }
CSR_API(CsrHideDesktop) { +#if 0 PRIVATE_NOTIFY_DESKTOP nmh; DPRINT("CsrHideDesktop\n");
@@ -296,7 +327,7 @@ { return STATUS_UNSUCCESSFUL; } - +#endif return STATUS_SUCCESS; }
@@ -304,6 +335,8 @@ FASTCALL DtbgIsDesktopVisible(VOID) { + VisibleDesktopWindow = GetDesktopWindow(); // DESKTOPWNDPROC + if (VisibleDesktopWindow != NULL && !IsWindowVisible(VisibleDesktopWindow)) {