-/* $Id$
+/*
*
* COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS user32.dll
/* GLOBALS *******************************************************************/
-COLORREF SysColors[NUM_SYSCOLORS] = {0};
-HPEN SysPens[NUM_SYSCOLORS] = {0};
-HBRUSH SysBrushes[NUM_SYSCOLORS] = {0};
-
/* Bits in the dwKeyData */
#define KEYDATA_ALT 0x2000
#define KEYDATA_PREVSTATE 0x4000
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 */
- (void)NtUserGetSysColors(SysColors, NUM_SYSCOLORS);
- (void)NtUserGetSysColorPens(SysPens, NUM_SYSCOLORS);
- (void)NtUserGetSysColorBrushes(SysBrushes, NUM_SYSCOLORS);
- }
+
+ // Done! gpsi!
}
/*
* @implemented
*/
-DWORD STDCALL
+DWORD WINAPI
GetSysColor(int nIndex)
{
- if(nIndex >= 0 && nIndex <= NUM_SYSCOLORS)
+ if(nIndex >= 0 && nIndex < NUM_SYSCOLORS)
{
- return SysColors[nIndex];
+ return gpsi->argbSystem[nIndex];
}
SetLastError(ERROR_INVALID_PARAMETER);
/*
* @implemented
*/
-HPEN STDCALL
-GetSysColorPen(int nIndex)
-{
- if(nIndex >= 0 && nIndex <= NUM_SYSCOLORS)
- {
- return SysPens[nIndex];
- }
-
- SetLastError(ERROR_INVALID_PARAMETER);
- return NULL;
-}
-
-/*
- * @implemented
- */
-HBRUSH STDCALL
+HBRUSH WINAPI
GetSysColorBrush(int nIndex)
{
- if(nIndex >= 0 && nIndex <= NUM_SYSCOLORS)
+ if(nIndex >= 0 && nIndex < NUM_SYSCOLORS)
{
- return SysBrushes[nIndex];
+ return gpsi->ahbrSystem[nIndex];
}
SetLastError(ERROR_INVALID_PARAMETER);
* @implemented
*/
BOOL
-STDCALL
+WINAPI
SetSysColors(
int cElements,
CONST INT *lpaElements,
CONST COLORREF *lpaRgbValues)
{
- BOOL Ret;
- struct
- {
- INT *Elements;
- COLORREF *Colors;
- } ChangeSysColors;
+ return NtUserSetSysColors(cElements, lpaElements, lpaRgbValues, 0);
+}
- ChangeSysColors.Elements = (INT*)lpaElements;
- ChangeSysColors.Colors = (COLORREF*)lpaRgbValues;
+BOOL
+FASTCALL
+DefSetText(HWND hWnd, PCWSTR String, BOOL Ansi)
+{
+ LARGE_STRING lsString;
- if(cElements > 0)
+ if ( String )
{
- Ret = NtUserSetSysColors(&ChangeSysColors, cElements);
- if(Ret)
- {
- /* FIXME - just change it in the usermode structure, too, instead of asking win32k again */
- (void)NtUserGetSysColors(SysColors, NUM_SYSCOLORS);
- }
+ if ( Ansi )
+ RtlInitLargeAnsiString((PLARGE_ANSI_STRING)&lsString, (PCSZ)String, 0);
+ else
+ RtlInitLargeUnicodeString((PLARGE_UNICODE_STRING)&lsString, String, 0);
}
- else
- {
- SetLastError(ERROR_INVALID_PARAMETER);
- Ret = FALSE;
- }
-
- return Ret;
+ return NtUserDefSetText(hWnd, (String ? &lsString : NULL));
}
void
-UserGetInsideRectNC(PWINDOW Wnd, RECT *rect)
+UserGetInsideRectNC(PWND Wnd, RECT *rect)
{
ULONG Style;
ULONG ExStyle;
- Style = Wnd->Style;
+ Style = Wnd->style;
ExStyle = Wnd->ExStyle;
rect->top = rect->left = 0;
- rect->right = Wnd->WindowRect.right - Wnd->WindowRect.left;
- rect->bottom = Wnd->WindowRect.bottom - Wnd->WindowRect.top;
+ rect->right = Wnd->rcWindow.right - Wnd->rcWindow.left;
+ rect->bottom = Wnd->rcWindow.bottom - Wnd->rcWindow.top;
if (Style & WS_ICONIC)
{
VOID
DefWndSetRedraw(HWND hWnd, WPARAM wParam)
{
- LONG Style = GetWindowLong(hWnd, GWL_STYLE);
+ LONG Style = GetWindowLongPtr(hWnd, GWL_STYLE);
/* Content can be redrawn after a change. */
if (wParam)
{
if (!(Style & WS_VISIBLE)) /* Not Visible */
{
- SetWindowLong(hWnd, GWL_STYLE, WS_VISIBLE);
+ SetWindowLongPtr(hWnd, GWL_STYLE, WS_VISIBLE);
}
}
else /* Content cannot be redrawn after a change. */
{
RedrawWindow( hWnd, NULL, 0, RDW_ALLCHILDREN | RDW_VALIDATE );
Style &= ~WS_VISIBLE;
- SetWindowLong(hWnd, GWL_STYLE, Style); /* clear bits */
+ SetWindowLongPtr(hWnd, GWL_STYLE, Style); /* clear bits */
}
}
return;
case HTCLIENT:
{
- HICON hCursor = (HICON)GetClassLongW(hWnd, GCL_HCURSOR);
+ HICON hCursor = (HICON)GetClassLongPtrW(hWnd, GCL_HCURSOR);
if (hCursor)
{
SetCursor(hCursor);
case HTBOTTOMLEFT:
case HTTOPRIGHT:
{
- if (GetWindowLongW(hWnd, GWL_STYLE) & WS_MAXIMIZE)
+ if (GetWindowLongPtrW(hWnd, GWL_STYLE) & WS_MAXIMIZE)
{
break;
}
}
static LONG
-DefWndStartSizeMove(HWND hWnd, PWINDOW Wnd, WPARAM wParam, POINT *capturePoint)
+DefWndStartSizeMove(HWND hWnd, PWND Wnd, WPARAM wParam, POINT *capturePoint)
{
LONG hittest = 0;
POINT pt;
MSG msg;
RECT rectWindow;
- ULONG Style = Wnd->Style;
+ ULONG Style = Wnd->style;
- rectWindow = Wnd->WindowRect;
+ rectWindow = Wnd->rcWindow;
if ((wParam & 0xfff0) == SC_MOVE)
{
DWORD dwPoint = GetMessagePos();
BOOL DragFullWindows = FALSE;
HWND hWndParent = NULL;
- PWINDOW Wnd;
+ PWND Wnd;
Wnd = ValidateHwnd(hwnd);
if (!Wnd)
return;
- Style = Wnd->Style;
+ Style = Wnd->style;
ExStyle = Wnd->ExStyle;
iconic = (Style & WS_MINIMIZE) != 0;
/* Get min/max info */
WinPosGetMinMaxInfo(hwnd, NULL, NULL, &minTrack, &maxTrack);
- sizingRect = Wnd->WindowRect;
+ sizingRect = Wnd->rcWindow;
if (Style & WS_CHILD)
{
hWndParent = GetParent(hwnd);
if( iconic ) /* create a cursor for dragging */
{
- HICON hIcon = (HICON)GetClassLongW(hwnd, GCL_HICON);
+ HICON hIcon = (HICON)GetClassLongPtrW(hwnd, GCL_HICON);
if(!hIcon) hIcon = (HICON)SendMessageW( hwnd, WM_QUERYDRAGICON, 0, 0L);
if( hIcon ) hDragCursor = CursorIconToCursor( hIcon, TRUE );
if( !hDragCursor ) iconic = FALSE;
DeleteObject(DesktopRgn);
}
}
+//#if 0
+// if (ISITHOOKED(WH_CBT))
+ {
+ LRESULT lResult;
+ NtUserMessageCall( hwnd, WM_CBT, HCBT_MOVESIZE, (LPARAM)&sizingRect, (ULONG_PTR)&lResult, FNID_DEFWINDOWPROC, FALSE);
+ if (lResult) moved = FALSE;
+ }
+//#endif
(void)NtUserSetGUIThreadHandle(MSQ_STATE_MOVESIZE, NULL);
SendMessageA( hwnd, WM_EXITSIZEMOVE, 0, 0 );
SendMessageA( hwnd, WM_SETVISIBLE, !IsIconic(hwnd), 0L);
WINDOWPLACEMENT wp;
POINT Pt;
+ if (!IsWindowEnabled( hWnd )) return 0;
+
+//#if 0
+// if (ISITHOOKED(WH_CBT))
+ {
+ LRESULT lResult;
+ NtUserMessageCall( hWnd, WM_SYSCOMMAND, wParam, lParam, (ULONG_PTR)&lResult, FNID_DEFWINDOWPROC, FALSE);
+ if (lResult) return 0;
+ }
+//#endif
switch (wParam & 0xfff0)
{
case SC_MOVE:
}
break;
case SC_CLOSE:
- SendMessageA(hWnd, WM_CLOSE, 0, 0);
- break;
+ return SendMessageW(hWnd, WM_CLOSE, 0, 0);
+
case SC_MOUSEMENU:
{
Pt.x = (short)LOWORD(lParam);
DefWndHandleWindowPosChanging(HWND hWnd, WINDOWPOS* Pos)
{
POINT maxTrack, minTrack;
- LONG style = GetWindowLongA(hWnd, GWL_STYLE);
+ LONG style = GetWindowLongPtrA(hWnd, GWL_STYLE);
if (Pos->flags & SWP_NOSIZE) return 0;
if ((style & WS_THICKFRAME) || ((style & (WS_POPUP | WS_CHILD)) == 0))
RECT Rect;
GetClientRect(hWnd, &Rect);
- MapWindowPoints(hWnd, (GetWindowLongW(hWnd, GWL_STYLE) & WS_CHILD ?
+ MapWindowPoints(hWnd, (GetWindowLongPtrW(hWnd, GWL_STYLE) & WS_CHILD ?
GetParent(hWnd) : NULL), (LPPOINT) &Rect, 2);
if (! (Pos->flags & SWP_NOCLIENTMOVE))
* Client area
*/
if ( uFlags & PRF_CLIENT)
- SendMessageW(hwnd, WM_PRINTCLIENT, (WPARAM)hdc, PRF_CLIENT);
+ SendMessageW(hwnd, WM_PRINTCLIENT, (WPARAM)hdc, uFlags);
+}
+
+static BOOL CALLBACK
+UserSendUiUpdateMsg(HWND hwnd, LPARAM lParam)
+{
+ SendMessageW(hwnd, WM_UPDATEUISTATE, (WPARAM)lParam, 0);
+ return TRUE;
}
DefWndScreenshot(HWND hWnd)
{
RECT rect;
+ HDC hdc;
+ INT w;
+ INT h;
+ HBITMAP hbitmap;
+ HDC hdc2;
OpenClipboard(hWnd);
EmptyClipboard();
- HDC hdc = GetWindowDC(hWnd);
+ hdc = GetWindowDC(hWnd);
GetWindowRect(hWnd, &rect);
- INT w = rect.right - rect.left;
- INT h = rect.bottom - rect.top;
+ w = rect.right - rect.left;
+ h = rect.bottom - rect.top;
- HBITMAP hbitmap = CreateCompatibleBitmap(hdc, w, h);
- HDC hdc2 = CreateCompatibleDC(hdc);
+ hbitmap = CreateCompatibleBitmap(hdc, w, h);
+ hdc2 = CreateCompatibleDC(hdc);
SelectObject(hdc2, hbitmap);
BitBlt(hdc2, 0, 0, w, h,
-LRESULT STDCALL
+LRESULT WINAPI
User32DefWindowProc(HWND hWnd,
UINT Msg,
WPARAM wParam,
return DefWndNCCalcSize(hWnd, (BOOL)wParam, (RECT*)lParam);
}
+ case WM_POPUPSYSTEMMENU:
+ {
+ /* This is an undocumented message used by the windows taskbar to
+ display the system menu of windows that belong to other processes. */
+ HMENU menu = GetSystemMenu(hWnd, FALSE);
+
+ if (menu)
+ TrackPopupMenu(menu, TPM_LEFTBUTTON|TPM_RIGHTBUTTON,
+ LOWORD(lParam), HIWORD(lParam), 0, hWnd, NULL);
+ return 0;
+ }
+
case WM_NCACTIVATE:
{
return DefWndNCActivate(hWnd, wParam);
case WM_CONTEXTMENU:
{
- if (GetWindowLongW(hWnd, GWL_STYLE) & WS_CHILD)
+ if (GetWindowLongPtrW(hWnd, GWL_STYLE) & WS_CHILD)
{
if (bUnicode)
{
else
{
POINT Pt;
- DWORD Style;
+ LONG_PTR Style;
LONG HitCode;
- Style = GetWindowLongW(hWnd, GWL_STYLE);
+ Style = GetWindowLongPtrW(hWnd, GWL_STYLE);
Pt.x = GET_X_LPARAM(lParam);
Pt.y = GET_Y_LPARAM(lParam);
if((SystemMenu = GetSystemMenu(hWnd, FALSE)))
{
- MenuInitSysMenuPopup(SystemMenu, GetWindowLongW(hWnd, GWL_STYLE),
- GetClassLongW(hWnd, GCL_STYLE), HitCode);
+ MenuInitSysMenuPopup(SystemMenu, GetWindowLongPtrW(hWnd, GWL_STYLE),
+ GetClassLongPtrW(hWnd, GCL_STYLE), HitCode);
if(HitCode == HTCAPTION)
Flags = TPM_LEFTBUTTON | TPM_RIGHTBUTTON;
return (0);
}
+ case WM_SYSCOLORCHANGE:
+ {
+ /* force to redraw non-client area */
+ DefWndNCPaint(hWnd, (HRGN)1, -1);
+ /* Use InvalidateRect to redraw client area, enable
+ * erase to redraw all subcontrols otherwise send the
+ * WM_SYSCOLORCHANGE to child windows/controls is required
+ */
+ InvalidateRect(hWnd,NULL,TRUE);
+ return (0);
+ }
+
case WM_PAINTICON:
case WM_PAINT:
{
if (hDC)
{
HICON hIcon;
- if (GetWindowLongW(hWnd, GWL_STYLE) & WS_MINIMIZE &&
- (hIcon = (HICON)GetClassLongW(hWnd, GCL_HICON)) != NULL)
+
+ if (GetWindowLongPtrW(hWnd, GWL_STYLE) & WS_MINIMIZE &&
+ (hIcon = (HICON)GetClassLongPtrW(hWnd, GCL_HICON)) != NULL)
{
RECT ClientRect;
INT x, y;
case WM_SETREDRAW:
{
- DefWndSetRedraw(hWnd, wParam);
+ LONG_PTR Style = GetWindowLongPtrW(hWnd, GWL_STYLE);
+ if (wParam) SetWindowLongPtr(hWnd, GWL_STYLE, Style | WS_VISIBLE);
+ else
+ {
+ RedrawWindow(hWnd, NULL, 0, RDW_ALLCHILDREN | RDW_VALIDATE);
+ Style &= ~WS_VISIBLE;
+ SetWindowLongPtr(hWnd, GWL_STYLE, Style);
+ }
return (0);
}
case WM_MOUSEACTIVATE:
{
- if (GetWindowLongW(hWnd, GWL_STYLE) & WS_CHILD)
+ if (GetWindowLongPtrW(hWnd, GWL_STYLE) & WS_CHILD)
{
LONG Ret;
if (bUnicode)
{
/* Check if the window is minimized. */
if (LOWORD(wParam) != WA_INACTIVE &&
- !(GetWindowLongW(hWnd, GWL_STYLE) & WS_MINIMIZE))
+ !(GetWindowLongPtrW(hWnd, GWL_STYLE) & WS_MINIMIZE))
{
SetFocus(hWnd);
}
case WM_MOUSEWHEEL:
{
- if (GetWindowLongW(hWnd, GWL_STYLE) & WS_CHILD)
+ if (GetWindowLongPtrW(hWnd, GWL_STYLE) & WS_CHILD)
{
if (bUnicode)
{
case WM_ICONERASEBKGND:
{
RECT Rect;
- HBRUSH hBrush = (HBRUSH)GetClassLongW(hWnd, GCL_HBRBACKGROUND);
+ HBRUSH hBrush = (HBRUSH)GetClassLongPtrW(hWnd, GCL_HBRBACKGROUND);
if (NULL == hBrush)
{
return 0;
}
- if (GetClassLongW(hWnd, GCL_STYLE) & CS_PARENTDC)
+ if (GetClassLongPtrW(hWnd, GCL_STYLE) & CS_PARENTDC)
{
/* can't use GetClipBox with a parent DC or we fill the whole parent */
GetClientRect(hWnd, &Rect);
case WM_SETCURSOR:
{
- ULONG Style = GetWindowLongW(hWnd, GWL_STYLE);
+ LONG_PTR Style = GetWindowLongPtrW(hWnd, GWL_STYLE);
if (Style & WS_CHILD)
{
{
if (HIWORD(lParam) & KEYDATA_ALT)
{
+ HWND top = GetAncestor(hWnd, GA_ROOT);
/* if( HIWORD(lParam) & ~KEYDATA_PREVSTATE ) */
if ( (wParam == VK_MENU || wParam == VK_LMENU
|| wParam == VK_RMENU) && !iMenuSysKey )
+ {
iMenuSysKey = 1;
+ /* mimic behaviour of XP, sending a WM_SYSCOMMAND when pressing <alt> */
+ SendMessageW( top, WM_SYSCOMMAND, SC_KEYMENU, 0L );
+ }
else
iMenuSysKey = 0;
if (wParam == VK_F4) /* Try to close the window */
{
- HWND top = GetAncestor(hWnd, GA_ROOT);
- if (!(GetClassLongW(top, GCL_STYLE) & CS_NOCLOSE))
+ if (!(GetClassLongPtrW(top, GCL_STYLE) & CS_NOCLOSE))
{
if (bUnicode)
PostMessageW(top, WM_SYSCOMMAND, SC_CLOSE, 0);
if ((HIWORD(lParam) & KEYDATA_ALT) && wParam)
{
if (wParam == '\t' || wParam == '\x1b') break;
- if (wParam == ' ' && (GetWindowLongW( hWnd, GWL_STYLE ) & WS_CHILD))
+ if (wParam == ' ' && (GetWindowLongPtrW( hWnd, GWL_STYLE ) & WS_CHILD))
SendMessageW( GetParent(hWnd), Msg, wParam, lParam );
else
SendMessageW( hWnd, WM_SYSCOMMAND, SC_KEYMENU, wParam );
case WM_SHOWWINDOW:
{
- LONG Style;
- INT Ret = 0;
-
- if (!lParam) return 0;
- Style = GetWindowLongW(hWnd, GWL_STYLE);
- if ((Style & WS_VISIBLE) && wParam) return 0;
- if (!(Style & WS_VISIBLE) && !wParam) return 0;
- if (!GetWindow(hWnd, GW_OWNER)) return 0;
- Ret = NtUserCallTwoParam((DWORD) hWnd, (DWORD) wParam, TWOPARAM_ROUTINE_ROS_SHOWWINDOW);
- if(Ret)
- {
- if( Ret == -1) return 0;
- return Ret;
- }
- ShowWindow(hWnd, wParam ? SW_SHOWNOACTIVATE : SW_HIDE);
+ if (lParam) // Call when it is necessary.
+ NtUserMessageCall( hWnd, Msg, wParam, lParam, 0, FNID_DEFWINDOWPROC, FALSE);
break;
}
+ case WM_CLIENTSHUTDOWN:
+ {
+ LRESULT lResult;
+ NtUserMessageCall( hWnd, Msg, wParam, lParam, (ULONG_PTR)&lResult, FNID_DEFWINDOWPROC, FALSE);
+ return lResult;
+ }
+
case WM_CANCELMODE:
{
iMenuSysKey = 0;
/* FIXME: Check for a desktop. */
- if (!(GetWindowLongW( hWnd, GWL_STYLE ) & WS_CHILD)) EndMenu();
+ if (!(GetWindowLongPtrW( hWnd, GWL_STYLE ) & WS_CHILD)) EndMenu();
if (GetCapture() == hWnd)
{
ReleaseCapture();
*/
case WM_QUERYDROPOBJECT:
{
- if (GetWindowLongW(hWnd, GWL_EXSTYLE) & WS_EX_ACCEPTFILES)
+ if (GetWindowLongPtrW(hWnd, GWL_EXSTYLE) & WS_EX_ACCEPTFILES)
{
return(1);
}
UINT Len;
HICON hIcon;
- hIcon = (HICON)GetClassLongW(hWnd, GCL_HICON);
+ hIcon = (HICON)GetClassLongPtrW(hWnd, GCL_HICON);
if (hIcon)
{
return ((LRESULT)hIcon);
return ((LRESULT)LoadIconW(0, IDI_APPLICATION));
}
- /* FIXME: WM_ISACTIVEICON */
+ case WM_ISACTIVEICON:
+ {
+ PWND pWnd;
+ BOOL isai;
+ pWnd = ValidateHwnd(hWnd);
+ if (!pWnd) return 0;
+ isai = (pWnd->state & WNDS_ACTIVEFRAME) != 0;
+ return isai;
+ }
case WM_NOTIFYFORMAT:
{
case WM_SETICON:
{
INT Index = (wParam != 0) ? GCL_HICON : GCL_HICONSM;
- HICON hOldIcon = (HICON)GetClassLongW(hWnd, Index);
- SetClassLongW(hWnd, Index, lParam);
+ HICON hOldIcon = (HICON)GetClassLongPtrW(hWnd, Index);
+ SetClassLongPtrW(hWnd, Index, lParam);
SetWindowPos(hWnd, 0, 0, 0, 0, 0,
SWP_FRAMECHANGED | SWP_NOSIZE | SWP_NOMOVE |
SWP_NOACTIVATE | SWP_NOZORDER);
case WM_GETICON:
{
INT Index = (wParam == ICON_BIG) ? GCL_HICON : GCL_HICONSM;
- return (GetClassLongW(hWnd, Index));
+ return (GetClassLongPtrW(hWnd, Index));
}
case WM_HELP:
case WM_INPUTLANGCHANGE:
{
- //FIXME: What to do?
- return TRUE;
+ int count = 0;
+ HWND *win_array = WIN_ListChildren( hWnd );
+
+ if (!win_array)
+ break;
+ while (win_array[count])
+ SendMessageW( win_array[count++], WM_INPUTLANGCHANGE, wParam, lParam);
+ HeapFree(GetProcessHeap(),0,win_array);
+ break;
}
- case WM_ENDSESSION:
- if (wParam) PostQuitMessage(0);
- return 0;
+ case WM_QUERYUISTATE:
+ {
+ LRESULT Ret = 0;
+ PWND Wnd = ValidateHwnd(hWnd);
+ if (Wnd != NULL)
+ {
+ if (Wnd->HideFocus)
+ Ret |= UISF_HIDEFOCUS;
+ if (Wnd->HideAccel)
+ Ret |= UISF_HIDEACCEL;
+ }
+ return Ret;
+ }
+
+ case WM_CHANGEUISTATE:
+ {
+ BOOL AlwaysShowCues = FALSE;
+ WORD Action = LOWORD(wParam);
+ WORD Flags = HIWORD(wParam);
+ PWND Wnd;
+
+ SystemParametersInfoW(SPI_GETKEYBOARDCUES, 0, &AlwaysShowCues, 0);
+ if (AlwaysShowCues)
+ break;
+
+ Wnd= ValidateHwnd(hWnd);
+ if (!Wnd || lParam != 0)
+ break;
+
+ if (Flags & ~(UISF_HIDEFOCUS | UISF_HIDEACCEL | UISF_ACTIVE))
+ break;
+
+ if (Flags & UISF_ACTIVE)
+ {
+ WARN("WM_CHANGEUISTATE does not yet support UISF_ACTIVE!\n");
+ }
+
+ if (Action == UIS_INITIALIZE)
+ {
+ PDESKTOPINFO Desk = GetThreadDesktopInfo();
+ if (Desk == NULL)
+ break;
+
+ Action = Desk->LastInputWasKbd ? UIS_CLEAR : UIS_SET;
+ Flags = UISF_HIDEFOCUS | UISF_HIDEACCEL;
+
+ /* We need to update wParam in case we need to send out messages */
+ wParam = MAKEWPARAM(Action, Flags);
+ }
+
+ switch (Action)
+ {
+ case UIS_SET:
+ /* See if we actually need to change something */
+ if ((Flags & UISF_HIDEFOCUS) && !Wnd->HideFocus)
+ break;
+ if ((Flags & UISF_HIDEACCEL) && !Wnd->HideAccel)
+ break;
+
+ /* Don't need to do anything... */
+ return 0;
+
+ case UIS_CLEAR:
+ /* See if we actually need to change something */
+ if ((Flags & UISF_HIDEFOCUS) && Wnd->HideFocus)
+ break;
+ if ((Flags & UISF_HIDEACCEL) && Wnd->HideAccel)
+ break;
+
+ /* Don't need to do anything... */
+ return 0;
+
+ default:
+ WARN("WM_CHANGEUISTATE: Unsupported Action 0x%x\n", Action);
+ break;
+ }
+
+ if ((Wnd->style & WS_CHILD) && Wnd->spwndParent != NULL)
+ {
+ /* We're a child window and we need to pass this message down until
+ we reach the root */
+ hWnd = UserHMGetHandle((PWND)DesktopPtrToUser(Wnd->spwndParent));
+ }
+ else
+ {
+ /* We're a top level window, we need to change the UI state */
+ Msg = WM_UPDATEUISTATE;
+ }
+
+ if (bUnicode)
+ return SendMessageW(hWnd, Msg, wParam, lParam);
+ else
+ return SendMessageA(hWnd, Msg, wParam, lParam);
+ }
+
+ case WM_UPDATEUISTATE:
+ {
+ BOOL Change = TRUE;
+ BOOL AlwaysShowCues = FALSE;
+ WORD Action = LOWORD(wParam);
+ WORD Flags = HIWORD(wParam);
+ PWND Wnd;
+
+ SystemParametersInfoW(SPI_GETKEYBOARDCUES, 0, &AlwaysShowCues, 0);
+ if (AlwaysShowCues)
+ break;
+
+ Wnd = ValidateHwnd(hWnd);
+ if (!Wnd || lParam != 0)
+ break;
+
+ if (Flags & ~(UISF_HIDEFOCUS | UISF_HIDEACCEL | UISF_ACTIVE))
+ break;
+
+ if (Flags & UISF_ACTIVE)
+ {
+ WARN("WM_UPDATEUISTATE does not yet support UISF_ACTIVE!\n");
+ }
+
+ if (Action == UIS_INITIALIZE)
+ {
+ PDESKTOPINFO Desk = GetThreadDesktopInfo();
+ if (Desk == NULL)
+ break;
+
+ Action = Desk->LastInputWasKbd ? UIS_CLEAR : UIS_SET;
+ Flags = UISF_HIDEFOCUS | UISF_HIDEACCEL;
+
+ /* We need to update wParam for broadcasting the update */
+ wParam = MAKEWPARAM(Action, Flags);
+ }
+
+ switch (Action)
+ {
+ case UIS_SET:
+ /* See if we actually need to change something */
+ if ((Flags & UISF_HIDEFOCUS) && !Wnd->HideFocus)
+ break;
+ if ((Flags & UISF_HIDEACCEL) && !Wnd->HideAccel)
+ break;
+
+ /* Don't need to do anything... */
+ Change = FALSE;
+ break;
+
+ case UIS_CLEAR:
+ /* See if we actually need to change something */
+ if ((Flags & UISF_HIDEFOCUS) && Wnd->HideFocus)
+ break;
+ if ((Flags & UISF_HIDEACCEL) && Wnd->HideAccel)
+ break;
+
+ /* Don't need to do anything... */
+ Change = FALSE;
+ break;
+
+ default:
+ WARN("WM_UPDATEUISTATE: Unsupported Action 0x%x\n", Action);
+ return 0;
+ }
+
+ /* Pack the information and call win32k */
+ if (Change)
+ {
+ if (!NtUserCallTwoParam((DWORD_PTR)hWnd, (DWORD_PTR)Flags | ((DWORD_PTR)Action << 3), TWOPARAM_ROUTINE_ROS_UPDATEUISTATE))
+ break;
+ }
+
+ /* Always broadcast the update to all children */
+ EnumChildWindows(hWnd,
+ UserSendUiUpdateMsg,
+ (LPARAM)wParam);
+
+ break;
+ }
}
return 0;
}
-LRESULT STDCALL
-DefWindowProcA(HWND hWnd,
- UINT Msg,
- WPARAM wParam,
- LPARAM lParam)
+/*
+ * helpers for calling IMM32 (from Wine 10/22/2008)
+ *
+ * WM_IME_* messages are generated only by IMM32,
+ * so I assume imm32 is already LoadLibrary-ed.
+ */
+static HWND
+DefWndImmGetDefaultIMEWnd(HWND hwnd)
+{
+ HINSTANCE hInstIMM = GetModuleHandleW(L"imm32\0");
+ HWND (WINAPI *pFunc)(HWND);
+ HWND hwndRet = 0;
+
+ if (!hInstIMM)
+ {
+ ERR("cannot get IMM32 handle\n");
+ return 0;
+ }
+
+ pFunc = (void*) GetProcAddress(hInstIMM, "ImmGetDefaultIMEWnd");
+ if (pFunc != NULL)
+ hwndRet = (*pFunc)(hwnd);
+
+ return hwndRet;
+}
+
+
+static BOOL
+DefWndImmIsUIMessageA(HWND hwndIME, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+ HINSTANCE hInstIMM = GetModuleHandleW(L"imm32\0");
+ BOOL (WINAPI *pFunc)(HWND,UINT,WPARAM,LPARAM);
+ BOOL fRet = FALSE;
+
+ if (!hInstIMM)
+ {
+ ERR("cannot get IMM32 handle\n");
+ return FALSE;
+ }
+
+ pFunc = (void*) GetProcAddress(hInstIMM, "ImmIsUIMessageA");
+ if (pFunc != NULL)
+ fRet = (*pFunc)(hwndIME, msg, wParam, lParam);
+
+ return fRet;
+}
+
+
+static BOOL
+DefWndImmIsUIMessageW(HWND hwndIME, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+ HINSTANCE hInstIMM = GetModuleHandleW(L"imm32\0");
+ BOOL (WINAPI *pFunc)(HWND,UINT,WPARAM,LPARAM);
+ BOOL fRet = FALSE;
+
+ if (!hInstIMM)
+ {
+ ERR("cannot get IMM32 handle\n");
+ return FALSE;
+ }
+
+ pFunc = (void*) GetProcAddress(hInstIMM, "ImmIsUIMessageW");
+ if (pFunc != NULL)
+ fRet = (*pFunc)(hwndIME, msg, wParam, lParam);
+
+ return fRet;
+}
+
+
+LRESULT WINAPI
+RealDefWindowProcA(HWND hWnd,
+ UINT Msg,
+ WPARAM wParam,
+ LPARAM lParam)
{
LRESULT Result = 0;
+ PWND Wnd;
SPY_EnterMessage(SPY_DEFWNDPROC, hWnd, Msg, wParam, lParam);
switch (Msg)
{
case WM_NCCREATE:
{
- ANSI_STRING AnsiString;
- UNICODE_STRING UnicodeString;
- LPCREATESTRUCTA cs = (LPCREATESTRUCTA)lParam;
- /* check for string, as static icons, bitmaps (SS_ICON, SS_BITMAP)
- * may have child window IDs instead of window name */
-
- if(cs->lpszName)
+ if (lParam)
{
- RtlInitAnsiString(&AnsiString, (LPSTR)cs->lpszName);
- RtlAnsiStringToUnicodeString(&UnicodeString, &AnsiString, TRUE);
- NtUserDefSetText(hWnd, &UnicodeString);
- RtlFreeUnicodeString(&UnicodeString);
+ LPCREATESTRUCTA cs = (LPCREATESTRUCTA)lParam;
+ /* check for string, as static icons, bitmaps (SS_ICON, SS_BITMAP)
+ * may have child window IDs instead of window name */
+ if (HIWORD(cs->lpszName))
+ {
+ DefSetText(hWnd, (PCWSTR)cs->lpszName, TRUE);
+ }
+ Result = 1;
}
- else
- NtUserDefSetText(hWnd, NULL);
-
- Result = 1;
break;
}
case WM_GETTEXTLENGTH:
{
- Result = (LRESULT)NtUserInternalGetWindowText(hWnd, NULL, 0);
+ PWSTR buf;
+ ULONG len;
+
+ Wnd = ValidateHwnd(hWnd);
+ if (Wnd != NULL && Wnd->strName.Length != 0)
+ {
+ buf = DesktopPtrToUser(Wnd->strName.Buffer);
+ if (buf != NULL &&
+ NT_SUCCESS(RtlUnicodeToMultiByteSize(&len,
+ buf,
+ Wnd->strName.Length)))
+ {
+ Result = (LRESULT) len;
+ }
+ }
+ else Result = 0L;
+
break;
}
case WM_GETTEXT:
{
- LPWSTR Buffer;
- LPSTR AnsiBuffer = (LPSTR)lParam;
- INT Length;
+ PWSTR buf = NULL;
+ PSTR outbuf = (PSTR)lParam;
+ UINT copy;
- Buffer = HeapAlloc(GetProcessHeap(), 0, wParam * sizeof(WCHAR));
- if (!Buffer)
+ Wnd = ValidateHwnd(hWnd);
+ if (Wnd != NULL && wParam != 0)
{
- Result = 0;
- break;
- }
- Length = NtUserInternalGetWindowText(hWnd, Buffer, wParam);
- if (Length > 0 && wParam > 0 &&
- !WideCharToMultiByte(CP_ACP, 0, Buffer, -1,
- AnsiBuffer, wParam, NULL, NULL))
- {
- AnsiBuffer[0] = '\0';
- }
-
- HeapFree(GetProcessHeap(), 0, Buffer);
+ if (Wnd->strName.Buffer != NULL)
+ buf = DesktopPtrToUser(Wnd->strName.Buffer);
+ else
+ outbuf[0] = L'\0';
- Result = (LRESULT)Length;
+ if (buf != NULL)
+ {
+ if (Wnd->strName.Length != 0)
+ {
+ copy = min(Wnd->strName.Length / sizeof(WCHAR), wParam - 1);
+ Result = WideCharToMultiByte(CP_ACP,
+ 0,
+ buf,
+ copy,
+ outbuf,
+ wParam,
+ NULL,
+ NULL);
+ outbuf[Result] = '\0';
+ }
+ else
+ outbuf[0] = '\0';
+ }
+ }
break;
}
case WM_SETTEXT:
{
- ANSI_STRING AnsiString;
- UNICODE_STRING UnicodeString;
+ DefSetText(hWnd, (PCWSTR)lParam, TRUE);
- if(lParam)
- {
- RtlInitAnsiString(&AnsiString, (LPSTR)lParam);
- RtlAnsiStringToUnicodeString(&UnicodeString, &AnsiString, TRUE);
- NtUserDefSetText(hWnd, &UnicodeString);
- RtlFreeUnicodeString(&UnicodeString);
- }
- else
- NtUserDefSetText(hWnd, NULL);
-
- if ((GetWindowLongW(hWnd, GWL_STYLE) & WS_CAPTION) == WS_CAPTION)
+ if ((GetWindowLongPtrW(hWnd, GWL_STYLE) & WS_CAPTION) == WS_CAPTION)
{
DefWndNCPaint(hWnd, (HRGN)1, -1);
}
break;
}
-/* FIXME: Implement these. */
- case WM_IME_CHAR:
case WM_IME_KEYDOWN:
+ {
+ Result = PostMessageA(hWnd, WM_KEYDOWN, wParam, lParam);
+ break;
+ }
+
case WM_IME_KEYUP:
+ {
+ Result = PostMessageA(hWnd, WM_KEYUP, wParam, lParam);
+ break;
+ }
+
+ case WM_IME_CHAR:
+ {
+ if (HIBYTE(wParam))
+ PostMessageA(hWnd, WM_CHAR, HIBYTE(wParam), lParam);
+ PostMessageA(hWnd, WM_CHAR, LOBYTE(wParam), lParam);
+ break;
+ }
+
case WM_IME_STARTCOMPOSITION:
case WM_IME_COMPOSITION:
case WM_IME_ENDCOMPOSITION:
case WM_IME_SELECT:
+ case WM_IME_NOTIFY:
+ {
+ HWND hwndIME;
+
+ hwndIME = DefWndImmGetDefaultIMEWnd(hWnd);
+ if (hwndIME)
+ Result = SendMessageA(hwndIME, Msg, wParam, lParam);
+ break;
+ }
+
case WM_IME_SETCONTEXT:
- FIXME("FIXME: WM_IME_* conversion isn't implemented yet!");
+ {
+ HWND hwndIME;
+
+ hwndIME = DefWndImmGetDefaultIMEWnd(hWnd);
+ if (hwndIME)
+ Result = DefWndImmIsUIMessageA(hwndIME, Msg, wParam, lParam);
+ break;
+ }
+
/* fall through */
default:
Result = User32DefWindowProc(hWnd, Msg, wParam, lParam, FALSE);
}
-LRESULT STDCALL
-DefWindowProcW(HWND hWnd,
- UINT Msg,
- WPARAM wParam,
- LPARAM lParam)
+LRESULT WINAPI
+RealDefWindowProcW(HWND hWnd,
+ UINT Msg,
+ WPARAM wParam,
+ LPARAM lParam)
{
LRESULT Result = 0;
+ PWND Wnd;
SPY_EnterMessage(SPY_DEFWNDPROC, hWnd, Msg, wParam, lParam);
switch (Msg)
{
case WM_NCCREATE:
{
- UNICODE_STRING UnicodeString;
- LPCREATESTRUCTW cs = (LPCREATESTRUCTW)lParam;
- /* check for string, as static icons, bitmaps (SS_ICON, SS_BITMAP)
- * may have child window IDs instead of window name */
-
- if(cs->lpszName)
- RtlInitUnicodeString(&UnicodeString, (LPWSTR)cs->lpszName);
+ if (lParam)
+ {
+ LPCREATESTRUCTW cs = (LPCREATESTRUCTW)lParam;
+ /* check for string, as static icons, bitmaps (SS_ICON, SS_BITMAP)
+ * may have child window IDs instead of window name */
- NtUserDefSetText( hWnd, (cs->lpszName ? &UnicodeString : NULL));
- Result = 1;
+ if (HIWORD(cs->lpszName))
+ {
+ DefSetText(hWnd, cs->lpszName, FALSE);
+ }
+ Result = 1;
+ }
break;
}
case WM_GETTEXTLENGTH:
{
- Result = (LRESULT)NtUserInternalGetWindowText(hWnd, NULL, 0);
+ PWSTR buf;
+ ULONG len;
+
+ Wnd = ValidateHwnd(hWnd);
+ if (Wnd != NULL && Wnd->strName.Length != 0)
+ {
+ buf = DesktopPtrToUser(Wnd->strName.Buffer);
+ if (buf != NULL &&
+ NT_SUCCESS(RtlUnicodeToMultiByteSize(&len,
+ buf,
+ Wnd->strName.Length)))
+ {
+ Result = (LRESULT) (Wnd->strName.Length / sizeof(WCHAR));
+ }
+ }
+ else Result = 0L;
+
break;
}
case WM_GETTEXT:
{
- Result = (LRESULT)NtUserInternalGetWindowText(hWnd, (PWSTR)lParam, wParam);
+ PWSTR buf = NULL;
+ PWSTR outbuf = (PWSTR)lParam;
+
+ Wnd = ValidateHwnd(hWnd);
+ if (Wnd != NULL && wParam != 0)
+ {
+ if (Wnd->strName.Buffer != NULL)
+ buf = DesktopPtrToUser(Wnd->strName.Buffer);
+ else
+ outbuf[0] = L'\0';
+
+ if (buf != NULL)
+ {
+ if (Wnd->strName.Length != 0)
+ {
+ Result = min(Wnd->strName.Length / sizeof(WCHAR), wParam - 1);
+ RtlCopyMemory(outbuf,
+ buf,
+ Result * sizeof(WCHAR));
+ outbuf[Result] = L'\0';
+ }
+ else
+ outbuf[0] = L'\0';
+ }
+ }
break;
}
case WM_SETTEXT:
{
- UNICODE_STRING UnicodeString;
-
- if(lParam)
- RtlInitUnicodeString(&UnicodeString, (LPWSTR)lParam);
+ DefSetText(hWnd, (PCWSTR)lParam, FALSE);
- NtUserDefSetText(hWnd, (lParam ? &UnicodeString : NULL));
-
- if ((GetWindowLongW(hWnd, GWL_STYLE) & WS_CAPTION) == WS_CAPTION)
+ if ((GetWindowLongPtrW(hWnd, GWL_STYLE) & WS_CAPTION) == WS_CAPTION)
{
DefWndNCPaint(hWnd, (HRGN)1, -1);
}
case WM_IME_CHAR:
{
- SendMessageW(hWnd, WM_CHAR, wParam, lParam);
+ PostMessageW(hWnd, WM_CHAR, wParam, lParam);
Result = 0;
break;
}
+ case WM_IME_KEYDOWN:
+ {
+ Result = PostMessageW(hWnd, WM_KEYDOWN, wParam, lParam);
+ break;
+ }
+
+ case WM_IME_KEYUP:
+ {
+ Result = PostMessageW(hWnd, WM_KEYUP, wParam, lParam);
+ break;
+ }
+
+ case WM_IME_STARTCOMPOSITION:
+ case WM_IME_COMPOSITION:
+ case WM_IME_ENDCOMPOSITION:
+ case WM_IME_SELECT:
+ case WM_IME_NOTIFY:
+ {
+ HWND hwndIME;
+
+ hwndIME = DefWndImmGetDefaultIMEWnd(hWnd);
+ if (hwndIME)
+ Result = SendMessageW(hwndIME, Msg, wParam, lParam);
+ break;
+ }
+
case WM_IME_SETCONTEXT:
{
- /* FIXME */
- FIXME("FIXME: WM_IME_SETCONTEXT is not implemented!");
- Result = 0;
+ HWND hwndIME;
+
+ hwndIME = DefWndImmGetDefaultIMEWnd(hWnd);
+ if (hwndIME)
+ Result = DefWndImmIsUIMessageW(hwndIME, Msg, wParam, lParam);
break;
}
return Result;
}
+LRESULT WINAPI
+DefWindowProcA(HWND hWnd,
+ UINT Msg,
+ WPARAM wParam,
+ LPARAM lParam)
+{
+ BOOL Hook, msgOverride = FALSE;
+ LRESULT Result = 0;
+
+ LOADUSERAPIHOOK
+
+ Hook = BeginIfHookedUserApiHook();
+ if (Hook)
+ msgOverride = IsMsgOverride(Msg, &guah.DefWndProcArray);
+
+ /* Bypass SEH and go direct. */
+ if (!Hook || !msgOverride)
+ return RealDefWindowProcA(hWnd, Msg, wParam, lParam);
+
+ _SEH2_TRY
+ {
+ Result = guah.DefWindowProcA(hWnd, Msg, wParam, lParam);
+ }
+ _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER)
+ {
+ }
+ _SEH2_END;
+
+ EndUserApiHook();
+
+ return Result;
+}
+
+LRESULT WINAPI
+DefWindowProcW(HWND hWnd,
+ UINT Msg,
+ WPARAM wParam,
+ LPARAM lParam)
+{
+ BOOL Hook, msgOverride = FALSE;
+ LRESULT Result = 0;
+
+ LOADUSERAPIHOOK
+
+ Hook = BeginIfHookedUserApiHook();
+ if (Hook)
+ msgOverride = IsMsgOverride(Msg, &guah.DefWndProcArray);
+
+ /* Bypass SEH and go direct. */
+ if (!Hook || !msgOverride)
+ return RealDefWindowProcW(hWnd, Msg, wParam, lParam);
+
+ _SEH2_TRY
+ {
+ Result = guah.DefWindowProcW(hWnd, Msg, wParam, lParam);
+ }
+ _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER)
+ {
+ }
+ _SEH2_END;
+
+ EndUserApiHook();
+
+ return Result;
+}