blob: 62280d9c6568276c9b1c7778e521b47f8af06938 [file] [log] [blame]
Alexandre Julliard401710d1993-09-04 10:09:32 +00001/*
2 * Window related functions
3 *
Alexandre Julliardaca05781994-10-17 18:12:41 +00004 * Copyright 1993, 1994 Alexandre Julliard
Alexandre Julliard401710d1993-09-04 10:09:32 +00005 */
Alexandre Julliard1e9ac791996-06-06 18:38:27 +00006
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00007#include <stdlib.h>
Alexandre Julliardfb9a9191994-03-01 19:48:04 +00008#include <string.h>
Alexandre Julliard18f92e71996-07-17 20:02:21 +00009#include <X11/Xatom.h>
Alexandre Julliard401710d1993-09-04 10:09:32 +000010
Alexandre Julliard36ca1361994-06-02 22:38:20 +000011#include "options.h"
Alexandre Julliard401710d1993-09-04 10:09:32 +000012#include "class.h"
13#include "win.h"
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +000014#include "heap.h"
Alexandre Julliardf0b23541993-09-29 12:21:49 +000015#include "user.h"
Alexandre Julliard5f721f81994-01-04 20:14:34 +000016#include "dce.h"
Alexandre Julliardcdd09231994-01-12 11:12:51 +000017#include "sysmetrics.h"
Alexandre Julliardaf0bae51995-10-03 17:06:08 +000018#include "cursoricon.h"
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +000019#include "heap.h"
20#include "hook.h"
Alexandre Julliard1285c2f1996-05-06 16:06:24 +000021#include "menu.h"
Alexandre Julliardef702d81996-05-28 18:54:58 +000022#include "message.h"
Alexandre Julliarde2abbb11995-03-19 17:39:39 +000023#include "nonclient.h"
Alexandre Julliardb817f4f1996-03-14 18:08:34 +000024#include "queue.h"
Alexandre Julliard234bc241994-12-10 13:02:28 +000025#include "winpos.h"
26#include "color.h"
Alexandre Julliarde2991ea1995-07-29 13:09:43 +000027#include "shm_main_blk.h"
28#include "dde_proc.h"
Alexandre Julliard1e9ac791996-06-06 18:38:27 +000029#include "clipboard.h"
Alexandre Julliard2d93d001996-05-21 15:01:41 +000030#include "winproc.h"
Alexandre Julliard01d63461997-01-20 19:43:45 +000031#include "thread.h"
Alexandre Julliard85ed45e1998-08-22 19:03:56 +000032#include "process.h"
Alexandre Julliardaca05781994-10-17 18:12:41 +000033#include "debug.h"
Alexandre Julliard767e6f61998-08-09 12:47:43 +000034#include "winerror.h"
Rein Klazes5c6fc1b1998-11-01 14:50:06 +000035#include "mdi.h"
Alexandre Julliard401710d1993-09-04 10:09:32 +000036
Alexandre Julliard59730ae1996-03-24 16:20:51 +000037/* Desktop window */
38static WND *pWndDesktop = NULL;
39
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +000040static HWND32 hwndSysModal = 0;
Alexandre Julliard401710d1993-09-04 10:09:32 +000041
Alexandre Julliardd4719651995-12-12 18:49:11 +000042static WORD wDragWidth = 4;
43static WORD wDragHeight= 3;
Alexandre Julliardade697e1995-11-26 13:59:11 +000044
Alexandre Julliard401710d1993-09-04 10:09:32 +000045/***********************************************************************
46 * WIN_FindWndPtr
47 *
48 * Return a pointer to the WND structure corresponding to a HWND.
Alexandre Julliard401710d1993-09-04 10:09:32 +000049 */
Alexandre Julliardac9c9b01996-07-28 18:50:11 +000050WND * WIN_FindWndPtr( HWND32 hwnd )
Alexandre Julliard401710d1993-09-04 10:09:32 +000051{
52 WND * ptr;
53
Alexandre Julliardac9c9b01996-07-28 18:50:11 +000054 if (!hwnd || HIWORD(hwnd)) return NULL;
Alexandre Julliarde2abbb11995-03-19 17:39:39 +000055 ptr = (WND *) USER_HEAP_LIN_ADDR( hwnd );
Alexandre Julliardf0b23541993-09-29 12:21:49 +000056 if (ptr->dwMagic != WND_MAGIC) return NULL;
Alexandre Julliard59730ae1996-03-24 16:20:51 +000057 if (ptr->hwndSelf != hwnd)
58 {
Alexandre Julliarda845b881998-06-01 10:44:35 +000059 ERR( win, "Can't happen: hwnd %04x self pointer is %04x\n",
Alexandre Julliard59730ae1996-03-24 16:20:51 +000060 hwnd, ptr->hwndSelf );
61 return NULL;
62 }
Alexandre Julliard401710d1993-09-04 10:09:32 +000063 return ptr;
64}
65
66
67/***********************************************************************
Alexandre Julliardb817f4f1996-03-14 18:08:34 +000068 * WIN_DumpWindow
69 *
70 * Dump the content of a window structure to stderr.
71 */
Alexandre Julliardac9c9b01996-07-28 18:50:11 +000072void WIN_DumpWindow( HWND32 hwnd )
Alexandre Julliardb817f4f1996-03-14 18:08:34 +000073{
Alexandre Julliardb817f4f1996-03-14 18:08:34 +000074 WND *ptr;
75 char className[80];
76 int i;
77
78 if (!(ptr = WIN_FindWndPtr( hwnd )))
79 {
Alexandre Julliarda845b881998-06-01 10:44:35 +000080 WARN( win, "%04x is not a window handle\n", hwnd );
Alexandre Julliardb817f4f1996-03-14 18:08:34 +000081 return;
82 }
83
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +000084 if (!GetClassName32A( hwnd, className, sizeof(className ) ))
Alexandre Julliardb817f4f1996-03-14 18:08:34 +000085 strcpy( className, "#NULL#" );
86
Alexandre Julliarda845b881998-06-01 10:44:35 +000087 TRACE( win, "Window %04x (%p):\n", hwnd, ptr );
88 DUMP( "next=%p child=%p parent=%p owner=%p class=%p '%s'\n"
Alexandre Julliard670cdc41997-08-24 16:00:30 +000089 "inst=%04x taskQ=%04x updRgn=%04x active=%04x dce=%p idmenu=%08x\n"
Alexandre Julliard1e9ac791996-06-06 18:38:27 +000090 "style=%08lx exstyle=%08lx wndproc=%08x text='%s'\n"
Alexandre Julliard23946ad1997-06-16 17:43:53 +000091 "client=%d,%d-%d,%d window=%d,%d-%d,%d"
Alexandre Julliardac9c9b01996-07-28 18:50:11 +000092 "sysmenu=%04x flags=%04x props=%p vscroll=%p hscroll=%p\n",
Alexandre Julliard59730ae1996-03-24 16:20:51 +000093 ptr->next, ptr->child, ptr->parent, ptr->owner,
Alexandre Julliard2ace16a1996-04-28 15:09:19 +000094 ptr->class, className, ptr->hInstance, ptr->hmemTaskQ,
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +000095 ptr->hrgnUpdate, ptr->hwndLastActive, ptr->dce, ptr->wIDmenu,
Alexandre Julliard3051b641996-07-05 17:14:13 +000096 ptr->dwStyle, ptr->dwExStyle, (UINT32)ptr->winproc,
Alexandre Julliard2d93d001996-05-21 15:01:41 +000097 ptr->text ? ptr->text : "",
Alexandre Julliardb817f4f1996-03-14 18:08:34 +000098 ptr->rectClient.left, ptr->rectClient.top, ptr->rectClient.right,
99 ptr->rectClient.bottom, ptr->rectWindow.left, ptr->rectWindow.top,
Alexandre Julliard23946ad1997-06-16 17:43:53 +0000100 ptr->rectWindow.right, ptr->rectWindow.bottom, ptr->hSysMenu,
Alexandre Julliardac9c9b01996-07-28 18:50:11 +0000101 ptr->flags, ptr->pProp, ptr->pVScroll, ptr->pHScroll );
Alexandre Julliardb817f4f1996-03-14 18:08:34 +0000102
Alexandre Julliard1285c2f1996-05-06 16:06:24 +0000103 if (ptr->class->cbWndExtra)
Alexandre Julliardb817f4f1996-03-14 18:08:34 +0000104 {
Alexandre Julliarda845b881998-06-01 10:44:35 +0000105 DUMP( "extra bytes:" );
Alexandre Julliard1285c2f1996-05-06 16:06:24 +0000106 for (i = 0; i < ptr->class->cbWndExtra; i++)
Alexandre Julliarda845b881998-06-01 10:44:35 +0000107 DUMP( " %02x", *((BYTE*)ptr->wExtra+i) );
108 DUMP( "\n" );
Alexandre Julliardb817f4f1996-03-14 18:08:34 +0000109 }
Alexandre Julliarda845b881998-06-01 10:44:35 +0000110 DUMP( "\n" );
Alexandre Julliardb817f4f1996-03-14 18:08:34 +0000111}
112
113
114/***********************************************************************
115 * WIN_WalkWindows
116 *
117 * Walk the windows tree and print each window on stderr.
118 */
Alexandre Julliardac9c9b01996-07-28 18:50:11 +0000119void WIN_WalkWindows( HWND32 hwnd, int indent )
Alexandre Julliardb817f4f1996-03-14 18:08:34 +0000120{
121 WND *ptr;
Alexandre Julliardb817f4f1996-03-14 18:08:34 +0000122 char className[80];
123
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000124 ptr = hwnd ? WIN_FindWndPtr( hwnd ) : pWndDesktop;
125 if (!ptr)
126 {
Alexandre Julliarda845b881998-06-01 10:44:35 +0000127 WARN( win, "Invalid window handle %04x\n", hwnd );
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000128 return;
129 }
130
Alexandre Julliardb817f4f1996-03-14 18:08:34 +0000131 if (!indent) /* first time around */
Alexandre Julliarda845b881998-06-01 10:44:35 +0000132 DUMP( "%-16.16s %-8.8s %-6.6s %-17.17s %-8.8s %s\n",
Rein Klazesd62c62b1998-10-11 14:05:34 +0000133 "hwnd", " wndPtr", "queue", "Class Name", " Style", " WndProc"
134 " Text");
Alexandre Julliardb817f4f1996-03-14 18:08:34 +0000135
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000136 while (ptr)
Alexandre Julliardb817f4f1996-03-14 18:08:34 +0000137 {
Alexandre Julliarda845b881998-06-01 10:44:35 +0000138 DUMP( "%*s%04x%*s", indent, "", ptr->hwndSelf, 13-indent,"");
Alexandre Julliard2ace16a1996-04-28 15:09:19 +0000139
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000140 GlobalGetAtomName16(ptr->class->atomName,className,sizeof(className));
Alexandre Julliardb817f4f1996-03-14 18:08:34 +0000141
Rein Klazesd62c62b1998-10-11 14:05:34 +0000142 DUMP( "%08lx %-6.4x %-17.17s %08x %08x %.14s\n",
Alexandre Julliardb817f4f1996-03-14 18:08:34 +0000143 (DWORD)ptr, ptr->hmemTaskQ, className,
Rein Klazesd62c62b1998-10-11 14:05:34 +0000144 (UINT32)ptr->dwStyle, (UINT32)ptr->winproc,
145 ptr->text?ptr->text:"<null>");
Alexandre Julliardb817f4f1996-03-14 18:08:34 +0000146
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000147 if (ptr->child) WIN_WalkWindows( ptr->child->hwndSelf, indent+1 );
148 ptr = ptr->next;
Alexandre Julliardb817f4f1996-03-14 18:08:34 +0000149 }
150}
151
152
153/***********************************************************************
Alexandre Julliardaca05781994-10-17 18:12:41 +0000154 * WIN_GetXWindow
155 *
156 * Return the X window associated to a window.
157 */
Alexandre Julliardac9c9b01996-07-28 18:50:11 +0000158Window WIN_GetXWindow( HWND32 hwnd )
Alexandre Julliardaca05781994-10-17 18:12:41 +0000159{
160 WND *wndPtr = WIN_FindWndPtr( hwnd );
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000161 while (wndPtr && !wndPtr->window) wndPtr = wndPtr->parent;
Alexandre Julliardaca05781994-10-17 18:12:41 +0000162 return wndPtr ? wndPtr->window : 0;
163}
164
165
166/***********************************************************************
Alexandre Julliard5f721f81994-01-04 20:14:34 +0000167 * WIN_UnlinkWindow
168 *
169 * Remove a window from the siblings linked list.
170 */
Alexandre Julliardac9c9b01996-07-28 18:50:11 +0000171BOOL32 WIN_UnlinkWindow( HWND32 hwnd )
Alexandre Julliard5f721f81994-01-04 20:14:34 +0000172{
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000173 WND *wndPtr, **ppWnd;
Alexandre Julliard5f721f81994-01-04 20:14:34 +0000174
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000175 if (!(wndPtr = WIN_FindWndPtr( hwnd )) || !wndPtr->parent) return FALSE;
176 ppWnd = &wndPtr->parent->child;
177 while (*ppWnd != wndPtr) ppWnd = &(*ppWnd)->next;
178 *ppWnd = wndPtr->next;
Alexandre Julliard5f721f81994-01-04 20:14:34 +0000179 return TRUE;
180}
181
182
183/***********************************************************************
184 * WIN_LinkWindow
185 *
186 * Insert a window into the siblings linked list.
187 * The window is inserted after the specified window, which can also
188 * be specified as HWND_TOP or HWND_BOTTOM.
189 */
Alexandre Julliardac9c9b01996-07-28 18:50:11 +0000190BOOL32 WIN_LinkWindow( HWND32 hwnd, HWND32 hwndInsertAfter )
Alexandre Julliard5f721f81994-01-04 20:14:34 +0000191{
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000192 WND *wndPtr, **ppWnd;
Alexandre Julliard5f721f81994-01-04 20:14:34 +0000193
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000194 if (!(wndPtr = WIN_FindWndPtr( hwnd )) || !wndPtr->parent) return FALSE;
Alexandre Julliardfb9a9191994-03-01 19:48:04 +0000195
Alexandre Julliard5f721f81994-01-04 20:14:34 +0000196 if ((hwndInsertAfter == HWND_TOP) || (hwndInsertAfter == HWND_BOTTOM))
197 {
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000198 ppWnd = &wndPtr->parent->child; /* Point to first sibling hwnd */
Alexandre Julliard5f721f81994-01-04 20:14:34 +0000199 if (hwndInsertAfter == HWND_BOTTOM) /* Find last sibling hwnd */
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000200 while (*ppWnd) ppWnd = &(*ppWnd)->next;
Alexandre Julliard5f721f81994-01-04 20:14:34 +0000201 }
202 else /* Normal case */
203 {
204 WND * afterPtr = WIN_FindWndPtr( hwndInsertAfter );
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000205 if (!afterPtr) return FALSE;
206 ppWnd = &afterPtr->next;
Alexandre Julliard5f721f81994-01-04 20:14:34 +0000207 }
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000208 wndPtr->next = *ppWnd;
209 *ppWnd = wndPtr;
Alexandre Julliard5f721f81994-01-04 20:14:34 +0000210 return TRUE;
211}
212
213
214/***********************************************************************
Alexandre Julliard401710d1993-09-04 10:09:32 +0000215 * WIN_FindWinToRepaint
216 *
217 * Find a window that needs repaint.
218 */
Alexandre Julliardac9c9b01996-07-28 18:50:11 +0000219HWND32 WIN_FindWinToRepaint( HWND32 hwnd, HQUEUE16 hQueue )
Alexandre Julliard401710d1993-09-04 10:09:32 +0000220{
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000221 HWND32 hwndRet;
Alexandre Julliardc981d0b1996-03-31 16:40:13 +0000222 WND *pWnd = pWndDesktop;
Alexandre Julliard8d24ae61994-04-05 21:42:43 +0000223
Alexandre Julliard1e37a181996-08-18 16:21:52 +0000224 /* Note: the desktop window never gets WM_PAINT messages
225 * The real reason why is because Windows DesktopWndProc
226 * does ValidateRgn inside WM_ERASEBKGND handler.
227 */
228
Alexandre Julliardc981d0b1996-03-31 16:40:13 +0000229 pWnd = hwnd ? WIN_FindWndPtr( hwnd ) : pWndDesktop->child;
230
231 for ( ; pWnd ; pWnd = pWnd->next )
Alexandre Julliard401710d1993-09-04 10:09:32 +0000232 {
Alexandre Julliarde658d821997-11-30 17:45:40 +0000233 if (!(pWnd->dwStyle & WS_VISIBLE))
Alexandre Julliardc981d0b1996-03-31 16:40:13 +0000234 {
Alexandre Julliarda69b88b1998-03-15 20:29:56 +0000235 TRACE(win, "skipping window %04x\n",
Alexandre Julliardc981d0b1996-03-31 16:40:13 +0000236 pWnd->hwndSelf );
Alexandre Julliardaca05781994-10-17 18:12:41 +0000237 continue;
Alexandre Julliardc981d0b1996-03-31 16:40:13 +0000238 }
239 if ((pWnd->hmemTaskQ == hQueue) &&
240 (pWnd->hrgnUpdate || (pWnd->flags & WIN_INTERNAL_PAINT))) break;
241
242 if (pWnd->child )
243 if ((hwndRet = WIN_FindWinToRepaint( pWnd->child->hwndSelf, hQueue )) )
244 return hwndRet;
Alexandre Julliard401710d1993-09-04 10:09:32 +0000245 }
Alexandre Julliardc981d0b1996-03-31 16:40:13 +0000246
247 if (!pWnd) return 0;
248
249 hwndRet = pWnd->hwndSelf;
250
251 /* look among siblings if we got a transparent window */
252 while (pWnd && ((pWnd->dwExStyle & WS_EX_TRANSPARENT) ||
253 !(pWnd->hrgnUpdate || (pWnd->flags & WIN_INTERNAL_PAINT))))
254 {
255 pWnd = pWnd->next;
256 }
257 if (pWnd) hwndRet = pWnd->hwndSelf;
Alexandre Julliarda69b88b1998-03-15 20:29:56 +0000258 TRACE(win,"found %04x\n",hwndRet);
Alexandre Julliardc981d0b1996-03-31 16:40:13 +0000259 return hwndRet;
Alexandre Julliard401710d1993-09-04 10:09:32 +0000260}
261
262
263/***********************************************************************
Alexandre Julliardaca05781994-10-17 18:12:41 +0000264 * WIN_DestroyWindow
265 *
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000266 * Destroy storage associated to a window. "Internals" p.358
Alexandre Julliardaca05781994-10-17 18:12:41 +0000267 */
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000268static WND* WIN_DestroyWindow( WND* wndPtr )
Alexandre Julliardaca05781994-10-17 18:12:41 +0000269{
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000270 HWND32 hwnd = wndPtr->hwndSelf;
Alexandre Julliard349a9531997-02-02 19:01:52 +0000271 WND *pWnd;
Alexandre Julliardaca05781994-10-17 18:12:41 +0000272
Alexandre Julliarda69b88b1998-03-15 20:29:56 +0000273 TRACE(win, "%04x\n", wndPtr->hwndSelf );
Alexandre Julliard75d86e11996-11-17 18:59:11 +0000274
Alexandre Julliardb7258be1995-09-01 15:57:28 +0000275#ifdef CONFIG_IPC
Alexandre Julliarde2991ea1995-07-29 13:09:43 +0000276 if (main_block)
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000277 DDE_DestroyWindow(wndPtr->hwndSelf);
Alexandre Julliardb7258be1995-09-01 15:57:28 +0000278#endif /* CONFIG_IPC */
Alexandre Julliarde2991ea1995-07-29 13:09:43 +0000279
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000280 /* free child windows */
281
Alexandre Julliard349a9531997-02-02 19:01:52 +0000282 while ((pWnd = wndPtr->child))
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000283 wndPtr->child = WIN_DestroyWindow( pWnd );
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000284
285 SendMessage32A( wndPtr->hwndSelf, WM_NCDESTROY, 0, 0);
286
287 /* FIXME: do we need to fake QS_MOUSEMOVE wakebit? */
288
Alexandre Julliard23946ad1997-06-16 17:43:53 +0000289 WINPOS_CheckInternalPos( hwnd );
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000290 if( hwnd == GetCapture32()) ReleaseCapture();
291
292 /* free resources associated with the window */
293
294 TIMER_RemoveWindowTimers( wndPtr->hwndSelf );
Alexandre Julliardac9c9b01996-07-28 18:50:11 +0000295 PROPERTY_RemoveWindowProps( wndPtr );
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000296
Alexandre Julliardaca05781994-10-17 18:12:41 +0000297 wndPtr->dwMagic = 0; /* Mark it as invalid */
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000298
Alexandre Julliardaca05781994-10-17 18:12:41 +0000299 if ((wndPtr->hrgnUpdate) || (wndPtr->flags & WIN_INTERNAL_PAINT))
300 {
Alexandre Julliard491502b1997-11-01 19:08:16 +0000301 if (wndPtr->hrgnUpdate > 1) DeleteObject32( wndPtr->hrgnUpdate );
Alexandre Julliardb817f4f1996-03-14 18:08:34 +0000302 QUEUE_DecPaintCount( wndPtr->hmemTaskQ );
Alexandre Julliardaca05781994-10-17 18:12:41 +0000303 }
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000304
305 /* toss stale messages from the queue */
306
307 if( wndPtr->hmemTaskQ )
Alexandre Julliardaca05781994-10-17 18:12:41 +0000308 {
Alexandre Julliard491502b1997-11-01 19:08:16 +0000309 int pos;
310 BOOL32 bPostQuit = FALSE;
311 WPARAM32 wQuitParam = 0;
312 MESSAGEQUEUE* msgQ = (MESSAGEQUEUE*) GlobalLock16(wndPtr->hmemTaskQ);
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000313
Alexandre Julliard491502b1997-11-01 19:08:16 +0000314 while( (pos = QUEUE_FindMsg(msgQ, hwnd, 0, 0)) != -1 )
315 {
316 if( msgQ->messages[pos].msg.message == WM_QUIT )
317 {
318 bPostQuit = TRUE;
319 wQuitParam = msgQ->messages[pos].msg.wParam;
320 }
321 QUEUE_RemoveMsg(msgQ, pos);
322 }
Alexandre Julliarda0b2b1d1997-11-16 17:38:29 +0000323 /* repost WM_QUIT to make sure this app exits its message loop */
Alexandre Julliard491502b1997-11-01 19:08:16 +0000324 if( bPostQuit ) PostQuitMessage32(wQuitParam);
325 wndPtr->hmemTaskQ = 0;
Alexandre Julliardaca05781994-10-17 18:12:41 +0000326 }
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000327
328 if (!(wndPtr->dwStyle & WS_CHILD))
Alexandre Julliardc6c09441997-01-12 18:32:19 +0000329 if (wndPtr->wIDmenu) DestroyMenu32( (HMENU32)wndPtr->wIDmenu );
330 if (wndPtr->hSysMenu) DestroyMenu32( wndPtr->hSysMenu );
Alexandre Julliard7ebe1a41996-12-22 18:27:48 +0000331 if (wndPtr->window) EVENT_DestroyWindow( wndPtr );
Alexandre Julliard85ed45e1998-08-22 19:03:56 +0000332 DCE_FreeWindowDCE( wndPtr ); /* Always do this to catch orphaned DCs */
Alexandre Julliarddf2673b1997-03-29 17:20:20 +0000333 WINPROC_FreeProc( wndPtr->winproc, WIN_PROC_WINDOW );
Alexandre Julliard85ed45e1998-08-22 19:03:56 +0000334 wndPtr->hwndSelf = 0;
Alexandre Julliard2ace16a1996-04-28 15:09:19 +0000335 wndPtr->class->cWindows--;
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000336 wndPtr->class = NULL;
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000337 pWnd = wndPtr->next;
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000338
Alexandre Julliardaca05781994-10-17 18:12:41 +0000339 USER_HEAP_FREE( hwnd );
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000340 return pWnd;
Alexandre Julliardaca05781994-10-17 18:12:41 +0000341}
342
Alexandre Julliardaca05781994-10-17 18:12:41 +0000343/***********************************************************************
Alexandre Julliardda0cfb31996-12-01 17:17:47 +0000344 * WIN_ResetQueueWindows
Alexandre Julliard77b99181997-09-14 17:17:23 +0000345 *
346 * Reset the queue of all the children of a given window.
347 * Return TRUE if something was done.
Alexandre Julliard2ace16a1996-04-28 15:09:19 +0000348 */
Alexandre Julliard77b99181997-09-14 17:17:23 +0000349BOOL32 WIN_ResetQueueWindows( WND* wnd, HQUEUE16 hQueue, HQUEUE16 hNew )
Alexandre Julliard2ace16a1996-04-28 15:09:19 +0000350{
Alexandre Julliard77b99181997-09-14 17:17:23 +0000351 BOOL32 ret = FALSE;
Alexandre Julliard2ace16a1996-04-28 15:09:19 +0000352
Alexandre Julliard77b99181997-09-14 17:17:23 +0000353 if (hNew) /* Set a new queue */
Alexandre Julliard2ace16a1996-04-28 15:09:19 +0000354 {
Alexandre Julliard77b99181997-09-14 17:17:23 +0000355 for (wnd = wnd->child; (wnd); wnd = wnd->next)
356 {
357 if (wnd->hmemTaskQ == hQueue)
358 {
359 wnd->hmemTaskQ = hNew;
360 ret = TRUE;
361 }
362 if (wnd->child)
363 ret |= WIN_ResetQueueWindows( wnd->child, hQueue, hNew );
364 }
Alexandre Julliard2ace16a1996-04-28 15:09:19 +0000365 }
Alexandre Julliard77b99181997-09-14 17:17:23 +0000366 else /* Queue is being destroyed */
367 {
368 while (wnd->child)
369 {
370 WND *tmp = wnd->child;
371 ret = FALSE;
372 while (tmp)
373 {
374 if (tmp->hmemTaskQ == hQueue)
375 {
376 DestroyWindow32( tmp->hwndSelf );
377 ret = TRUE;
378 break;
379 }
380 if (tmp->child && WIN_ResetQueueWindows(tmp->child,hQueue,0))
381 ret = TRUE;
382 else
383 tmp = tmp->next;
384 }
385 if (!ret) break;
386 }
387 }
388 return ret;
Alexandre Julliard2ace16a1996-04-28 15:09:19 +0000389}
390
Alexandre Julliard2ace16a1996-04-28 15:09:19 +0000391/***********************************************************************
Alexandre Julliardfb9a9191994-03-01 19:48:04 +0000392 * WIN_CreateDesktopWindow
393 *
394 * Create the desktop window.
395 */
Alexandre Julliardac9c9b01996-07-28 18:50:11 +0000396BOOL32 WIN_CreateDesktopWindow(void)
Alexandre Julliardfb9a9191994-03-01 19:48:04 +0000397{
Alexandre Julliard2ace16a1996-04-28 15:09:19 +0000398 CLASS *class;
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000399 HWND32 hwndDesktop;
Alexandre Julliardfb9a9191994-03-01 19:48:04 +0000400
Alexandre Julliarda69b88b1998-03-15 20:29:56 +0000401 TRACE(win,"Creating desktop window\n");
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000402
Alexandre Julliard23946ad1997-06-16 17:43:53 +0000403 if (!ICONTITLE_Init() ||
404 !WINPOS_CreateInternalPosAtom() ||
405 !(class = CLASS_FindClassByAtom( DESKTOP_CLASS_ATOM, 0 )))
Alexandre Julliard8d24ae61994-04-05 21:42:43 +0000406 return FALSE;
Alexandre Julliardfb9a9191994-03-01 19:48:04 +0000407
Alexandre Julliard1285c2f1996-05-06 16:06:24 +0000408 hwndDesktop = USER_HEAP_ALLOC( sizeof(WND)+class->cbWndExtra );
Alexandre Julliard8d24ae61994-04-05 21:42:43 +0000409 if (!hwndDesktop) return FALSE;
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000410 pWndDesktop = (WND *) USER_HEAP_LIN_ADDR( hwndDesktop );
Alexandre Julliardfb9a9191994-03-01 19:48:04 +0000411
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000412 pWndDesktop->next = NULL;
413 pWndDesktop->child = NULL;
414 pWndDesktop->parent = NULL;
415 pWndDesktop->owner = NULL;
Alexandre Julliard2ace16a1996-04-28 15:09:19 +0000416 pWndDesktop->class = class;
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000417 pWndDesktop->dwMagic = WND_MAGIC;
418 pWndDesktop->hwndSelf = hwndDesktop;
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000419 pWndDesktop->hInstance = 0;
420 pWndDesktop->rectWindow.left = 0;
421 pWndDesktop->rectWindow.top = 0;
422 pWndDesktop->rectWindow.right = SYSMETRICS_CXSCREEN;
423 pWndDesktop->rectWindow.bottom = SYSMETRICS_CYSCREEN;
424 pWndDesktop->rectClient = pWndDesktop->rectWindow;
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000425 pWndDesktop->text = NULL;
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000426 pWndDesktop->hmemTaskQ = 0; /* Desktop does not belong to a task */
427 pWndDesktop->hrgnUpdate = 0;
428 pWndDesktop->hwndLastActive = hwndDesktop;
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000429 pWndDesktop->dwStyle = WS_VISIBLE | WS_CLIPCHILDREN |
430 WS_CLIPSIBLINGS;
431 pWndDesktop->dwExStyle = 0;
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000432 pWndDesktop->dce = NULL;
Alexandre Julliardca22b331996-07-12 19:02:39 +0000433 pWndDesktop->pVScroll = NULL;
434 pWndDesktop->pHScroll = NULL;
Alexandre Julliardac9c9b01996-07-28 18:50:11 +0000435 pWndDesktop->pProp = NULL;
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000436 pWndDesktop->wIDmenu = 0;
Alexandre Julliardc7c217b1998-04-13 12:21:30 +0000437 pWndDesktop->helpContext = 0;
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000438 pWndDesktop->flags = 0;
439 pWndDesktop->window = rootWindow;
440 pWndDesktop->hSysMenu = 0;
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000441 pWndDesktop->userdata = 0;
442
Alexandre Julliarddf2673b1997-03-29 17:20:20 +0000443 pWndDesktop->winproc = (WNDPROC16)class->winproc;
444
Alexandre Julliard8b915631996-06-16 16:16:05 +0000445 EVENT_RegisterWindow( pWndDesktop );
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000446 SendMessage32A( hwndDesktop, WM_NCCREATE, 0, 0 );
Alexandre Julliard1e37a181996-08-18 16:21:52 +0000447 pWndDesktop->flags |= WIN_NEEDS_ERASEBKGND;
Alexandre Julliard8d24ae61994-04-05 21:42:43 +0000448 return TRUE;
Alexandre Julliardfb9a9191994-03-01 19:48:04 +0000449}
450
451
452/***********************************************************************
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000453 * WIN_CreateWindowEx
454 *
455 * Implementation of CreateWindowEx().
Alexandre Julliard401710d1993-09-04 10:09:32 +0000456 */
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000457static HWND32 WIN_CreateWindowEx( CREATESTRUCT32A *cs, ATOM classAtom,
458 BOOL32 win32, BOOL32 unicode )
Alexandre Julliard401710d1993-09-04 10:09:32 +0000459{
Alexandre Julliard401710d1993-09-04 10:09:32 +0000460 CLASS *classPtr;
Alexandre Julliardd2e1c1a1996-03-09 16:12:43 +0000461 WND *wndPtr;
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000462 HWND16 hwnd, hwndLinkAfter;
Alexandre Julliardd37eb361997-07-20 16:23:21 +0000463 POINT32 maxSize, maxPos, minTrack, maxTrack;
Alexandre Julliard767e6f61998-08-09 12:47:43 +0000464 LRESULT (CALLBACK *localSend32)(HWND32, UINT32, WPARAM32, LPARAM);
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000465
Alexandre Julliard767e6f61998-08-09 12:47:43 +0000466 TRACE(win, "%s %s %08lx %08lx %d,%d %dx%d %04x %04x %08x %p\n",
467 unicode ? debugres_w((LPWSTR)cs->lpszName) : debugres_a(cs->lpszName),
468 unicode ? debugres_w((LPWSTR)cs->lpszClass) : debugres_a(cs->lpszClass),
469 cs->dwExStyle, cs->style, cs->x, cs->y, cs->cx, cs->cy,
470 cs->hwndParent, cs->hMenu, cs->hInstance, cs->lpCreateParams );
Alexandre Julliard401710d1993-09-04 10:09:32 +0000471
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000472 /* Find the parent window */
Alexandre Julliard401710d1993-09-04 10:09:32 +0000473
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000474 if (cs->hwndParent)
Alexandre Julliard401710d1993-09-04 10:09:32 +0000475 {
Alexandre Julliardbd34d4f1995-06-20 19:08:12 +0000476 /* Make sure parent is valid */
Alexandre Julliard21979011997-03-05 08:22:35 +0000477 if (!IsWindow32( cs->hwndParent ))
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000478 {
Alexandre Julliarda845b881998-06-01 10:44:35 +0000479 WARN( win, "Bad parent %04x\n", cs->hwndParent );
Alexandre Julliardbd34d4f1995-06-20 19:08:12 +0000480 return 0;
Alexandre Julliardfa68b751995-04-03 16:55:37 +0000481 }
Alexandre Julliard3db94ef1997-09-28 17:43:24 +0000482 } else if ((cs->style & WS_CHILD) && !(cs->style & WS_POPUP)) {
Alexandre Julliarda845b881998-06-01 10:44:35 +0000483 WARN( win, "No parent for child window\n" );
Alexandre Julliard3db94ef1997-09-28 17:43:24 +0000484 return 0; /* WS_CHILD needs a parent, but WS_POPUP doesn't */
Alexandre Julliardbd34d4f1995-06-20 19:08:12 +0000485 }
Alexandre Julliard8d24ae61994-04-05 21:42:43 +0000486
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000487 /* Find the window class */
Alexandre Julliard77b99181997-09-14 17:17:23 +0000488 if (!(classPtr = CLASS_FindClassByAtom( classAtom, win32?cs->hInstance:GetExePtr(cs->hInstance) )))
Alexandre Julliard808cb041995-08-17 17:11:36 +0000489 {
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000490 char buffer[256];
491 GlobalGetAtomName32A( classAtom, buffer, sizeof(buffer) );
Alexandre Julliarda845b881998-06-01 10:44:35 +0000492 WARN( win, "Bad class '%s'\n", buffer );
Alexandre Julliardff8331e1995-09-18 11:19:54 +0000493 return 0;
Alexandre Julliardbd34d4f1995-06-20 19:08:12 +0000494 }
Alexandre Julliardcdd09231994-01-12 11:12:51 +0000495
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000496 /* Fix the coordinates */
Alexandre Julliardcdd09231994-01-12 11:12:51 +0000497
Alexandre Julliard85ed45e1998-08-22 19:03:56 +0000498 if (cs->x == CW_USEDEFAULT32)
499 {
500 PDB32 *pdb = PROCESS_Current();
501 if ( !(cs->style & (WS_CHILD | WS_POPUP))
502 && (pdb->env_db->startup_info->dwFlags & STARTF_USEPOSITION) )
503 {
504 cs->x = pdb->env_db->startup_info->dwX;
505 cs->y = pdb->env_db->startup_info->dwY;
506 }
507 else
508 {
509 cs->x = 0;
510 cs->y = 0;
511 }
512 }
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000513 if (cs->cx == CW_USEDEFAULT32)
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000514 {
Alexandre Julliard85ed45e1998-08-22 19:03:56 +0000515 PDB32 *pdb = PROCESS_Current();
516 if ( !(cs->style & (WS_CHILD | WS_POPUP))
517 && (pdb->env_db->startup_info->dwFlags & STARTF_USESIZE) )
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000518 {
Alexandre Julliard85ed45e1998-08-22 19:03:56 +0000519 cs->cx = pdb->env_db->startup_info->dwXSize;
520 cs->cy = pdb->env_db->startup_info->dwYSize;
521 }
522 else
523 {
524 cs->cx = 600; /* FIXME */
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000525 cs->cy = 400;
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000526 }
527 }
Alexandre Julliardcdd09231994-01-12 11:12:51 +0000528
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000529 /* Create the window structure */
Alexandre Julliard401710d1993-09-04 10:09:32 +0000530
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000531 if (!(hwnd = USER_HEAP_ALLOC( sizeof(*wndPtr) + classPtr->cbWndExtra
532 - sizeof(wndPtr->wExtra) )))
533 {
Alexandre Julliarda69b88b1998-03-15 20:29:56 +0000534 TRACE(win, "out of memory\n" );
Alexandre Julliardbd34d4f1995-06-20 19:08:12 +0000535 return 0;
536 }
Alexandre Julliard401710d1993-09-04 10:09:32 +0000537
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000538 /* Fill the window structure */
Alexandre Julliard401710d1993-09-04 10:09:32 +0000539
Alexandre Julliarde2abbb11995-03-19 17:39:39 +0000540 wndPtr = (WND *) USER_HEAP_LIN_ADDR( hwnd );
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000541 wndPtr->next = NULL;
542 wndPtr->child = NULL;
543
Alexandre Julliard3db94ef1997-09-28 17:43:24 +0000544 if ((cs->style & WS_CHILD) && cs->hwndParent)
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000545 {
546 wndPtr->parent = WIN_FindWndPtr( cs->hwndParent );
547 wndPtr->owner = NULL;
548 }
549 else
550 {
551 wndPtr->parent = pWndDesktop;
552 if (!cs->hwndParent || (cs->hwndParent == pWndDesktop->hwndSelf))
553 wndPtr->owner = NULL;
554 else
Alexandre Julliard670cdc41997-08-24 16:00:30 +0000555 wndPtr->owner = WIN_GetTopParentPtr(WIN_FindWndPtr(cs->hwndParent));
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000556 }
557
Alexandre Julliardbd34d4f1995-06-20 19:08:12 +0000558 wndPtr->window = 0;
Alexandre Julliard2ace16a1996-04-28 15:09:19 +0000559 wndPtr->class = classPtr;
Alexandre Julliarddf2673b1997-03-29 17:20:20 +0000560 wndPtr->winproc = classPtr->winproc;
Alexandre Julliardbd34d4f1995-06-20 19:08:12 +0000561 wndPtr->dwMagic = WND_MAGIC;
Alexandre Julliard59730ae1996-03-24 16:20:51 +0000562 wndPtr->hwndSelf = hwnd;
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000563 wndPtr->hInstance = cs->hInstance;
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000564 wndPtr->text = NULL;
Alexandre Julliardbd34d4f1995-06-20 19:08:12 +0000565 wndPtr->hmemTaskQ = GetTaskQueue(0);
566 wndPtr->hrgnUpdate = 0;
Alexandre Julliardbd34d4f1995-06-20 19:08:12 +0000567 wndPtr->hwndLastActive = hwnd;
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000568 wndPtr->dwStyle = cs->style & ~WS_VISIBLE;
569 wndPtr->dwExStyle = cs->dwExStyle;
Alexandre Julliardbd34d4f1995-06-20 19:08:12 +0000570 wndPtr->wIDmenu = 0;
Alexandre Julliardc7c217b1998-04-13 12:21:30 +0000571 wndPtr->helpContext = 0;
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000572 wndPtr->flags = win32 ? WIN_ISWIN32 : 0;
Alexandre Julliardca22b331996-07-12 19:02:39 +0000573 wndPtr->pVScroll = NULL;
574 wndPtr->pHScroll = NULL;
Alexandre Julliardac9c9b01996-07-28 18:50:11 +0000575 wndPtr->pProp = NULL;
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000576 wndPtr->userdata = 0;
Alexandre Julliard7ff1c411997-05-25 13:58:18 +0000577 wndPtr->hSysMenu = (wndPtr->dwStyle & WS_SYSMENU)
578 ? MENU_GetSysMenu( hwnd, 0 ) : 0;
Alexandre Julliardf0b23541993-09-29 12:21:49 +0000579
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000580 if (classPtr->cbWndExtra) memset( wndPtr->wExtra, 0, classPtr->cbWndExtra);
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000581
582 /* Call the WH_CBT hook */
583
584 hwndLinkAfter = (cs->style & WS_CHILD) ? HWND_BOTTOM : HWND_TOP;
585
Alexandre Julliard7e6ae4b1996-12-08 19:25:27 +0000586 if (HOOK_IsHooked( WH_CBT ))
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000587 {
Alexandre Julliard7e6ae4b1996-12-08 19:25:27 +0000588 CBT_CREATEWND32A cbtc;
Alexandre Julliard767e6f61998-08-09 12:47:43 +0000589 LRESULT ret;
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000590
Alexandre Julliard7e6ae4b1996-12-08 19:25:27 +0000591 cbtc.lpcs = cs;
592 cbtc.hwndInsertAfter = hwndLinkAfter;
Alexandre Julliard767e6f61998-08-09 12:47:43 +0000593 ret = unicode ? HOOK_CallHooks32W(WH_CBT, HCBT_CREATEWND, hwnd, (LPARAM)&cbtc)
594 : HOOK_CallHooks32A(WH_CBT, HCBT_CREATEWND, hwnd, (LPARAM)&cbtc);
595 if (ret)
Alexandre Julliard7e6ae4b1996-12-08 19:25:27 +0000596 {
Alexandre Julliarda69b88b1998-03-15 20:29:56 +0000597 TRACE(win, "CBT-hook returned 0\n");
Alexandre Julliard7e6ae4b1996-12-08 19:25:27 +0000598 USER_HEAP_FREE( hwnd );
599 return 0;
600 }
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000601 }
Alexandre Julliard401710d1993-09-04 10:09:32 +0000602
Alexandre Julliarddf2673b1997-03-29 17:20:20 +0000603 /* Increment class window counter */
Alexandre Julliard3051b641996-07-05 17:14:13 +0000604
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000605 classPtr->cWindows++;
Alexandre Julliard3051b641996-07-05 17:14:13 +0000606
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000607 /* Correct the window style */
608
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000609 if (!(cs->style & (WS_POPUP | WS_CHILD))) /* Overlapped window */
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000610 {
611 wndPtr->dwStyle |= WS_CAPTION | WS_CLIPSIBLINGS;
612 wndPtr->flags |= WIN_NEED_SIZE;
613 }
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000614 if (cs->dwExStyle & WS_EX_DLGMODALFRAME) wndPtr->dwStyle &= ~WS_THICKFRAME;
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000615
616 /* Get class or window DC if needed */
Alexandre Julliardaca05781994-10-17 18:12:41 +0000617
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000618 if (classPtr->style & CS_OWNDC) wndPtr->dce = DCE_AllocDCE(hwnd,DCE_WINDOW_DC);
619 else if (classPtr->style & CS_CLASSDC) wndPtr->dce = classPtr->dce;
620 else wndPtr->dce = NULL;
Alexandre Julliard5f721f81994-01-04 20:14:34 +0000621
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000622 /* Send the WM_GETMINMAXINFO message and fix the size if needed */
Alexandre Julliard988ca971994-06-21 16:15:21 +0000623
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000624 if ((cs->style & WS_THICKFRAME) || !(cs->style & (WS_POPUP | WS_CHILD)))
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000625 {
Alexandre Julliardd37eb361997-07-20 16:23:21 +0000626 WINPOS_GetMinMaxInfo( wndPtr, &maxSize, &maxPos, &minTrack, &maxTrack);
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000627 if (maxSize.x < cs->cx) cs->cx = maxSize.x;
628 if (maxSize.y < cs->cy) cs->cy = maxSize.y;
Alexandre Julliardac9c9b01996-07-28 18:50:11 +0000629 if (cs->cx < minTrack.x ) cs->cx = minTrack.x;
630 if (cs->cy < minTrack.y ) cs->cy = minTrack.y;
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000631 }
Alexandre Julliard44ed71f1997-12-21 19:17:50 +0000632
633 if(cs->style & WS_CHILD)
634 {
635 if(cs->cx < 0) cs->cx = 0;
636 if(cs->cy < 0) cs->cy = 0;
637 }
638 else
639 {
640 if (cs->cx <= 0) cs->cx = 1;
641 if (cs->cy <= 0) cs->cy = 1;
642 }
Alexandre Julliardbd34d4f1995-06-20 19:08:12 +0000643
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000644 wndPtr->rectWindow.left = cs->x;
645 wndPtr->rectWindow.top = cs->y;
646 wndPtr->rectWindow.right = cs->x + cs->cx;
647 wndPtr->rectWindow.bottom = cs->y + cs->cy;
Alexandre Julliardbd34d4f1995-06-20 19:08:12 +0000648 wndPtr->rectClient = wndPtr->rectWindow;
Alexandre Julliard940d58c1994-09-16 09:24:37 +0000649
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000650 /* Create the X window (only for top-level windows, and then only */
651 /* when there's no desktop window) */
Alexandre Julliard0e607781993-11-03 19:23:37 +0000652
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000653 if (!(cs->style & WS_CHILD) && (rootWindow == DefaultRootWindow(display)))
Alexandre Julliardaca05781994-10-17 18:12:41 +0000654 {
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000655 XSetWindowAttributes win_attr;
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000656
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000657 if (Options.managed && ((cs->style & (WS_DLGFRAME | WS_THICKFRAME)) ||
658 (cs->dwExStyle & WS_EX_DLGMODALFRAME)))
Alexandre Julliard0c126c71996-02-18 18:44:41 +0000659 {
Alexandre Julliardd4719651995-12-12 18:49:11 +0000660 win_attr.event_mask = ExposureMask | KeyPressMask |
661 KeyReleaseMask | PointerMotionMask |
662 ButtonPressMask | ButtonReleaseMask |
663 FocusChangeMask | StructureNotifyMask;
664 win_attr.override_redirect = FALSE;
Alexandre Julliard0c126c71996-02-18 18:44:41 +0000665 wndPtr->flags |= WIN_MANAGED;
Alexandre Julliardd4719651995-12-12 18:49:11 +0000666 }
Alexandre Julliard0c126c71996-02-18 18:44:41 +0000667 else
668 {
Alexandre Julliardd4719651995-12-12 18:49:11 +0000669 win_attr.event_mask = ExposureMask | KeyPressMask |
670 KeyReleaseMask | PointerMotionMask |
671 ButtonPressMask | ButtonReleaseMask |
Alexandre Julliarda0b2b1d1997-11-16 17:38:29 +0000672 FocusChangeMask;
Alexandre Julliardd4719651995-12-12 18:49:11 +0000673 win_attr.override_redirect = TRUE;
674 }
Alexandre Julliard18f92e71996-07-17 20:02:21 +0000675 win_attr.colormap = COLOR_GetColormap();
Alexandre Julliardaca05781994-10-17 18:12:41 +0000676 win_attr.backing_store = Options.backingstore ? WhenMapped : NotUseful;
Alexandre Julliard1285c2f1996-05-06 16:06:24 +0000677 win_attr.save_under = ((classPtr->style & CS_SAVEBITS) != 0);
Alexandre Julliardaf0bae51995-10-03 17:06:08 +0000678 win_attr.cursor = CURSORICON_XCursor;
Alexandre Julliard60ce85c1998-02-01 18:33:27 +0000679 wndPtr->window = TSXCreateWindow( display, rootWindow, cs->x, cs->y,
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000680 cs->cx, cs->cy, 0, CopyFromParent,
Alexandre Julliardaca05781994-10-17 18:12:41 +0000681 InputOutput, CopyFromParent,
682 CWEventMask | CWOverrideRedirect |
683 CWColormap | CWCursor | CWSaveUnder |
684 CWBackingStore, &win_attr );
Alexandre Julliard18f92e71996-07-17 20:02:21 +0000685
686 if ((wndPtr->flags & WIN_MANAGED) &&
687 (cs->dwExStyle & WS_EX_DLGMODALFRAME))
688 {
Alexandre Julliard60ce85c1998-02-01 18:33:27 +0000689 XSizeHints* size_hints = TSXAllocSizeHints();
Alexandre Julliard18f92e71996-07-17 20:02:21 +0000690
691 if (size_hints)
692 {
693 size_hints->min_width = size_hints->max_width = cs->cx;
694 size_hints->min_height = size_hints->max_height = cs->cy;
695 size_hints->flags = (PSize | PMinSize | PMaxSize);
Alexandre Julliard60ce85c1998-02-01 18:33:27 +0000696 TSXSetWMSizeHints( display, wndPtr->window, size_hints,
Alexandre Julliard18f92e71996-07-17 20:02:21 +0000697 XA_WM_NORMAL_HINTS );
Alexandre Julliard60ce85c1998-02-01 18:33:27 +0000698 TSXFree(size_hints);
Alexandre Julliard18f92e71996-07-17 20:02:21 +0000699 }
700 }
701
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000702 if (cs->hwndParent) /* Get window owner */
Alexandre Julliard02ed4c21996-03-02 19:34:10 +0000703 {
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000704 Window win = WIN_GetXWindow( cs->hwndParent );
Alexandre Julliard60ce85c1998-02-01 18:33:27 +0000705 if (win) TSXSetTransientForHint( display, wndPtr->window, win );
Alexandre Julliard02ed4c21996-03-02 19:34:10 +0000706 }
Alexandre Julliard8b915631996-06-16 16:16:05 +0000707 EVENT_RegisterWindow( wndPtr );
Alexandre Julliard988ca971994-06-21 16:15:21 +0000708 }
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000709
710 /* Set the window menu */
711
Alexandre Julliard670cdc41997-08-24 16:00:30 +0000712 if ((wndPtr->dwStyle & (WS_CAPTION | WS_CHILD)) == WS_CAPTION )
Alexandre Julliarde2abbb11995-03-19 17:39:39 +0000713 {
Alexandre Julliardc6c09441997-01-12 18:32:19 +0000714 if (cs->hMenu) SetMenu32(hwnd, cs->hMenu);
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000715 else
716 {
717#if 0 /* FIXME: should check if classPtr->menuNameW can be used as is */
718 if (classPtr->menuNameA)
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000719 cs->hMenu = HIWORD(classPtr->menuNameA) ?
720 LoadMenu(cs->hInstance,SEGPTR_GET(classPtr->menuNameA)):
721 LoadMenu(cs->hInstance,(SEGPTR)classPtr->menuNameA);
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000722#else
Alexandre Julliard77b99181997-09-14 17:17:23 +0000723 SEGPTR menuName = (SEGPTR)GetClassLong16( hwnd, GCL_MENUNAME );
Alexandre Julliard54c27111998-03-29 19:44:57 +0000724 if (menuName)
725 {
726 /* hInstance is still 16-bit in 980215 winelib */
727 if (HIWORD(cs->hInstance) || __winelib)
728 cs->hMenu = LoadMenu32A(cs->hInstance,PTR_SEG_TO_LIN(menuName));
729 else
730 /* doesn't work for winelib, since resources are unicode */
731 cs->hMenu = LoadMenu16(cs->hInstance,menuName);
732
733 if (cs->hMenu) SetMenu32( hwnd, cs->hMenu );
734 }
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000735#endif
736 }
Alexandre Julliarde2abbb11995-03-19 17:39:39 +0000737 }
Alexandre Julliard21979011997-03-05 08:22:35 +0000738 else wndPtr->wIDmenu = (UINT32)cs->hMenu;
Alexandre Julliard490a27e1994-06-08 13:57:50 +0000739
Alexandre Julliardda0cfb31996-12-01 17:17:47 +0000740 /* Send the WM_CREATE message
741 * Perhaps we shouldn't allow width/height changes as well.
742 * See p327 in "Internals".
743 */
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000744
Alexandre Julliardda0cfb31996-12-01 17:17:47 +0000745 maxPos.x = wndPtr->rectWindow.left; maxPos.y = wndPtr->rectWindow.top;
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000746
747 localSend32 = unicode ? SendMessage32W : SendMessage32A;
748 if( (*localSend32)( hwnd, WM_NCCREATE, 0, (LPARAM)cs) )
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000749 {
Rein Klazesbf1bc511998-10-31 12:09:32 +0000750 /* Insert the window in the linked list */
751
752 WIN_LinkWindow( hwnd, hwndLinkAfter );
753
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000754 WINPOS_SendNCCalcSize( hwnd, FALSE, &wndPtr->rectWindow,
755 NULL, NULL, 0, &wndPtr->rectClient );
Alexandre Julliardd37eb361997-07-20 16:23:21 +0000756 OffsetRect32(&wndPtr->rectWindow, maxPos.x - wndPtr->rectWindow.left,
757 maxPos.y - wndPtr->rectWindow.top);
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000758 if( ((*localSend32)( hwnd, WM_CREATE, 0, (LPARAM)cs )) != -1 )
759 {
760 /* Send the size messages */
761
762 if (!(wndPtr->flags & WIN_NEED_SIZE))
763 {
764 /* send it anyway */
Alexandre Julliard46ea8b31998-05-03 19:01:20 +0000765 if (((wndPtr->rectClient.right-wndPtr->rectClient.left) <0)
766 ||((wndPtr->rectClient.bottom-wndPtr->rectClient.top)<0))
767 WARN(win,"sending bogus WM_SIZE message 0x%08lx\n",
768 MAKELONG(wndPtr->rectClient.right-wndPtr->rectClient.left,
769 wndPtr->rectClient.bottom-wndPtr->rectClient.top));
Alexandre Julliardd37eb361997-07-20 16:23:21 +0000770 SendMessage32A( hwnd, WM_SIZE, SIZE_RESTORED,
771 MAKELONG(wndPtr->rectClient.right-wndPtr->rectClient.left,
772 wndPtr->rectClient.bottom-wndPtr->rectClient.top));
773 SendMessage32A( hwnd, WM_MOVE, 0,
774 MAKELONG( wndPtr->rectClient.left,
775 wndPtr->rectClient.top ) );
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000776 }
777
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000778 /* Show the window, maximizing or minimizing if needed */
779
Alexandre Julliard77b99181997-09-14 17:17:23 +0000780 if (wndPtr->dwStyle & (WS_MINIMIZE | WS_MAXIMIZE))
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000781 {
Alexandre Julliard23946ad1997-06-16 17:43:53 +0000782 RECT16 newPos;
Alexandre Julliard77b99181997-09-14 17:17:23 +0000783 UINT16 swFlag = (wndPtr->dwStyle & WS_MINIMIZE) ? SW_MINIMIZE : SW_MAXIMIZE;
Alexandre Julliard23946ad1997-06-16 17:43:53 +0000784 wndPtr->dwStyle &= ~(WS_MAXIMIZE | WS_MINIMIZE);
Alexandre Julliard77b99181997-09-14 17:17:23 +0000785 WINPOS_MinMaximize( wndPtr, swFlag, &newPos );
786 swFlag = ((wndPtr->dwStyle & WS_CHILD) || GetActiveWindow32()) ? SWP_NOACTIVATE : 0;
787 SetWindowPos32( hwnd, 0, newPos.left, newPos.top,
788 newPos.right, newPos.bottom, SWP_FRAMECHANGED | swFlag );
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000789 }
Alexandre Julliard77b99181997-09-14 17:17:23 +0000790
791 if( wndPtr->dwStyle & WS_CHILD && !(wndPtr->dwExStyle & WS_EX_NOPARENTNOTIFY) )
792 {
793 /* Notify the parent window only */
794
795 SendMessage32A( wndPtr->parent->hwndSelf, WM_PARENTNOTIFY,
796 MAKEWPARAM(WM_CREATE, wndPtr->wIDmenu), (LPARAM)hwnd );
797 if( !IsWindow32(hwnd) ) return 0;
798 }
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000799
800 if (cs->style & WS_VISIBLE) ShowWindow32( hwnd, SW_SHOW );
801
802 /* Call WH_SHELL hook */
803
804 if (!(wndPtr->dwStyle & WS_CHILD) && !wndPtr->owner)
805 HOOK_CallHooks16( WH_SHELL, HSHELL_WINDOWCREATED, hwnd, 0 );
806
Alexandre Julliarda69b88b1998-03-15 20:29:56 +0000807 TRACE(win, "created window %04x\n", hwnd);
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000808 return hwnd;
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000809 }
Rein Klazesbf1bc511998-10-31 12:09:32 +0000810 WIN_UnlinkWindow( hwnd );
Alexandre Julliard5f721f81994-01-04 20:14:34 +0000811 }
Alexandre Julliard401710d1993-09-04 10:09:32 +0000812
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000813 /* Abort window creation */
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000814
Alexandre Julliarda69b88b1998-03-15 20:29:56 +0000815 WARN(win, "aborted by WM_xxCREATE!\n");
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000816 WIN_DestroyWindow( wndPtr );
817 return 0;
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000818}
819
820
821/***********************************************************************
822 * CreateWindow16 (USER.41)
823 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +0000824HWND16 WINAPI CreateWindow16( LPCSTR className, LPCSTR windowName,
825 DWORD style, INT16 x, INT16 y, INT16 width,
826 INT16 height, HWND16 parent, HMENU16 menu,
827 HINSTANCE16 instance, LPVOID data )
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000828{
829 return CreateWindowEx16( 0, className, windowName, style,
830 x, y, width, height, parent, menu, instance, data );
831}
832
833
834/***********************************************************************
835 * CreateWindowEx16 (USER.452)
836 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +0000837HWND16 WINAPI CreateWindowEx16( DWORD exStyle, LPCSTR className,
838 LPCSTR windowName, DWORD style, INT16 x,
839 INT16 y, INT16 width, INT16 height,
840 HWND16 parent, HMENU16 menu,
841 HINSTANCE16 instance, LPVOID data )
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000842{
843 ATOM classAtom;
844 CREATESTRUCT32A cs;
845
846 /* Find the class atom */
847
848 if (!(classAtom = GlobalFindAtom32A( className )))
849 {
850 fprintf( stderr, "CreateWindowEx16: bad class name " );
851 if (!HIWORD(className)) fprintf( stderr, "%04x\n", LOWORD(className) );
852 else fprintf( stderr, "'%s'\n", className );
853 return 0;
854 }
855
856 /* Fix the coordinates */
857
858 cs.x = (x == CW_USEDEFAULT16) ? CW_USEDEFAULT32 : (INT32)x;
859 cs.y = (y == CW_USEDEFAULT16) ? CW_USEDEFAULT32 : (INT32)y;
860 cs.cx = (width == CW_USEDEFAULT16) ? CW_USEDEFAULT32 : (INT32)width;
861 cs.cy = (height == CW_USEDEFAULT16) ? CW_USEDEFAULT32 : (INT32)height;
862
863 /* Create the window */
864
865 cs.lpCreateParams = data;
866 cs.hInstance = (HINSTANCE32)instance;
867 cs.hMenu = (HMENU32)menu;
868 cs.hwndParent = (HWND32)parent;
869 cs.style = style;
870 cs.lpszName = windowName;
871 cs.lpszClass = className;
872 cs.dwExStyle = exStyle;
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000873 return WIN_CreateWindowEx( &cs, classAtom, FALSE, FALSE );
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000874}
875
876
877/***********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +0000878 * CreateWindowEx32A (USER32.83)
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000879 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +0000880HWND32 WINAPI CreateWindowEx32A( DWORD exStyle, LPCSTR className,
881 LPCSTR windowName, DWORD style, INT32 x,
882 INT32 y, INT32 width, INT32 height,
883 HWND32 parent, HMENU32 menu,
884 HINSTANCE32 instance, LPVOID data )
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000885{
886 ATOM classAtom;
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000887 CREATESTRUCT32A cs;
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000888
Rein Klazes5c6fc1b1998-11-01 14:50:06 +0000889 if(exStyle & WS_EX_MDICHILD)
890 return MDI_CreateMDIWindow32A(className, windowName, style, x, y, width, height, parent, instance, data);
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000891 /* Find the class atom */
892
893 if (!(classAtom = GlobalFindAtom32A( className )))
894 {
895 fprintf( stderr, "CreateWindowEx32A: bad class name " );
896 if (!HIWORD(className)) fprintf( stderr, "%04x\n", LOWORD(className) );
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000897 else fprintf( stderr, "'%s'\n", className );
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000898 return 0;
899 }
900
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000901 /* Create the window */
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000902
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000903 cs.lpCreateParams = data;
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000904 cs.hInstance = instance;
905 cs.hMenu = menu;
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000906 cs.hwndParent = parent;
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000907 cs.x = x;
908 cs.y = y;
909 cs.cx = width;
910 cs.cy = height;
911 cs.style = style;
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000912 cs.lpszName = windowName;
913 cs.lpszClass = className;
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000914 cs.dwExStyle = exStyle;
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000915 return WIN_CreateWindowEx( &cs, classAtom, TRUE, FALSE );
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000916}
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000917
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000918
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000919/***********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +0000920 * CreateWindowEx32W (USER32.84)
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000921 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +0000922HWND32 WINAPI CreateWindowEx32W( DWORD exStyle, LPCWSTR className,
923 LPCWSTR windowName, DWORD style, INT32 x,
924 INT32 y, INT32 width, INT32 height,
925 HWND32 parent, HMENU32 menu,
926 HINSTANCE32 instance, LPVOID data )
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000927{
928 ATOM classAtom;
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000929 CREATESTRUCT32W cs;
930
Rein Klazes5c6fc1b1998-11-01 14:50:06 +0000931 if(exStyle & WS_EX_MDICHILD)
932 return MDI_CreateMDIWindow32W(className, windowName, style, x, y, width, height, parent, instance, data);
933
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000934 /* Find the class atom */
935
936 if (!(classAtom = GlobalFindAtom32W( className )))
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000937 {
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000938 if (HIWORD(className))
939 {
Alexandre Julliard7ebe1a41996-12-22 18:27:48 +0000940 LPSTR cn = HEAP_strdupWtoA( GetProcessHeap(), 0, className );
Alexandre Julliarda845b881998-06-01 10:44:35 +0000941 WARN( win, "Bad class name '%s'\n",cn);
Alexandre Julliard7ebe1a41996-12-22 18:27:48 +0000942 HeapFree( GetProcessHeap(), 0, cn );
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000943 }
944 else
Alexandre Julliarda845b881998-06-01 10:44:35 +0000945 WARN( win, "Bad class name %p\n", className );
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000946 return 0;
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +0000947 }
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000948
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000949 /* Create the window */
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000950
951 cs.lpCreateParams = data;
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000952 cs.hInstance = instance;
953 cs.hMenu = menu;
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000954 cs.hwndParent = parent;
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000955 cs.x = x;
956 cs.y = y;
957 cs.cx = width;
958 cs.cy = height;
959 cs.style = style;
Alexandre Julliard2d93d001996-05-21 15:01:41 +0000960 cs.lpszName = windowName;
961 cs.lpszClass = className;
Alexandre Julliard1e9ac791996-06-06 18:38:27 +0000962 cs.dwExStyle = exStyle;
963 /* Note: we rely on the fact that CREATESTRUCT32A and */
964 /* CREATESTRUCT32W have the same layout. */
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +0000965 return WIN_CreateWindowEx( (CREATESTRUCT32A *)&cs, classAtom, TRUE, TRUE );
Alexandre Julliard401710d1993-09-04 10:09:32 +0000966}
967
Alexandre Julliard8d24ae61994-04-05 21:42:43 +0000968
Alexandre Julliard401710d1993-09-04 10:09:32 +0000969/***********************************************************************
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000970 * WIN_CheckFocus
971 */
972static void WIN_CheckFocus( WND* pWnd )
973{
Alexandre Julliarda0b2b1d1997-11-16 17:38:29 +0000974 if( GetFocus16() == pWnd->hwndSelf )
975 SetFocus16( (pWnd->dwStyle & WS_CHILD) ? pWnd->parent->hwndSelf : 0 );
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000976}
977
978/***********************************************************************
979 * WIN_SendDestroyMsg
980 */
981static void WIN_SendDestroyMsg( WND* pWnd )
982{
Alexandre Julliarda0b2b1d1997-11-16 17:38:29 +0000983 WIN_CheckFocus(pWnd);
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000984
Alexandre Julliarda0b2b1d1997-11-16 17:38:29 +0000985 if( CARET_GetHwnd() == pWnd->hwndSelf ) DestroyCaret32();
986 if( !pWnd->window ) CLIPBOARD_ResetOwner( pWnd );
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000987
Alexandre Julliarda0b2b1d1997-11-16 17:38:29 +0000988 SendMessage32A( pWnd->hwndSelf, WM_DESTROY, 0, 0);
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +0000989
Alexandre Julliarda0b2b1d1997-11-16 17:38:29 +0000990 if( IsWindow32(pWnd->hwndSelf) )
991 {
992 WND* pChild = pWnd->child;
993 while( pChild )
994 {
995 WIN_SendDestroyMsg( pChild );
996 pChild = pChild->next;
997 }
998 WIN_CheckFocus(pWnd);
999 }
1000 else
Alexandre Julliarda69b88b1998-03-15 20:29:56 +00001001 WARN(win, "\tdestroyed itself while in WM_DESTROY!\n");
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001002}
1003
1004
1005/***********************************************************************
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001006 * DestroyWindow16 (USER.53)
Alexandre Julliard401710d1993-09-04 10:09:32 +00001007 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001008BOOL16 WINAPI DestroyWindow16( HWND16 hwnd )
Alexandre Julliard01d63461997-01-20 19:43:45 +00001009{
1010 return DestroyWindow32(hwnd);
1011}
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001012
1013
Alexandre Julliard01d63461997-01-20 19:43:45 +00001014/***********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001015 * DestroyWindow32 (USER32.135)
Alexandre Julliard01d63461997-01-20 19:43:45 +00001016 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001017BOOL32 WINAPI DestroyWindow32( HWND32 hwnd )
Alexandre Julliard401710d1993-09-04 10:09:32 +00001018{
Alexandre Julliard0e607781993-11-03 19:23:37 +00001019 WND * wndPtr;
Alexandre Julliard3a405ba1994-10-30 16:25:19 +00001020
Alexandre Julliarda69b88b1998-03-15 20:29:56 +00001021 TRACE(win, "(%04x)\n", hwnd);
Alexandre Julliard401710d1993-09-04 10:09:32 +00001022
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001023 /* Initialization */
Alexandre Julliard401710d1993-09-04 10:09:32 +00001024
Alexandre Julliard0e607781993-11-03 19:23:37 +00001025 if (!(wndPtr = WIN_FindWndPtr( hwnd ))) return FALSE;
Alexandre Julliard1e9ac791996-06-06 18:38:27 +00001026 if (wndPtr == pWndDesktop) return FALSE; /* Can't destroy desktop */
Alexandre Julliard58199531994-04-21 01:20:00 +00001027
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001028 /* Call hooks */
1029
Alexandre Julliard7e6ae4b1996-12-08 19:25:27 +00001030 if( HOOK_CallHooks16( WH_CBT, HCBT_DESTROYWND, hwnd, 0L) )
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001031 return FALSE;
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001032
1033 if (!(wndPtr->dwStyle & WS_CHILD) && !wndPtr->owner)
1034 {
Alexandre Julliard7e6ae4b1996-12-08 19:25:27 +00001035 HOOK_CallHooks16( WH_SHELL, HSHELL_WINDOWDESTROYED, hwnd, 0L );
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001036 /* FIXME: clean up palette - see "Internals" p.352 */
1037 }
1038
Alexandre Julliard7ff1c411997-05-25 13:58:18 +00001039 if( !QUEUE_IsExitingQueue(wndPtr->hmemTaskQ) )
Alexandre Julliard77b99181997-09-14 17:17:23 +00001040 if( wndPtr->dwStyle & WS_CHILD && !(wndPtr->dwExStyle & WS_EX_NOPARENTNOTIFY) )
1041 {
1042 /* Notify the parent window only */
1043 SendMessage32A( wndPtr->parent->hwndSelf, WM_PARENTNOTIFY,
1044 MAKEWPARAM(WM_DESTROY, wndPtr->wIDmenu), (LPARAM)hwnd );
1045 if( !IsWindow32(hwnd) ) return TRUE;
1046 }
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001047
Alexandre Julliarda0b2b1d1997-11-16 17:38:29 +00001048 if( wndPtr->window ) CLIPBOARD_ResetOwner( wndPtr ); /* before the window is unmapped */
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001049
Alexandre Julliard58199531994-04-21 01:20:00 +00001050 /* Hide the window */
1051
1052 if (wndPtr->dwStyle & WS_VISIBLE)
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001053 {
Alexandre Julliard01d63461997-01-20 19:43:45 +00001054 SetWindowPos32( hwnd, 0, 0, 0, 0, 0, SWP_HIDEWINDOW |
1055 SWP_NOACTIVATE|SWP_NOZORDER|SWP_NOMOVE|SWP_NOSIZE|
Alexandre Julliard7ff1c411997-05-25 13:58:18 +00001056 ((QUEUE_IsExitingQueue(wndPtr->hmemTaskQ))?SWP_DEFERERASE:0) );
Alexandre Julliard21979011997-03-05 08:22:35 +00001057 if (!IsWindow32(hwnd)) return TRUE;
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001058 }
Alexandre Julliard0e607781993-11-03 19:23:37 +00001059
Alexandre Julliard22945d51995-03-02 17:44:29 +00001060 /* Recursively destroy owned windows */
1061
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001062 if( !(wndPtr->dwStyle & WS_CHILD) )
Alexandre Julliard22945d51995-03-02 17:44:29 +00001063 {
Alexandre Julliard7ff1c411997-05-25 13:58:18 +00001064 /* make sure top menu popup doesn't get destroyed */
Alexandre Julliard77b99181997-09-14 17:17:23 +00001065 MENU_PatchResidentPopup( (HQUEUE16)0xFFFF, wndPtr );
Alexandre Julliard7ff1c411997-05-25 13:58:18 +00001066
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001067 for (;;)
1068 {
Alexandre Julliard59730ae1996-03-24 16:20:51 +00001069 WND *siblingPtr = wndPtr->parent->child; /* First sibling */
1070 while (siblingPtr)
Alexandre Julliard22945d51995-03-02 17:44:29 +00001071 {
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001072 if (siblingPtr->owner == wndPtr)
1073 if (siblingPtr->hmemTaskQ == wndPtr->hmemTaskQ)
1074 break;
1075 else
1076 siblingPtr->owner = NULL;
Alexandre Julliard59730ae1996-03-24 16:20:51 +00001077 siblingPtr = siblingPtr->next;
Alexandre Julliard22945d51995-03-02 17:44:29 +00001078 }
Alexandre Julliard01d63461997-01-20 19:43:45 +00001079 if (siblingPtr) DestroyWindow32( siblingPtr->hwndSelf );
Alexandre Julliard22945d51995-03-02 17:44:29 +00001080 else break;
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001081 }
1082
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001083 if( !Options.managed || EVENT_CheckFocus() )
1084 WINPOS_ActivateOtherWindow(wndPtr);
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001085
1086 if( wndPtr->owner &&
1087 wndPtr->owner->hwndLastActive == wndPtr->hwndSelf )
1088 wndPtr->owner->hwndLastActive = wndPtr->owner->hwndSelf;
Alexandre Julliard22945d51995-03-02 17:44:29 +00001089 }
1090
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001091 /* Send destroy messages */
Alexandre Julliard0e607781993-11-03 19:23:37 +00001092
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001093 WIN_SendDestroyMsg( wndPtr );
Alexandre Julliard21979011997-03-05 08:22:35 +00001094 if (!IsWindow32(hwnd)) return TRUE;
Alexandre Julliard401710d1993-09-04 10:09:32 +00001095
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001096 /* Unlink now so we won't bother with the children later on */
Alexandre Julliard401710d1993-09-04 10:09:32 +00001097
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001098 if( wndPtr->parent ) WIN_UnlinkWindow(hwnd);
1099
1100 /* Destroy the window storage */
1101
1102 WIN_DestroyWindow( wndPtr );
Alexandre Julliard401710d1993-09-04 10:09:32 +00001103 return TRUE;
1104}
1105
1106
1107/***********************************************************************
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001108 * CloseWindow16 (USER.43)
Alexandre Julliarde399fc31993-11-24 17:08:56 +00001109 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001110BOOL16 WINAPI CloseWindow16( HWND16 hwnd )
Alexandre Julliarde399fc31993-11-24 17:08:56 +00001111{
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001112 return CloseWindow32( hwnd );
1113}
1114
1115
1116/***********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001117 * CloseWindow32 (USER32.56)
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001118 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001119BOOL32 WINAPI CloseWindow32( HWND32 hwnd )
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001120{
1121 WND * wndPtr = WIN_FindWndPtr( hwnd );
1122 if (!wndPtr || (wndPtr->dwStyle & WS_CHILD)) return FALSE;
1123 ShowWindow32( hwnd, SW_MINIMIZE );
Alexandre Julliard7e56f681996-01-31 19:02:28 +00001124 return TRUE;
Alexandre Julliarde399fc31993-11-24 17:08:56 +00001125}
1126
1127
Alexandre Julliarde399fc31993-11-24 17:08:56 +00001128/***********************************************************************
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001129 * OpenIcon16 (USER.44)
Alexandre Julliarde399fc31993-11-24 17:08:56 +00001130 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001131BOOL16 WINAPI OpenIcon16( HWND16 hwnd )
Alexandre Julliarde399fc31993-11-24 17:08:56 +00001132{
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001133 return OpenIcon32( hwnd );
1134}
1135
1136
1137/***********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001138 * OpenIcon32 (USER32.410)
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001139 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001140BOOL32 WINAPI OpenIcon32( HWND32 hwnd )
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001141{
1142 if (!IsIconic32( hwnd )) return FALSE;
1143 ShowWindow32( hwnd, SW_SHOWNORMAL );
1144 return TRUE;
Alexandre Julliarde399fc31993-11-24 17:08:56 +00001145}
1146
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00001147
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001148/***********************************************************************
1149 * WIN_FindWindow
1150 *
1151 * Implementation of FindWindow() and FindWindowEx().
1152 */
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001153static HWND32 WIN_FindWindow( HWND32 parent, HWND32 child, ATOM className,
1154 LPCSTR title )
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001155{
1156 WND *pWnd;
1157 CLASS *pClass = NULL;
1158
1159 if (child)
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00001160 {
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001161 if (!(pWnd = WIN_FindWndPtr( child ))) return 0;
1162 if (parent)
1163 {
1164 if (!pWnd->parent || (pWnd->parent->hwndSelf != parent)) return 0;
1165 }
1166 else if (pWnd->parent != pWndDesktop) return 0;
1167 pWnd = pWnd->next;
1168 }
1169 else
1170 {
1171 if (!(pWnd = parent ? WIN_FindWndPtr(parent) : pWndDesktop)) return 0;
1172 pWnd = pWnd->child;
1173 }
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001174 if (!pWnd) return 0;
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001175
1176 /* For a child window, all siblings will have the same hInstance, */
1177 /* so we can look for the class once and for all. */
1178
1179 if (className && (pWnd->dwStyle & WS_CHILD))
1180 {
1181 if (!(pClass = CLASS_FindClassByAtom( className, pWnd->hInstance )))
Alexandre Julliard2ace16a1996-04-28 15:09:19 +00001182 return 0;
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00001183 }
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00001184
Alexandre Julliard44ed71f1997-12-21 19:17:50 +00001185
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001186 for ( ; pWnd; pWnd = pWnd->next)
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00001187 {
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001188 if (className && !(pWnd->dwStyle & WS_CHILD))
1189 {
Alexandre Julliard44ed71f1997-12-21 19:17:50 +00001190 if (!(pClass = CLASS_FindClassByAtom( className, GetExePtr(pWnd->hInstance))))
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001191 continue; /* Skip this window */
1192 }
Alexandre Julliard44ed71f1997-12-21 19:17:50 +00001193
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001194 if (pClass && (pWnd->class != pClass))
1195 continue; /* Not the right class */
1196
1197 /* Now check the title */
1198
1199 if (!title) return pWnd->hwndSelf;
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001200 if (pWnd->text && !strcmp( pWnd->text, title )) return pWnd->hwndSelf;
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00001201 }
1202 return 0;
Alexandre Julliarde399fc31993-11-24 17:08:56 +00001203}
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001204
1205
1206
1207/***********************************************************************
1208 * FindWindow16 (USER.50)
1209 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001210HWND16 WINAPI FindWindow16( SEGPTR className, LPCSTR title )
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001211{
1212 return FindWindowEx16( 0, 0, className, title );
1213}
1214
1215
1216/***********************************************************************
1217 * FindWindowEx16 (USER.427)
1218 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001219HWND16 WINAPI FindWindowEx16( HWND16 parent, HWND16 child,
1220 SEGPTR className, LPCSTR title )
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001221{
Alexandre Julliard0e270f41996-08-24 18:26:35 +00001222 ATOM atom = 0;
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001223
Alexandre Julliarda69b88b1998-03-15 20:29:56 +00001224 TRACE(win, "%04x %04x '%s' '%s'\n", parent,
Alexandre Julliard641ee761997-08-04 16:34:36 +00001225 child, HIWORD(className)?(char *)PTR_SEG_TO_LIN(className):"",
1226 title ? title : "");
1227
Alexandre Julliard0e270f41996-08-24 18:26:35 +00001228 if (className)
1229 {
1230 /* If the atom doesn't exist, then no class */
1231 /* with this name exists either. */
1232 if (!(atom = GlobalFindAtom16( className ))) return 0;
1233 }
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001234 return WIN_FindWindow( parent, child, atom, title );
1235}
1236
1237
1238/***********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001239 * FindWindow32A (USER32.198)
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001240 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001241HWND32 WINAPI FindWindow32A( LPCSTR className, LPCSTR title )
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001242{
Alexandre Julliard767e6f61998-08-09 12:47:43 +00001243 HWND32 ret = FindWindowEx32A( 0, 0, className, title );
1244 if (!ret) SetLastError (ERROR_CANNOT_FIND_WND_CLASS);
1245 return ret;
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001246}
1247
1248
1249/***********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001250 * FindWindowEx32A (USER32.199)
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001251 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001252HWND32 WINAPI FindWindowEx32A( HWND32 parent, HWND32 child,
1253 LPCSTR className, LPCSTR title )
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001254{
Alexandre Julliard0e270f41996-08-24 18:26:35 +00001255 ATOM atom = 0;
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001256
Alexandre Julliard0e270f41996-08-24 18:26:35 +00001257 if (className)
1258 {
1259 /* If the atom doesn't exist, then no class */
1260 /* with this name exists either. */
Alexandre Julliard767e6f61998-08-09 12:47:43 +00001261 if (!(atom = GlobalFindAtom32A( className )))
1262 {
1263 SetLastError (ERROR_CANNOT_FIND_WND_CLASS);
1264 return 0;
1265 }
Alexandre Julliard0e270f41996-08-24 18:26:35 +00001266 }
Alexandre Julliard77b99181997-09-14 17:17:23 +00001267 return WIN_FindWindow( parent, child, atom, title );
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001268}
1269
1270
1271/***********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001272 * FindWindowEx32W (USER32.200)
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001273 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001274HWND32 WINAPI FindWindowEx32W( HWND32 parent, HWND32 child,
1275 LPCWSTR className, LPCWSTR title )
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001276{
Alexandre Julliard0e270f41996-08-24 18:26:35 +00001277 ATOM atom = 0;
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001278 char *buffer;
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001279 HWND32 hwnd;
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001280
Alexandre Julliard0e270f41996-08-24 18:26:35 +00001281 if (className)
1282 {
1283 /* If the atom doesn't exist, then no class */
1284 /* with this name exists either. */
Alexandre Julliard767e6f61998-08-09 12:47:43 +00001285 if (!(atom = GlobalFindAtom32W( className )))
1286 {
1287 SetLastError (ERROR_CANNOT_FIND_WND_CLASS);
1288 return 0;
1289 }
Alexandre Julliard0e270f41996-08-24 18:26:35 +00001290 }
Alexandre Julliard7ebe1a41996-12-22 18:27:48 +00001291 buffer = HEAP_strdupWtoA( GetProcessHeap(), 0, title );
Alexandre Julliard77b99181997-09-14 17:17:23 +00001292 hwnd = WIN_FindWindow( parent, child, atom, buffer );
Alexandre Julliard7ebe1a41996-12-22 18:27:48 +00001293 HeapFree( GetProcessHeap(), 0, buffer );
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001294 return hwnd;
1295}
1296
1297
1298/***********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001299 * FindWindow32W (USER32.201)
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001300 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001301HWND32 WINAPI FindWindow32W( LPCWSTR className, LPCWSTR title )
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001302{
1303 return FindWindowEx32W( 0, 0, className, title );
1304}
1305
1306
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001307/**********************************************************************
Alexandre Julliard59730ae1996-03-24 16:20:51 +00001308 * WIN_GetDesktop
1309 */
1310WND *WIN_GetDesktop(void)
1311{
1312 return pWndDesktop;
1313}
1314
1315
1316/**********************************************************************
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001317 * GetDesktopWindow16 (USER.286)
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001318 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001319HWND16 WINAPI GetDesktopWindow16(void)
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001320{
1321 return (HWND16)pWndDesktop->hwndSelf;
1322}
1323
1324
1325/**********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001326 * GetDesktopWindow32 (USER32.232)
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001327 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001328HWND32 WINAPI GetDesktopWindow32(void)
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001329{
Alexandre Julliard59730ae1996-03-24 16:20:51 +00001330 return pWndDesktop->hwndSelf;
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001331}
1332
1333
Alexandre Julliard02ed4c21996-03-02 19:34:10 +00001334/**********************************************************************
1335 * GetDesktopHwnd (USER.278)
1336 *
1337 * Exactly the same thing as GetDesktopWindow(), but not documented.
1338 * Don't ask me why...
1339 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001340HWND16 WINAPI GetDesktopHwnd(void)
Alexandre Julliard02ed4c21996-03-02 19:34:10 +00001341{
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00001342 return (HWND16)pWndDesktop->hwndSelf;
Alexandre Julliard02ed4c21996-03-02 19:34:10 +00001343}
1344
1345
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00001346/*******************************************************************
Alexandre Julliard01d63461997-01-20 19:43:45 +00001347 * EnableWindow16 (USER.34)
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00001348 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001349BOOL16 WINAPI EnableWindow16( HWND16 hwnd, BOOL16 enable )
Alexandre Julliard01d63461997-01-20 19:43:45 +00001350{
1351 return EnableWindow32( hwnd, enable );
1352}
1353
1354
1355/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001356 * EnableWindow32 (USER32.172)
Alexandre Julliard01d63461997-01-20 19:43:45 +00001357 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001358BOOL32 WINAPI EnableWindow32( HWND32 hwnd, BOOL32 enable )
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00001359{
1360 WND *wndPtr;
1361
1362 if (!(wndPtr = WIN_FindWndPtr( hwnd ))) return FALSE;
1363 if (enable && (wndPtr->dwStyle & WS_DISABLED))
1364 {
1365 /* Enable window */
1366 wndPtr->dwStyle &= ~WS_DISABLED;
Alexandre Julliard01d63461997-01-20 19:43:45 +00001367 SendMessage32A( hwnd, WM_ENABLE, TRUE, 0 );
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00001368 return TRUE;
1369 }
1370 else if (!enable && !(wndPtr->dwStyle & WS_DISABLED))
1371 {
1372 /* Disable window */
1373 wndPtr->dwStyle |= WS_DISABLED;
Alexandre Julliard01d63461997-01-20 19:43:45 +00001374 if ((hwnd == GetFocus32()) || IsChild32( hwnd, GetFocus32() ))
Alexandre Julliard8bbf8181996-09-13 16:50:47 +00001375 SetFocus32( 0 ); /* A disabled window can't have the focus */
Alexandre Julliard01d63461997-01-20 19:43:45 +00001376 if ((hwnd == GetCapture32()) || IsChild32( hwnd, GetCapture32() ))
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00001377 ReleaseCapture(); /* A disabled window can't capture the mouse */
Alexandre Julliard01d63461997-01-20 19:43:45 +00001378 SendMessage32A( hwnd, WM_ENABLE, FALSE, 0 );
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00001379 return FALSE;
1380 }
1381 return ((wndPtr->dwStyle & WS_DISABLED) != 0);
1382}
1383
1384
1385/***********************************************************************
Alexandre Julliard01d63461997-01-20 19:43:45 +00001386 * IsWindowEnabled16 (USER.35)
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00001387 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001388BOOL16 WINAPI IsWindowEnabled16(HWND16 hWnd)
Alexandre Julliard01d63461997-01-20 19:43:45 +00001389{
1390 return IsWindowEnabled32(hWnd);
1391}
1392
1393
1394/***********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001395 * IsWindowEnabled32 (USER32.349)
Alexandre Julliard01d63461997-01-20 19:43:45 +00001396 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001397BOOL32 WINAPI IsWindowEnabled32(HWND32 hWnd)
Alexandre Julliard8d24ae61994-04-05 21:42:43 +00001398{
1399 WND * wndPtr;
1400
1401 if (!(wndPtr = WIN_FindWndPtr(hWnd))) return FALSE;
1402 return !(wndPtr->dwStyle & WS_DISABLED);
1403}
1404
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001405
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001406/***********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001407 * IsWindowUnicode (USER32.350)
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001408 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001409BOOL32 WINAPI IsWindowUnicode( HWND32 hwnd )
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001410{
1411 WND * wndPtr;
1412
1413 if (!(wndPtr = WIN_FindWndPtr(hwnd))) return FALSE;
Alexandre Julliard3051b641996-07-05 17:14:13 +00001414 return (WINPROC_GetProcType( wndPtr->winproc ) == WIN_PROC_32W);
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00001415}
1416
1417
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001418/**********************************************************************
Alexandre Julliard21979011997-03-05 08:22:35 +00001419 * GetWindowWord16 (USER.133)
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001420 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001421WORD WINAPI GetWindowWord16( HWND16 hwnd, INT16 offset )
Alexandre Julliard21979011997-03-05 08:22:35 +00001422{
1423 return GetWindowWord32( hwnd, offset );
1424}
1425
1426
1427/**********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001428 * GetWindowWord32 (USER32.314)
Alexandre Julliard21979011997-03-05 08:22:35 +00001429 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001430WORD WINAPI GetWindowWord32( HWND32 hwnd, INT32 offset )
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001431{
1432 WND * wndPtr = WIN_FindWndPtr( hwnd );
1433 if (!wndPtr) return 0;
Alexandre Julliard3051b641996-07-05 17:14:13 +00001434 if (offset >= 0)
1435 {
1436 if (offset + sizeof(WORD) > wndPtr->class->cbWndExtra)
1437 {
Alexandre Julliarda845b881998-06-01 10:44:35 +00001438 WARN( win, "Invalid offset %d\n", offset );
Alexandre Julliard3051b641996-07-05 17:14:13 +00001439 return 0;
1440 }
1441 return *(WORD *)(((char *)wndPtr->wExtra) + offset);
1442 }
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001443 switch(offset)
1444 {
Alexandre Julliard77b99181997-09-14 17:17:23 +00001445 case GWW_ID:
1446 if (HIWORD(wndPtr->wIDmenu))
Alexandre Julliarda845b881998-06-01 10:44:35 +00001447 WARN( win,"GWW_ID: discards high bits of 0x%08x!\n",
1448 wndPtr->wIDmenu);
Alexandre Julliard77b99181997-09-14 17:17:23 +00001449 return (WORD)wndPtr->wIDmenu;
Alexandre Julliardebfc0fe1998-06-28 18:40:26 +00001450 case GWW_HWNDPARENT:
1451 return wndPtr->parent ?
1452 wndPtr->parent->hwndSelf : (
1453 wndPtr->owner ?
1454 wndPtr->owner->hwndSelf :
1455 0);
Alexandre Julliard77b99181997-09-14 17:17:23 +00001456 case GWW_HINSTANCE:
1457 if (HIWORD(wndPtr->hInstance))
Alexandre Julliarda845b881998-06-01 10:44:35 +00001458 WARN(win,"GWW_HINSTANCE: discards high bits of 0x%08x!\n",
1459 wndPtr->hInstance);
Alexandre Julliard77b99181997-09-14 17:17:23 +00001460 return (WORD)wndPtr->hInstance;
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001461 default:
Alexandre Julliarda845b881998-06-01 10:44:35 +00001462 WARN( win, "Invalid offset %d\n", offset );
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001463 return 0;
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001464 }
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001465}
1466
1467
1468/**********************************************************************
Alexandre Julliardaf0bae51995-10-03 17:06:08 +00001469 * WIN_GetWindowInstance
1470 */
Alexandre Julliard77b99181997-09-14 17:17:23 +00001471HINSTANCE32 WIN_GetWindowInstance( HWND32 hwnd )
Alexandre Julliardaf0bae51995-10-03 17:06:08 +00001472{
1473 WND * wndPtr = WIN_FindWndPtr( hwnd );
Alexandre Julliard77b99181997-09-14 17:17:23 +00001474 if (!wndPtr) return (HINSTANCE32)0;
Alexandre Julliardaf0bae51995-10-03 17:06:08 +00001475 return wndPtr->hInstance;
1476}
1477
1478
1479/**********************************************************************
Alexandre Julliard21979011997-03-05 08:22:35 +00001480 * SetWindowWord16 (USER.134)
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001481 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001482WORD WINAPI SetWindowWord16( HWND16 hwnd, INT16 offset, WORD newval )
Alexandre Julliard21979011997-03-05 08:22:35 +00001483{
1484 return SetWindowWord32( hwnd, offset, newval );
1485}
1486
1487
1488/**********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001489 * SetWindowWord32 (USER32.524)
Alexandre Julliard21979011997-03-05 08:22:35 +00001490 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001491WORD WINAPI SetWindowWord32( HWND32 hwnd, INT32 offset, WORD newval )
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001492{
1493 WORD *ptr, retval;
1494 WND * wndPtr = WIN_FindWndPtr( hwnd );
1495 if (!wndPtr) return 0;
Alexandre Julliard3051b641996-07-05 17:14:13 +00001496 if (offset >= 0)
1497 {
1498 if (offset + sizeof(WORD) > wndPtr->class->cbWndExtra)
1499 {
Alexandre Julliarda845b881998-06-01 10:44:35 +00001500 WARN( win, "Invalid offset %d\n", offset );
Alexandre Julliard3051b641996-07-05 17:14:13 +00001501 return 0;
1502 }
1503 ptr = (WORD *)(((char *)wndPtr->wExtra) + offset);
1504 }
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001505 else switch(offset)
1506 {
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001507 case GWW_ID: ptr = (WORD *)&wndPtr->wIDmenu; break;
1508 case GWW_HINSTANCE: ptr = (WORD *)&wndPtr->hInstance; break;
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001509 case GWW_HWNDPARENT: return SetParent32( hwnd, newval );
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001510 default:
Alexandre Julliarda845b881998-06-01 10:44:35 +00001511 WARN( win, "Invalid offset %d\n", offset );
Alexandre Julliardaf0bae51995-10-03 17:06:08 +00001512 return 0;
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001513 }
1514 retval = *ptr;
1515 *ptr = newval;
1516 return retval;
1517}
1518
1519
1520/**********************************************************************
Alexandre Julliard3051b641996-07-05 17:14:13 +00001521 * WIN_GetWindowLong
1522 *
1523 * Helper function for GetWindowLong().
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001524 */
Alexandre Julliard3051b641996-07-05 17:14:13 +00001525static LONG WIN_GetWindowLong( HWND32 hwnd, INT32 offset, WINDOWPROCTYPE type )
Alexandre Julliard1e9ac791996-06-06 18:38:27 +00001526{
Alexandre Julliard3051b641996-07-05 17:14:13 +00001527 LONG retval;
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001528 WND * wndPtr = WIN_FindWndPtr( hwnd );
1529 if (!wndPtr) return 0;
Alexandre Julliard3051b641996-07-05 17:14:13 +00001530 if (offset >= 0)
1531 {
1532 if (offset + sizeof(LONG) > wndPtr->class->cbWndExtra)
1533 {
Alexandre Julliarda845b881998-06-01 10:44:35 +00001534 WARN( win, "Invalid offset %d\n", offset );
Alexandre Julliard3051b641996-07-05 17:14:13 +00001535 return 0;
1536 }
1537 retval = *(LONG *)(((char *)wndPtr->wExtra) + offset);
1538 /* Special case for dialog window procedure */
1539 if ((offset == DWL_DLGPROC) && (wndPtr->flags & WIN_ISDIALOG))
1540 return (LONG)WINPROC_GetProc( (HWINDOWPROC)retval, type );
1541 return retval;
1542 }
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001543 switch(offset)
1544 {
Alexandre Julliard1e9ac791996-06-06 18:38:27 +00001545 case GWL_USERDATA: return wndPtr->userdata;
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001546 case GWL_STYLE: return wndPtr->dwStyle;
1547 case GWL_EXSTYLE: return wndPtr->dwExStyle;
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001548 case GWL_ID: return (LONG)wndPtr->wIDmenu;
Alexandre Julliard3051b641996-07-05 17:14:13 +00001549 case GWL_WNDPROC: return (LONG)WINPROC_GetProc( wndPtr->winproc,
1550 type );
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001551 case GWL_HWNDPARENT: return wndPtr->parent ?
1552 (HWND32)wndPtr->parent->hwndSelf : 0;
Alexandre Julliard77b99181997-09-14 17:17:23 +00001553 case GWL_HINSTANCE: return wndPtr->hInstance;
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001554 default:
Alexandre Julliarda845b881998-06-01 10:44:35 +00001555 WARN( win, "Unknown offset %d\n", offset );
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001556 }
1557 return 0;
1558}
1559
1560
1561/**********************************************************************
Alexandre Julliard3051b641996-07-05 17:14:13 +00001562 * WIN_SetWindowLong
1563 *
1564 * Helper function for SetWindowLong().
Alexandre Julliardd30dfd21998-09-27 18:28:36 +00001565 *
1566 * 0 is the failure code. However, in the case of failure SetLastError
1567 * must be set to distinguish between a 0 return value and a failure.
1568 *
1569 * FIXME: The error values for SetLastError may not be right. Can
1570 * someone check with the real thing?
Alexandre Julliard1e9ac791996-06-06 18:38:27 +00001571 */
Alexandre Julliard3051b641996-07-05 17:14:13 +00001572static LONG WIN_SetWindowLong( HWND32 hwnd, INT32 offset, LONG newval,
1573 WINDOWPROCTYPE type )
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001574{
1575 LONG *ptr, retval;
1576 WND * wndPtr = WIN_FindWndPtr( hwnd );
Alexandre Julliarda0d77311998-09-13 16:32:00 +00001577 STYLESTRUCT style;
1578
1579 TRACE(win,"%x=%p %x %lx %x\n",hwnd, wndPtr, offset, newval, type);
Alexandre Julliardd30dfd21998-09-27 18:28:36 +00001580
1581 if (!wndPtr)
1582 {
1583 /* Is this the right error? */
1584 SetLastError( ERROR_INVALID_WINDOW_HANDLE );
1585 return 0;
1586 }
1587
Alexandre Julliard3051b641996-07-05 17:14:13 +00001588 if (offset >= 0)
1589 {
1590 if (offset + sizeof(LONG) > wndPtr->class->cbWndExtra)
1591 {
Alexandre Julliarda845b881998-06-01 10:44:35 +00001592 WARN( win, "Invalid offset %d\n", offset );
Alexandre Julliardd30dfd21998-09-27 18:28:36 +00001593
1594 /* Is this the right error? */
1595 SetLastError( ERROR_OUTOFMEMORY );
1596
Alexandre Julliard3051b641996-07-05 17:14:13 +00001597 return 0;
1598 }
1599 ptr = (LONG *)(((char *)wndPtr->wExtra) + offset);
1600 /* Special case for dialog window procedure */
1601 if ((offset == DWL_DLGPROC) && (wndPtr->flags & WIN_ISDIALOG))
1602 {
1603 retval = (LONG)WINPROC_GetProc( (HWINDOWPROC)*ptr, type );
Alexandre Julliarddf2673b1997-03-29 17:20:20 +00001604 WINPROC_SetProc( (HWINDOWPROC *)ptr, (WNDPROC16)newval,
1605 type, WIN_PROC_WINDOW );
Alexandre Julliard3051b641996-07-05 17:14:13 +00001606 return retval;
1607 }
1608 }
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001609 else switch(offset)
1610 {
Alexandre Julliarda0d77311998-09-13 16:32:00 +00001611 case GWL_ID:
1612 ptr = (DWORD*)&wndPtr->wIDmenu;
1613 break;
1614 case GWL_HINSTANCE:
1615 return SetWindowWord32( hwnd, offset, newval );
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001616 case GWL_WNDPROC:
Alexandre Julliarda0d77311998-09-13 16:32:00 +00001617 retval = (LONG)WINPROC_GetProc( wndPtr->winproc, type );
1618 WINPROC_SetProc( &wndPtr->winproc, (WNDPROC16)newval,
Alexandre Julliarddf2673b1997-03-29 17:20:20 +00001619 type, WIN_PROC_WINDOW );
Alexandre Julliarda0d77311998-09-13 16:32:00 +00001620 return retval;
Alexandre Julliardca22b331996-07-12 19:02:39 +00001621 case GWL_STYLE:
Alexandre Julliardd30dfd21998-09-27 18:28:36 +00001622 style.styleOld = wndPtr->dwStyle;
1623 newval &= ~(WS_VISIBLE | WS_CHILD); /* Some bits can't be changed this way */
1624 style.styleNew = newval | (style.styleOld & (WS_VISIBLE | WS_CHILD));
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001625
Alexandre Julliardd30dfd21998-09-27 18:28:36 +00001626 if (wndPtr->flags & WIN_ISWIN32)
Alexandre Julliarda0d77311998-09-13 16:32:00 +00001627 SendMessage32A(hwnd,WM_STYLECHANGING,GWL_STYLE,(LPARAM)&style);
Alexandre Julliardd30dfd21998-09-27 18:28:36 +00001628 wndPtr->dwStyle = style.styleNew;
1629 if (wndPtr->flags & WIN_ISWIN32)
Alexandre Julliarda0d77311998-09-13 16:32:00 +00001630 SendMessage32A(hwnd,WM_STYLECHANGED,GWL_STYLE,(LPARAM)&style);
Alexandre Julliardd30dfd21998-09-27 18:28:36 +00001631 return style.styleOld;
1632
Alexandre Julliarda0d77311998-09-13 16:32:00 +00001633 case GWL_USERDATA:
1634 ptr = &wndPtr->userdata;
1635 break;
1636 case GWL_EXSTYLE:
Alexandre Julliardd30dfd21998-09-27 18:28:36 +00001637 style.styleOld = wndPtr->dwExStyle;
1638 style.styleNew = newval;
Alexandre Julliarda0d77311998-09-13 16:32:00 +00001639 if (wndPtr->flags & WIN_ISWIN32)
Alexandre Julliarda0d77311998-09-13 16:32:00 +00001640 SendMessage32A(hwnd,WM_STYLECHANGING,GWL_EXSTYLE,(LPARAM)&style);
Alexandre Julliardd30dfd21998-09-27 18:28:36 +00001641 wndPtr->dwExStyle = newval;
1642 if (wndPtr->flags & WIN_ISWIN32)
Alexandre Julliarda0d77311998-09-13 16:32:00 +00001643 SendMessage32A(hwnd,WM_STYLECHANGED,GWL_EXSTYLE,(LPARAM)&style);
Alexandre Julliardd30dfd21998-09-27 18:28:36 +00001644 return style.styleOld;
1645
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001646 default:
Alexandre Julliarda845b881998-06-01 10:44:35 +00001647 WARN( win, "Invalid offset %d\n", offset );
Alexandre Julliardd30dfd21998-09-27 18:28:36 +00001648
1649 /* Don't think this is right error but it should do */
1650 SetLastError( ERROR_OUTOFMEMORY );
1651
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001652 return 0;
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001653 }
1654 retval = *ptr;
1655 *ptr = newval;
1656 return retval;
1657}
1658
1659
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001660/**********************************************************************
Alexandre Julliard3051b641996-07-05 17:14:13 +00001661 * GetWindowLong16 (USER.135)
1662 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001663LONG WINAPI GetWindowLong16( HWND16 hwnd, INT16 offset )
Alexandre Julliard3051b641996-07-05 17:14:13 +00001664{
1665 return WIN_GetWindowLong( (HWND32)hwnd, offset, WIN_PROC_16 );
1666}
1667
1668
1669/**********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001670 * GetWindowLong32A (USER32.305)
Alexandre Julliard3051b641996-07-05 17:14:13 +00001671 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001672LONG WINAPI GetWindowLong32A( HWND32 hwnd, INT32 offset )
Alexandre Julliard3051b641996-07-05 17:14:13 +00001673{
1674 return WIN_GetWindowLong( hwnd, offset, WIN_PROC_32A );
1675}
1676
1677
1678/**********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001679 * GetWindowLong32W (USER32.306)
Alexandre Julliard3051b641996-07-05 17:14:13 +00001680 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001681LONG WINAPI GetWindowLong32W( HWND32 hwnd, INT32 offset )
Alexandre Julliard3051b641996-07-05 17:14:13 +00001682{
1683 return WIN_GetWindowLong( hwnd, offset, WIN_PROC_32W );
1684}
1685
1686
1687/**********************************************************************
1688 * SetWindowLong16 (USER.136)
1689 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001690LONG WINAPI SetWindowLong16( HWND16 hwnd, INT16 offset, LONG newval )
Alexandre Julliard3051b641996-07-05 17:14:13 +00001691{
1692 return WIN_SetWindowLong( hwnd, offset, newval, WIN_PROC_16 );
1693}
1694
1695
1696/**********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001697 * SetWindowLong32A (USER32.517)
Alexandre Julliard3051b641996-07-05 17:14:13 +00001698 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001699LONG WINAPI SetWindowLong32A( HWND32 hwnd, INT32 offset, LONG newval )
Alexandre Julliard3051b641996-07-05 17:14:13 +00001700{
1701 return WIN_SetWindowLong( hwnd, offset, newval, WIN_PROC_32A );
1702}
1703
1704
1705/**********************************************************************
Alexandre Julliard767e6f61998-08-09 12:47:43 +00001706 * SetWindowLong32W (USER32.518) Set window attribute
1707 *
1708 * SetWindowLong() alters one of a window's attributes or sets a 32-bit (long)
1709 * value in a window's extra memory.
1710 *
1711 * The _hwnd_ parameter specifies the window. is the handle to a
1712 * window that has extra memory. The _newval_ parameter contains the
1713 * new attribute or extra memory value. If positive, the _offset_
1714 * parameter is the byte-addressed location in the window's extra
1715 * memory to set. If negative, _offset_ specifies the window
1716 * attribute to set, and should be one of the following values:
1717 *
1718 * GWL_EXSTYLE The window's extended window style
1719 *
1720 * GWL_STYLE The window's window style.
1721 *
1722 * GWL_WNDPROC Pointer to the window's window procedure.
1723 *
1724 * GWL_HINSTANCE The window's pplication instance handle.
1725 *
1726 * GWL_ID The window's identifier.
1727 *
1728 * GWL_USERDATA The window's user-specified data.
1729 *
1730 * If the window is a dialog box, the _offset_ parameter can be one of
1731 * the following values:
1732 *
1733 * DWL_DLGPROC The address of the window's dialog box procedure.
1734 *
1735 * DWL_MSGRESULT The return value of a message
1736 * that the dialog box procedure processed.
1737 *
1738 * DWL_USER Application specific information.
1739 *
1740 * RETURNS
1741 *
1742 * If successful, returns the previous value located at _offset_. Otherwise,
1743 * returns 0.
1744 *
1745 * NOTES
1746 *
1747 * Extra memory for a window class is specified by a nonzero cbWndExtra
1748 * parameter of the WNDCLASS structure passed to RegisterClass() at the
1749 * time of class creation.
1750 *
1751 * Using GWL_WNDPROC to set a new window procedure effectively creates
1752 * a window subclass. Use CallWindowProc() in the new windows procedure
1753 * to pass messages to the superclass's window procedure.
1754 *
1755 * The user data is reserved for use by the application which created
1756 * the window.
1757 *
1758 * Do not use GWL_STYLE to change the window's WS_DISABLE style;
1759 * instead, call the EnableWindow() function to change the window's
1760 * disabled state.
1761 *
1762 * Do not use GWL_HWNDPARENT to reset the window's parent, use
1763 * SetParent() instead.
1764 *
1765 * BUGS
1766 *
1767 * GWL_STYLE does not dispatch WM_STYLE_... messages.
1768 *
1769 * CONFORMANCE
1770 *
1771 * ECMA-234, Win32
1772 *
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001773 */
Alexandre Julliard767e6f61998-08-09 12:47:43 +00001774LONG WINAPI SetWindowLong32W(
1775 HWND32 hwnd, /* window to alter */
1776 INT32 offset, /* offset, in bytes, of location to alter */
1777 LONG newval /* new value of location */
1778) {
Alexandre Julliard3051b641996-07-05 17:14:13 +00001779 return WIN_SetWindowLong( hwnd, offset, newval, WIN_PROC_32W );
Alexandre Julliarde2abbb11995-03-19 17:39:39 +00001780}
1781
1782
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001783/*******************************************************************
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001784 * GetWindowText16 (USER.36)
Alexandre Julliard0e607781993-11-03 19:23:37 +00001785 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001786INT16 WINAPI GetWindowText16( HWND16 hwnd, SEGPTR lpString, INT16 nMaxCount )
Alexandre Julliard0e607781993-11-03 19:23:37 +00001787{
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001788 return (INT16)SendMessage16(hwnd, WM_GETTEXT, nMaxCount, (LPARAM)lpString);
Alexandre Julliard0e607781993-11-03 19:23:37 +00001789}
1790
Alexandre Julliarde2abbb11995-03-19 17:39:39 +00001791
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001792/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001793 * GetWindowText32A (USER32.309)
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001794 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001795INT32 WINAPI GetWindowText32A( HWND32 hwnd, LPSTR lpString, INT32 nMaxCount )
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001796{
1797 return (INT32)SendMessage32A( hwnd, WM_GETTEXT, nMaxCount,
1798 (LPARAM)lpString );
1799}
1800
Alexandre Julliardf90efa91998-06-14 15:24:15 +00001801/*******************************************************************
1802 * InternalGetWindowText (USER32.326)
1803 */
1804INT32 WINAPI InternalGetWindowText(HWND32 hwnd,LPWSTR lpString,INT32 nMaxCount )
1805{
Juergen Schmied982f1391998-10-28 14:58:02 +00001806 FIXME(win,"(0x%08x,%p,0x%x),stub!\n",hwnd,lpString,nMaxCount);
Alexandre Julliard767e6f61998-08-09 12:47:43 +00001807 return GetWindowText32W(hwnd,lpString,nMaxCount);
Alexandre Julliardf90efa91998-06-14 15:24:15 +00001808}
1809
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001810
1811/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001812 * GetWindowText32W (USER32.312)
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001813 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001814INT32 WINAPI GetWindowText32W( HWND32 hwnd, LPWSTR lpString, INT32 nMaxCount )
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001815{
1816 return (INT32)SendMessage32W( hwnd, WM_GETTEXT, nMaxCount,
1817 (LPARAM)lpString );
1818}
1819
1820
1821/*******************************************************************
1822 * SetWindowText16 (USER.37)
1823 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001824void WINAPI SetWindowText16( HWND16 hwnd, SEGPTR lpString )
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001825{
1826 SendMessage16( hwnd, WM_SETTEXT, 0, (LPARAM)lpString );
1827}
1828
1829
1830/*******************************************************************
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001831 * SetWindowText32A (USER32.521)
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001832 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001833void WINAPI SetWindowText32A( HWND32 hwnd, LPCSTR lpString )
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001834{
1835 SendMessage32A( hwnd, WM_SETTEXT, 0, (LPARAM)lpString );
1836}
1837
1838
1839/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001840 * SetWindowText32W (USER32.523)
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001841 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001842void WINAPI SetWindowText32W( HWND32 hwnd, LPCWSTR lpString )
Alexandre Julliard2d93d001996-05-21 15:01:41 +00001843{
1844 SendMessage32W( hwnd, WM_SETTEXT, 0, (LPARAM)lpString );
Alexandre Julliarde2abbb11995-03-19 17:39:39 +00001845}
1846
1847
Alexandre Julliard0e607781993-11-03 19:23:37 +00001848/*******************************************************************
Alexandre Julliardb1bac321996-12-15 19:45:59 +00001849 * GetWindowTextLength16 (USER.38)
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001850 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001851INT16 WINAPI GetWindowTextLength16( HWND16 hwnd )
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001852{
Alexandre Julliardb1bac321996-12-15 19:45:59 +00001853 return (INT16)SendMessage16( hwnd, WM_GETTEXTLENGTH, 0, 0 );
Alexandre Julliardf0b23541993-09-29 12:21:49 +00001854}
1855
1856
Alexandre Julliard0e607781993-11-03 19:23:37 +00001857/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001858 * GetWindowTextLength32A (USER32.310)
Alexandre Julliardb1bac321996-12-15 19:45:59 +00001859 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001860INT32 WINAPI GetWindowTextLength32A( HWND32 hwnd )
Alexandre Julliardb1bac321996-12-15 19:45:59 +00001861{
1862 return SendMessage32A( hwnd, WM_GETTEXTLENGTH, 0, 0 );
1863}
1864
1865/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001866 * GetWindowTextLength32W (USER32.311)
Alexandre Julliardb1bac321996-12-15 19:45:59 +00001867 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001868INT32 WINAPI GetWindowTextLength32W( HWND32 hwnd )
Alexandre Julliardb1bac321996-12-15 19:45:59 +00001869{
1870 return SendMessage32W( hwnd, WM_GETTEXTLENGTH, 0, 0 );
1871}
1872
Alexandre Julliard21979011997-03-05 08:22:35 +00001873
Alexandre Julliardb1bac321996-12-15 19:45:59 +00001874/*******************************************************************
Alexandre Julliard21979011997-03-05 08:22:35 +00001875 * IsWindow16 (USER.47)
Alexandre Julliarde399fc31993-11-24 17:08:56 +00001876 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001877BOOL16 WINAPI IsWindow16( HWND16 hwnd )
Alexandre Julliard21979011997-03-05 08:22:35 +00001878{
1879 return IsWindow32( hwnd );
1880}
1881
Alexandre Julliardebfc0fe1998-06-28 18:40:26 +00001882void WINAPI WIN16_IsWindow16( CONTEXT *context )
1883{
1884 WORD *stack = PTR_SEG_OFF_TO_LIN(SS_reg(context), SP_reg(context));
1885 HWND16 hwnd = (HWND16)stack[2];
1886
1887 AX_reg(context) = IsWindow32( hwnd );
1888 ES_reg(context) = USER_HeapSel;
1889}
1890
Alexandre Julliard21979011997-03-05 08:22:35 +00001891
1892/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001893 * IsWindow32 (USER32.348)
Alexandre Julliard21979011997-03-05 08:22:35 +00001894 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001895BOOL32 WINAPI IsWindow32( HWND32 hwnd )
Alexandre Julliarde399fc31993-11-24 17:08:56 +00001896{
1897 WND * wndPtr = WIN_FindWndPtr( hwnd );
Alexandre Julliard5f721f81994-01-04 20:14:34 +00001898 return ((wndPtr != NULL) && (wndPtr->dwMagic == WND_MAGIC));
Alexandre Julliarde399fc31993-11-24 17:08:56 +00001899}
1900
1901
1902/*****************************************************************
Alexandre Julliardd1ce8b21996-09-02 16:46:30 +00001903 * GetParent16 (USER.46)
Alexandre Julliarde399fc31993-11-24 17:08:56 +00001904 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001905HWND16 WINAPI GetParent16( HWND16 hwnd )
Alexandre Julliardd1ce8b21996-09-02 16:46:30 +00001906{
1907 return (HWND16)GetParent32( hwnd );
1908}
1909
1910
1911/*****************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001912 * GetParent32 (USER32.278)
Alexandre Julliardd1ce8b21996-09-02 16:46:30 +00001913 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001914HWND32 WINAPI GetParent32( HWND32 hwnd )
Alexandre Julliarde399fc31993-11-24 17:08:56 +00001915{
1916 WND *wndPtr = WIN_FindWndPtr(hwnd);
Alexandre Julliard54c27111998-03-29 19:44:57 +00001917 if ((!wndPtr) || (!(wndPtr->dwStyle & (WS_POPUP|WS_CHILD)))) return 0;
Alexandre Julliard59730ae1996-03-24 16:20:51 +00001918 wndPtr = (wndPtr->dwStyle & WS_CHILD) ? wndPtr->parent : wndPtr->owner;
1919 return wndPtr ? wndPtr->hwndSelf : 0;
Alexandre Julliarde399fc31993-11-24 17:08:56 +00001920}
1921
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001922/*****************************************************************
1923 * WIN_GetTopParent
1924 *
1925 * Get the top-level parent for a child window.
1926 */
1927WND* WIN_GetTopParentPtr( WND* pWnd )
1928{
1929 while( pWnd && (pWnd->dwStyle & WS_CHILD)) pWnd = pWnd->parent;
1930 return pWnd;
1931}
Alexandre Julliarde2991ea1995-07-29 13:09:43 +00001932
1933/*****************************************************************
1934 * WIN_GetTopParent
1935 *
1936 * Get the top-level parent for a child window.
1937 */
Alexandre Julliardac9c9b01996-07-28 18:50:11 +00001938HWND32 WIN_GetTopParent( HWND32 hwnd )
Alexandre Julliarde2991ea1995-07-29 13:09:43 +00001939{
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001940 WND *wndPtr = WIN_GetTopParentPtr ( WIN_FindWndPtr( hwnd ) );
Alexandre Julliard59730ae1996-03-24 16:20:51 +00001941 return wndPtr ? wndPtr->hwndSelf : 0;
Alexandre Julliarde2991ea1995-07-29 13:09:43 +00001942}
1943
1944
Alexandre Julliard940d58c1994-09-16 09:24:37 +00001945/*****************************************************************
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001946 * SetParent16 (USER.233)
Alexandre Julliard940d58c1994-09-16 09:24:37 +00001947 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001948HWND16 WINAPI SetParent16( HWND16 hwndChild, HWND16 hwndNewParent )
Alexandre Julliard940d58c1994-09-16 09:24:37 +00001949{
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001950 return SetParent32( hwndChild, hwndNewParent );
1951}
Alexandre Julliard940d58c1994-09-16 09:24:37 +00001952
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001953
1954/*****************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00001955 * SetParent32 (USER32.495)
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001956 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00001957HWND32 WINAPI SetParent32( HWND32 hwndChild, HWND32 hwndNewParent )
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001958{
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00001959 WND *wndPtr = WIN_FindWndPtr( hwndChild );
Alexandre Julliard60ce85c1998-02-01 18:33:27 +00001960 WND *pWndParent = (hwndNewParent) ? WIN_FindWndPtr( hwndNewParent )
1961 : pWndDesktop;
Alexandre Julliard940d58c1994-09-16 09:24:37 +00001962
Alexandre Julliard60ce85c1998-02-01 18:33:27 +00001963 if( wndPtr && pWndParent && (wndPtr != pWndDesktop) )
1964 {
1965 WND* pWndPrev = wndPtr->parent;
Alexandre Julliard940d58c1994-09-16 09:24:37 +00001966
Alexandre Julliard60ce85c1998-02-01 18:33:27 +00001967 if( pWndParent != pWndPrev )
1968 {
1969 BOOL32 bFixupDCE = IsWindowVisible32(hwndChild);
1970
1971 if ( wndPtr->window )
1972 {
1973 /* Toplevel window needs to be reparented. Used by Tk 8.0 */
1974
1975 TSXDestroyWindow( display, wndPtr->window );
1976 wndPtr->window = None;
1977 }
1978 else if( bFixupDCE )
1979 DCE_InvalidateDCE( wndPtr, &wndPtr->rectWindow );
1980
1981 WIN_UnlinkWindow(hwndChild);
1982 wndPtr->parent = pWndParent;
1983
1984 /* FIXME: Create an X counterpart for reparented top-level windows
1985 * when not in the desktop mode. */
1986
Alexandre Julliarda0d77311998-09-13 16:32:00 +00001987 if ( pWndParent != pWndDesktop ) wndPtr->dwStyle |= WS_CHILD;
Alexandre Julliard60ce85c1998-02-01 18:33:27 +00001988 WIN_LinkWindow(hwndChild, HWND_BOTTOM);
1989
1990 if( bFixupDCE )
1991 {
1992 DCE_InvalidateDCE( wndPtr, &wndPtr->rectWindow );
1993 UpdateWindow32(hwndChild);
1994 }
Alexandre Julliarde658d821997-11-30 17:45:40 +00001995 }
Alexandre Julliard60ce85c1998-02-01 18:33:27 +00001996 return pWndPrev->hwndSelf;
1997 } /* failure */
1998 return 0;
Alexandre Julliard940d58c1994-09-16 09:24:37 +00001999}
2000
2001
Alexandre Julliarde399fc31993-11-24 17:08:56 +00002002/*******************************************************************
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002003 * IsChild16 (USER.48)
Alexandre Julliard0e607781993-11-03 19:23:37 +00002004 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002005BOOL16 WINAPI IsChild16( HWND16 parent, HWND16 child )
Alexandre Julliard01d63461997-01-20 19:43:45 +00002006{
2007 return IsChild32(parent,child);
2008}
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002009
2010
Alexandre Julliard01d63461997-01-20 19:43:45 +00002011/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00002012 * IsChild32 (USER32.339)
Alexandre Julliard01d63461997-01-20 19:43:45 +00002013 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002014BOOL32 WINAPI IsChild32( HWND32 parent, HWND32 child )
Alexandre Julliard0e607781993-11-03 19:23:37 +00002015{
Alexandre Julliardfb9a9191994-03-01 19:48:04 +00002016 WND * wndPtr = WIN_FindWndPtr( child );
2017 while (wndPtr && (wndPtr->dwStyle & WS_CHILD))
Alexandre Julliard0e607781993-11-03 19:23:37 +00002018 {
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002019 wndPtr = wndPtr->parent;
2020 if (wndPtr->hwndSelf == parent) return TRUE;
Alexandre Julliardfb9a9191994-03-01 19:48:04 +00002021 }
Alexandre Julliard0e607781993-11-03 19:23:37 +00002022 return FALSE;
2023}
2024
2025
Alexandre Julliarde399fc31993-11-24 17:08:56 +00002026/***********************************************************************
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002027 * IsWindowVisible16 (USER.49)
Alexandre Julliarde399fc31993-11-24 17:08:56 +00002028 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002029BOOL16 WINAPI IsWindowVisible16( HWND16 hwnd )
Alexandre Julliard01d63461997-01-20 19:43:45 +00002030{
2031 return IsWindowVisible32(hwnd);
2032}
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002033
2034
Alexandre Julliard01d63461997-01-20 19:43:45 +00002035/***********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00002036 * IsWindowVisible32 (USER32.351)
Alexandre Julliard01d63461997-01-20 19:43:45 +00002037 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002038BOOL32 WINAPI IsWindowVisible32( HWND32 hwnd )
Alexandre Julliarde399fc31993-11-24 17:08:56 +00002039{
Alexandre Julliardded30381995-07-06 17:18:27 +00002040 WND *wndPtr = WIN_FindWndPtr( hwnd );
2041 while (wndPtr && (wndPtr->dwStyle & WS_CHILD))
2042 {
2043 if (!(wndPtr->dwStyle & WS_VISIBLE)) return FALSE;
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002044 wndPtr = wndPtr->parent;
Alexandre Julliardded30381995-07-06 17:18:27 +00002045 }
2046 return (wndPtr && (wndPtr->dwStyle & WS_VISIBLE));
Alexandre Julliarde399fc31993-11-24 17:08:56 +00002047}
2048
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002049
Alexandre Julliard1e37a181996-08-18 16:21:52 +00002050/***********************************************************************
2051 * WIN_IsWindowDrawable
Alexandre Julliarddf2673b1997-03-29 17:20:20 +00002052 *
2053 * hwnd is drawable when it is visible, all parents are not
2054 * minimized, and it is itself not minimized unless we are
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002055 * trying to draw its default class icon.
Alexandre Julliard1e37a181996-08-18 16:21:52 +00002056 */
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002057BOOL32 WIN_IsWindowDrawable( WND* wnd, BOOL32 icon )
Alexandre Julliard1e37a181996-08-18 16:21:52 +00002058{
Alexandre Julliarddf2673b1997-03-29 17:20:20 +00002059 if( (wnd->dwStyle & WS_MINIMIZE &&
2060 icon && wnd->class->hIcon) ||
2061 !(wnd->dwStyle & WS_VISIBLE) ) return FALSE;
2062 for(wnd = wnd->parent; wnd; wnd = wnd->parent)
2063 if( wnd->dwStyle & WS_MINIMIZE ||
2064 !(wnd->dwStyle & WS_VISIBLE) ) break;
2065 return (wnd == NULL);
Alexandre Julliard1e37a181996-08-18 16:21:52 +00002066}
2067
Alexandre Julliarddf2673b1997-03-29 17:20:20 +00002068
Alexandre Julliard0e607781993-11-03 19:23:37 +00002069/*******************************************************************
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002070 * GetTopWindow16 (USER.229)
Alexandre Julliard0e607781993-11-03 19:23:37 +00002071 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002072HWND16 WINAPI GetTopWindow16( HWND16 hwnd )
Alexandre Julliard01d63461997-01-20 19:43:45 +00002073{
2074 return GetTopWindow32(hwnd);
2075}
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002076
2077
Alexandre Julliard01d63461997-01-20 19:43:45 +00002078/*******************************************************************
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002079 * GetTopWindow32 (USER.229)
Alexandre Julliard01d63461997-01-20 19:43:45 +00002080 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002081HWND32 WINAPI GetTopWindow32( HWND32 hwnd )
Alexandre Julliard0e607781993-11-03 19:23:37 +00002082{
2083 WND * wndPtr = WIN_FindWndPtr( hwnd );
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002084 if (wndPtr && wndPtr->child) return wndPtr->child->hwndSelf;
Alexandre Julliard0e607781993-11-03 19:23:37 +00002085 else return 0;
2086}
2087
2088
2089/*******************************************************************
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002090 * GetWindow16 (USER.262)
Alexandre Julliard0e607781993-11-03 19:23:37 +00002091 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002092HWND16 WINAPI GetWindow16( HWND16 hwnd, WORD rel )
Alexandre Julliard01d63461997-01-20 19:43:45 +00002093{
2094 return GetWindow32( hwnd,rel );
2095}
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002096
2097
Alexandre Julliard01d63461997-01-20 19:43:45 +00002098/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00002099 * GetWindow32 (USER32.302)
Alexandre Julliard01d63461997-01-20 19:43:45 +00002100 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002101HWND32 WINAPI GetWindow32( HWND32 hwnd, WORD rel )
Alexandre Julliard0e607781993-11-03 19:23:37 +00002102{
2103 WND * wndPtr = WIN_FindWndPtr( hwnd );
2104 if (!wndPtr) return 0;
2105 switch(rel)
2106 {
2107 case GW_HWNDFIRST:
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002108 if (wndPtr->parent) return wndPtr->parent->child->hwndSelf;
Alexandre Julliardfb9a9191994-03-01 19:48:04 +00002109 else return 0;
Alexandre Julliard0e607781993-11-03 19:23:37 +00002110
2111 case GW_HWNDLAST:
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002112 if (!wndPtr->parent) return 0; /* Desktop window */
2113 while (wndPtr->next) wndPtr = wndPtr->next;
2114 return wndPtr->hwndSelf;
Alexandre Julliard0e607781993-11-03 19:23:37 +00002115
2116 case GW_HWNDNEXT:
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002117 if (!wndPtr->next) return 0;
2118 return wndPtr->next->hwndSelf;
Alexandre Julliard0e607781993-11-03 19:23:37 +00002119
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002120 case GW_HWNDPREV:
2121 if (!wndPtr->parent) return 0; /* Desktop window */
2122 wndPtr = wndPtr->parent->child; /* First sibling */
2123 if (wndPtr->hwndSelf == hwnd) return 0; /* First in list */
2124 while (wndPtr->next)
2125 {
2126 if (wndPtr->next->hwndSelf == hwnd) return wndPtr->hwndSelf;
2127 wndPtr = wndPtr->next;
2128 }
2129 return 0;
Alexandre Julliard0e607781993-11-03 19:23:37 +00002130
2131 case GW_OWNER:
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002132 return wndPtr->owner ? wndPtr->owner->hwndSelf : 0;
Alexandre Julliard0e607781993-11-03 19:23:37 +00002133
2134 case GW_CHILD:
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002135 return wndPtr->child ? wndPtr->child->hwndSelf : 0;
Alexandre Julliard0e607781993-11-03 19:23:37 +00002136 }
2137 return 0;
2138}
2139
2140
2141/*******************************************************************
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002142 * GetNextWindow16 (USER.230)
Alexandre Julliard0e607781993-11-03 19:23:37 +00002143 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002144HWND16 WINAPI GetNextWindow16( HWND16 hwnd, WORD flag )
Alexandre Julliard0e607781993-11-03 19:23:37 +00002145{
2146 if ((flag != GW_HWNDNEXT) && (flag != GW_HWNDPREV)) return 0;
Alexandre Julliard01d63461997-01-20 19:43:45 +00002147 return GetWindow16( hwnd, flag );
Alexandre Julliard0e607781993-11-03 19:23:37 +00002148}
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002149
Alexandre Julliarde2991ea1995-07-29 13:09:43 +00002150/*******************************************************************
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002151 * ShowOwnedPopups16 (USER.265)
Alexandre Julliarde2991ea1995-07-29 13:09:43 +00002152 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002153void WINAPI ShowOwnedPopups16( HWND16 owner, BOOL16 fShow )
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002154{
2155 ShowOwnedPopups32( owner, fShow );
2156}
2157
2158
2159/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00002160 * ShowOwnedPopups32 (USER32.531)
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002161 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002162BOOL32 WINAPI ShowOwnedPopups32( HWND32 owner, BOOL32 fShow )
Alexandre Julliarde2991ea1995-07-29 13:09:43 +00002163{
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002164 WND *pWnd = pWndDesktop->child;
2165 while (pWnd)
Alexandre Julliarde2991ea1995-07-29 13:09:43 +00002166 {
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002167 if (pWnd->owner && (pWnd->owner->hwndSelf == owner) &&
2168 (pWnd->dwStyle & WS_POPUP))
Alexandre Julliard01d63461997-01-20 19:43:45 +00002169 ShowWindow32( pWnd->hwndSelf, fShow ? SW_SHOW : SW_HIDE );
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002170 pWnd = pWnd->next;
Alexandre Julliarde2991ea1995-07-29 13:09:43 +00002171 }
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002172 return TRUE;
Alexandre Julliarde2991ea1995-07-29 13:09:43 +00002173}
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002174
2175
Alexandre Julliard3a405ba1994-10-30 16:25:19 +00002176/*******************************************************************
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002177 * GetLastActivePopup16 (USER.287)
Alexandre Julliard3a405ba1994-10-30 16:25:19 +00002178 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002179HWND16 WINAPI GetLastActivePopup16( HWND16 hwnd )
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002180{
2181 return GetLastActivePopup32( hwnd );
2182}
2183
2184/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00002185 * GetLastActivePopup32 (USER32.256)
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002186 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002187HWND32 WINAPI GetLastActivePopup32( HWND32 hwnd )
Alexandre Julliard3a405ba1994-10-30 16:25:19 +00002188{
2189 WND *wndPtr;
2190 wndPtr = WIN_FindWndPtr(hwnd);
2191 if (wndPtr == NULL) return hwnd;
2192 return wndPtr->hwndLastActive;
2193}
2194
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002195
2196/*******************************************************************
Alexandre Julliard3051b641996-07-05 17:14:13 +00002197 * WIN_BuildWinArray
2198 *
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002199 * Build an array of pointers to the children of a given window.
2200 * The array must be freed with HeapFree(SystemHeap). Return NULL
2201 * when no windows are found.
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002202 */
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002203WND **WIN_BuildWinArray( WND *wndPtr, UINT32 bwaFlags, UINT32* pTotal )
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002204{
Alexandre Julliard3051b641996-07-05 17:14:13 +00002205 WND **list, **ppWnd;
2206 WND *pWnd;
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002207 UINT32 count, skipOwned, skipHidden;
2208 DWORD skipFlags;
2209
2210 skipHidden = bwaFlags & BWA_SKIPHIDDEN;
2211 skipOwned = bwaFlags & BWA_SKIPOWNED;
2212 skipFlags = (bwaFlags & BWA_SKIPDISABLED) ? WS_DISABLED : 0;
2213 if( bwaFlags & BWA_SKIPICONIC ) skipFlags |= WS_MINIMIZE;
Alexandre Julliard3051b641996-07-05 17:14:13 +00002214
2215 /* First count the windows */
2216
2217 if (!wndPtr) wndPtr = pWndDesktop;
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002218 for (pWnd = wndPtr->child, count = 0; pWnd; pWnd = pWnd->next)
2219 {
2220 if( (pWnd->dwStyle & skipFlags) || (skipOwned && pWnd->owner) ) continue;
2221 if( !skipHidden || pWnd->dwStyle & WS_VISIBLE ) count++;
2222 }
Alexandre Julliard3051b641996-07-05 17:14:13 +00002223
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002224 if( count )
2225 {
2226 /* Now build the list of all windows */
Alexandre Julliard3051b641996-07-05 17:14:13 +00002227
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002228 if ((list = (WND **)HeapAlloc( SystemHeap, 0, sizeof(WND *) * (count + 1))))
2229 {
2230 for (pWnd = wndPtr->child, ppWnd = list, count = 0; pWnd; pWnd = pWnd->next)
2231 {
2232 if( (pWnd->dwStyle & skipFlags) || (skipOwned && pWnd->owner) ) continue;
2233 if( !skipHidden || pWnd->dwStyle & WS_VISIBLE )
2234 {
2235 *ppWnd++ = pWnd;
2236 count++;
2237 }
2238 }
2239 *ppWnd = NULL;
2240 }
2241 else count = 0;
2242 } else list = NULL;
2243
2244 if( pTotal ) *pTotal = count;
Alexandre Julliard3051b641996-07-05 17:14:13 +00002245 return list;
2246}
2247
2248
2249/*******************************************************************
2250 * EnumWindows16 (USER.54)
2251 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002252BOOL16 WINAPI EnumWindows16( WNDENUMPROC16 lpEnumFunc, LPARAM lParam )
Alexandre Julliard3051b641996-07-05 17:14:13 +00002253{
2254 WND **list, **ppWnd;
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002255
Alexandre Julliard594997c1995-04-30 10:05:20 +00002256 /* We have to build a list of all windows first, to avoid */
2257 /* unpleasant side-effects, for instance if the callback */
2258 /* function changes the Z-order of the windows. */
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002259
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002260 if (!(list = WIN_BuildWinArray( pWndDesktop, 0, NULL ))) return FALSE;
Alexandre Julliard594997c1995-04-30 10:05:20 +00002261
Alexandre Julliard3051b641996-07-05 17:14:13 +00002262 /* Now call the callback function for every window */
Alexandre Julliard594997c1995-04-30 10:05:20 +00002263
Alexandre Julliard3051b641996-07-05 17:14:13 +00002264 for (ppWnd = list; *ppWnd; ppWnd++)
Alexandre Julliard594997c1995-04-30 10:05:20 +00002265 {
Alexandre Julliard3051b641996-07-05 17:14:13 +00002266 /* Make sure that the window still exists */
Alexandre Julliard21979011997-03-05 08:22:35 +00002267 if (!IsWindow32((*ppWnd)->hwndSelf)) continue;
Alexandre Julliardf1aa3031996-08-05 17:42:43 +00002268 if (!lpEnumFunc( (*ppWnd)->hwndSelf, lParam )) break;
Alexandre Julliard594997c1995-04-30 10:05:20 +00002269 }
Alexandre Julliard3051b641996-07-05 17:14:13 +00002270 HeapFree( SystemHeap, 0, list );
2271 return TRUE;
2272}
2273
2274
2275/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00002276 * EnumWindows32 (USER32.193)
Alexandre Julliard3051b641996-07-05 17:14:13 +00002277 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002278BOOL32 WINAPI EnumWindows32( WNDENUMPROC32 lpEnumFunc, LPARAM lParam )
Alexandre Julliard3051b641996-07-05 17:14:13 +00002279{
Alexandre Julliardf1aa3031996-08-05 17:42:43 +00002280 return (BOOL32)EnumWindows16( (WNDENUMPROC16)lpEnumFunc, lParam );
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002281}
2282
Alexandre Julliard594997c1995-04-30 10:05:20 +00002283
2284/**********************************************************************
Alexandre Julliard3051b641996-07-05 17:14:13 +00002285 * EnumTaskWindows16 (USER.225)
Alexandre Julliard594997c1995-04-30 10:05:20 +00002286 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002287BOOL16 WINAPI EnumTaskWindows16( HTASK16 hTask, WNDENUMPROC16 func,
2288 LPARAM lParam )
Alexandre Julliard594997c1995-04-30 10:05:20 +00002289{
Alexandre Julliard3051b641996-07-05 17:14:13 +00002290 WND **list, **ppWnd;
Alexandre Julliardbf9130a1996-10-13 17:45:47 +00002291 HQUEUE16 hQueue = GetTaskQueue( hTask );
Alexandre Julliard594997c1995-04-30 10:05:20 +00002292
2293 /* This function is the same as EnumWindows(), */
2294 /* except for an added check on the window queue. */
2295
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002296 if (!(list = WIN_BuildWinArray( pWndDesktop, 0, NULL ))) return FALSE;
Alexandre Julliard594997c1995-04-30 10:05:20 +00002297
Alexandre Julliard3051b641996-07-05 17:14:13 +00002298 /* Now call the callback function for every window */
Alexandre Julliard594997c1995-04-30 10:05:20 +00002299
Alexandre Julliard3051b641996-07-05 17:14:13 +00002300 for (ppWnd = list; *ppWnd; ppWnd++)
Alexandre Julliard594997c1995-04-30 10:05:20 +00002301 {
Alexandre Julliard3051b641996-07-05 17:14:13 +00002302 /* Make sure that the window still exists */
Alexandre Julliard21979011997-03-05 08:22:35 +00002303 if (!IsWindow32((*ppWnd)->hwndSelf)) continue;
Alexandre Julliard3051b641996-07-05 17:14:13 +00002304 if ((*ppWnd)->hmemTaskQ != hQueue) continue; /* Check the queue */
Alexandre Julliardf1aa3031996-08-05 17:42:43 +00002305 if (!func( (*ppWnd)->hwndSelf, lParam )) break;
Alexandre Julliard594997c1995-04-30 10:05:20 +00002306 }
Alexandre Julliard3051b641996-07-05 17:14:13 +00002307 HeapFree( SystemHeap, 0, list );
Alexandre Julliard594997c1995-04-30 10:05:20 +00002308 return TRUE;
2309}
2310
2311
Alexandre Julliard3051b641996-07-05 17:14:13 +00002312/**********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00002313 * EnumThreadWindows (USER32.190)
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002314 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002315BOOL32 WINAPI EnumThreadWindows( DWORD id, WNDENUMPROC32 func, LPARAM lParam )
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002316{
Alexandre Julliard0623a6f1998-01-18 18:01:49 +00002317 THDB *tdb = THREAD_ID_TO_THDB(id);
Alexandre Julliard01d63461997-01-20 19:43:45 +00002318
2319 return (BOOL16)EnumTaskWindows16(tdb->teb.htask16, (WNDENUMPROC16)func, lParam);
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002320}
2321
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002322
Alexandre Julliard3051b641996-07-05 17:14:13 +00002323/**********************************************************************
Alexandre Julliardf1aa3031996-08-05 17:42:43 +00002324 * WIN_EnumChildWindows
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002325 *
Alexandre Julliardf1aa3031996-08-05 17:42:43 +00002326 * Helper function for EnumChildWindows().
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002327 */
Alexandre Julliardf1aa3031996-08-05 17:42:43 +00002328static BOOL16 WIN_EnumChildWindows( WND **ppWnd, WNDENUMPROC16 func,
2329 LPARAM lParam )
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002330{
Alexandre Julliard3051b641996-07-05 17:14:13 +00002331 WND **childList;
2332 BOOL16 ret = FALSE;
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002333
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002334 for ( ; *ppWnd; ppWnd++)
Alexandre Julliard3051b641996-07-05 17:14:13 +00002335 {
2336 /* Make sure that the window still exists */
Alexandre Julliard21979011997-03-05 08:22:35 +00002337 if (!IsWindow32((*ppWnd)->hwndSelf)) continue;
Alexandre Julliard3051b641996-07-05 17:14:13 +00002338 /* Build children list first */
Alexandre Julliard85ed45e1998-08-22 19:03:56 +00002339 childList = WIN_BuildWinArray( *ppWnd, BWA_SKIPOWNED, NULL );
2340 ret = func( (*ppWnd)->hwndSelf, lParam );
2341 if (childList)
2342 {
2343 if (ret) ret = WIN_EnumChildWindows( childList, func, lParam );
2344 HeapFree( SystemHeap, 0, childList );
2345 }
Alexandre Julliard3051b641996-07-05 17:14:13 +00002346 if (!ret) return FALSE;
Alexandre Julliard3051b641996-07-05 17:14:13 +00002347 }
2348 return TRUE;
2349}
2350
2351
2352/**********************************************************************
2353 * EnumChildWindows16 (USER.55)
2354 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002355BOOL16 WINAPI EnumChildWindows16( HWND16 parent, WNDENUMPROC16 func,
2356 LPARAM lParam )
Alexandre Julliard3051b641996-07-05 17:14:13 +00002357{
2358 WND **list, *pParent;
2359
2360 if (!(pParent = WIN_FindWndPtr( parent ))) return FALSE;
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002361 if (!(list = WIN_BuildWinArray( pParent, BWA_SKIPOWNED, NULL ))) return FALSE;
Alexandre Julliardf1aa3031996-08-05 17:42:43 +00002362 WIN_EnumChildWindows( list, func, lParam );
Alexandre Julliard3051b641996-07-05 17:14:13 +00002363 HeapFree( SystemHeap, 0, list );
2364 return TRUE;
2365}
2366
2367
2368/**********************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00002369 * EnumChildWindows32 (USER32.178)
Alexandre Julliard3051b641996-07-05 17:14:13 +00002370 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002371BOOL32 WINAPI EnumChildWindows32( HWND32 parent, WNDENUMPROC32 func,
2372 LPARAM lParam )
Alexandre Julliard3051b641996-07-05 17:14:13 +00002373{
Alexandre Julliardf1aa3031996-08-05 17:42:43 +00002374 return (BOOL32)EnumChildWindows16( (HWND16)parent, (WNDENUMPROC16)func,
2375 lParam );
Alexandre Julliarddba420a1994-02-02 06:48:31 +00002376}
2377
Alexandre Julliard594997c1995-04-30 10:05:20 +00002378
Alexandre Julliard58199531994-04-21 01:20:00 +00002379/*******************************************************************
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002380 * AnyPopup16 (USER.52)
Alexandre Julliardd18872d1994-05-11 12:18:19 +00002381 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002382BOOL16 WINAPI AnyPopup16(void)
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002383{
2384 return AnyPopup32();
2385}
2386
2387
2388/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00002389 * AnyPopup32 (USER32.4)
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002390 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002391BOOL32 WINAPI AnyPopup32(void)
Alexandre Julliardd18872d1994-05-11 12:18:19 +00002392{
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002393 WND *wndPtr;
2394 for (wndPtr = pWndDesktop->child; wndPtr; wndPtr = wndPtr->next)
2395 if (wndPtr->owner && (wndPtr->dwStyle & WS_VISIBLE)) return TRUE;
2396 return FALSE;
Alexandre Julliardd18872d1994-05-11 12:18:19 +00002397}
2398
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002399
Alexandre Julliard73450d61994-05-18 18:29:32 +00002400/*******************************************************************
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002401 * FlashWindow16 (USER.105)
Alexandre Julliard73450d61994-05-18 18:29:32 +00002402 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002403BOOL16 WINAPI FlashWindow16( HWND16 hWnd, BOOL16 bInvert )
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002404{
2405 return FlashWindow32( hWnd, bInvert );
2406}
2407
2408
2409/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00002410 * FlashWindow32 (USER32.202)
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002411 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002412BOOL32 WINAPI FlashWindow32( HWND32 hWnd, BOOL32 bInvert )
Alexandre Julliard73450d61994-05-18 18:29:32 +00002413{
Alexandre Julliard7d654eb1996-02-25 11:36:22 +00002414 WND *wndPtr = WIN_FindWndPtr(hWnd);
2415
Alexandre Julliarda69b88b1998-03-15 20:29:56 +00002416 TRACE(win,"%04x\n", hWnd);
Alexandre Julliard7d654eb1996-02-25 11:36:22 +00002417
2418 if (!wndPtr) return FALSE;
2419
2420 if (wndPtr->dwStyle & WS_MINIMIZE)
2421 {
2422 if (bInvert && !(wndPtr->flags & WIN_NCACTIVATED))
2423 {
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00002424 HDC32 hDC = GetDC32(hWnd);
Alexandre Julliard7d654eb1996-02-25 11:36:22 +00002425
Alexandre Julliard530ee841996-10-23 16:59:13 +00002426 if (!SendMessage16( hWnd, WM_ERASEBKGND, (WPARAM16)hDC, 0 ))
Alexandre Julliard7d654eb1996-02-25 11:36:22 +00002427 wndPtr->flags |= WIN_NEEDS_ERASEBKGND;
2428
Alexandre Julliard2c69f6d1996-09-28 18:11:01 +00002429 ReleaseDC32( hWnd, hDC );
Alexandre Julliard7d654eb1996-02-25 11:36:22 +00002430 wndPtr->flags |= WIN_NCACTIVATED;
2431 }
2432 else
2433 {
Alexandre Julliard1e37a181996-08-18 16:21:52 +00002434 PAINT_RedrawWindow( hWnd, 0, 0, RDW_INVALIDATE | RDW_ERASE |
2435 RDW_UPDATENOW | RDW_FRAME, 0 );
Alexandre Julliard7d654eb1996-02-25 11:36:22 +00002436 wndPtr->flags &= ~WIN_NCACTIVATED;
2437 }
2438 return TRUE;
2439 }
2440 else
2441 {
Alexandre Julliard530ee841996-10-23 16:59:13 +00002442 WPARAM16 wparam;
Alexandre Julliard7d654eb1996-02-25 11:36:22 +00002443 if (bInvert) wparam = !(wndPtr->flags & WIN_NCACTIVATED);
Alexandre Julliard01d63461997-01-20 19:43:45 +00002444 else wparam = (hWnd == GetActiveWindow32());
Alexandre Julliard7d654eb1996-02-25 11:36:22 +00002445
Alexandre Julliard2d93d001996-05-21 15:01:41 +00002446 SendMessage16( hWnd, WM_NCACTIVATE, wparam, (LPARAM)0 );
Alexandre Julliard7d654eb1996-02-25 11:36:22 +00002447 return wparam;
2448 }
Alexandre Julliard73450d61994-05-18 18:29:32 +00002449}
2450
Alexandre Julliardd18872d1994-05-11 12:18:19 +00002451
2452/*******************************************************************
Alexandre Julliard18f92e71996-07-17 20:02:21 +00002453 * SetSysModalWindow16 (USER.188)
Alexandre Julliard58199531994-04-21 01:20:00 +00002454 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002455HWND16 WINAPI SetSysModalWindow16( HWND16 hWnd )
Alexandre Julliard58199531994-04-21 01:20:00 +00002456{
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002457 HWND32 hWndOldModal = hwndSysModal;
Alexandre Julliardd4719651995-12-12 18:49:11 +00002458 hwndSysModal = hWnd;
Alexandre Julliarda69b88b1998-03-15 20:29:56 +00002459 FIXME(win, "EMPTY STUB !! SetSysModalWindow(%04x) !\n", hWnd);
Alexandre Julliardd4719651995-12-12 18:49:11 +00002460 return hWndOldModal;
Alexandre Julliard58199531994-04-21 01:20:00 +00002461}
2462
Alexandre Julliardd18872d1994-05-11 12:18:19 +00002463
Alexandre Julliard1d62f6b1994-05-04 19:15:00 +00002464/*******************************************************************
Alexandre Julliard18f92e71996-07-17 20:02:21 +00002465 * GetSysModalWindow16 (USER.52)
Alexandre Julliard1d62f6b1994-05-04 19:15:00 +00002466 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002467HWND16 WINAPI GetSysModalWindow16(void)
Alexandre Julliard1d62f6b1994-05-04 19:15:00 +00002468{
Alexandre Julliardd4719651995-12-12 18:49:11 +00002469 return hwndSysModal;
Alexandre Julliard1d62f6b1994-05-04 19:15:00 +00002470}
Alexandre Julliardade697e1995-11-26 13:59:11 +00002471
Alexandre Julliard18f92e71996-07-17 20:02:21 +00002472
Alexandre Julliardade697e1995-11-26 13:59:11 +00002473/*******************************************************************
Alexandre Julliardc7c217b1998-04-13 12:21:30 +00002474 * GetWindowContextHelpId (USER32.303)
2475 */
2476DWORD WINAPI GetWindowContextHelpId( HWND32 hwnd )
2477{
2478 WND *wnd = WIN_FindWndPtr( hwnd );
2479 if (!wnd) return 0;
2480 return wnd->helpContext;
2481}
2482
2483
2484/*******************************************************************
2485 * SetWindowContextHelpId (USER32.515)
2486 */
2487BOOL32 WINAPI SetWindowContextHelpId( HWND32 hwnd, DWORD id )
2488{
2489 WND *wnd = WIN_FindWndPtr( hwnd );
2490 if (!wnd) return FALSE;
2491 wnd->helpContext = id;
2492 return TRUE;
2493}
2494
2495
2496/*******************************************************************
Alexandre Julliardade697e1995-11-26 13:59:11 +00002497 * DRAG_QueryUpdate
2498 *
2499 * recursively find a child that contains spDragInfo->pt point
2500 * and send WM_QUERYDROPOBJECT
2501 */
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002502BOOL16 DRAG_QueryUpdate( HWND32 hQueryWnd, SEGPTR spDragInfo, BOOL32 bNoSend )
Alexandre Julliardade697e1995-11-26 13:59:11 +00002503{
Alexandre Julliard75d86e11996-11-17 18:59:11 +00002504 BOOL16 wParam,bResult = 0;
Alexandre Julliardd37eb361997-07-20 16:23:21 +00002505 POINT32 pt;
Alexandre Julliardade697e1995-11-26 13:59:11 +00002506 LPDRAGINFO ptrDragInfo = (LPDRAGINFO) PTR_SEG_TO_LIN(spDragInfo);
2507 WND *ptrQueryWnd = WIN_FindWndPtr(hQueryWnd),*ptrWnd;
Alexandre Julliardd37eb361997-07-20 16:23:21 +00002508 RECT32 tempRect;
Alexandre Julliardade697e1995-11-26 13:59:11 +00002509
2510 if( !ptrQueryWnd || !ptrDragInfo ) return 0;
2511
Alexandre Julliardd37eb361997-07-20 16:23:21 +00002512 CONV_POINT16TO32( &ptrDragInfo->pt, &pt );
Alexandre Julliardade697e1995-11-26 13:59:11 +00002513
Alexandre Julliardd37eb361997-07-20 16:23:21 +00002514 GetWindowRect32(hQueryWnd,&tempRect);
Alexandre Julliardade697e1995-11-26 13:59:11 +00002515
Alexandre Julliardd37eb361997-07-20 16:23:21 +00002516 if( !PtInRect32(&tempRect,pt) ||
Alexandre Julliardade697e1995-11-26 13:59:11 +00002517 (ptrQueryWnd->dwStyle & WS_DISABLED) )
2518 return 0;
2519
2520 if( !(ptrQueryWnd->dwStyle & WS_MINIMIZE) )
2521 {
2522 tempRect = ptrQueryWnd->rectClient;
2523 if(ptrQueryWnd->dwStyle & WS_CHILD)
Alexandre Julliardd37eb361997-07-20 16:23:21 +00002524 MapWindowPoints32( ptrQueryWnd->parent->hwndSelf, 0,
2525 (LPPOINT32)&tempRect, 2 );
Alexandre Julliardade697e1995-11-26 13:59:11 +00002526
Alexandre Julliardd37eb361997-07-20 16:23:21 +00002527 if (PtInRect32( &tempRect, pt))
Alexandre Julliardade697e1995-11-26 13:59:11 +00002528 {
2529 wParam = 0;
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002530
2531 for (ptrWnd = ptrQueryWnd->child; ptrWnd ;ptrWnd = ptrWnd->next)
2532 if( ptrWnd->dwStyle & WS_VISIBLE )
Alexandre Julliardade697e1995-11-26 13:59:11 +00002533 {
Alexandre Julliardd37eb361997-07-20 16:23:21 +00002534 GetWindowRect32( ptrWnd->hwndSelf, &tempRect );
2535 if (PtInRect32( &tempRect, pt )) break;
Alexandre Julliardade697e1995-11-26 13:59:11 +00002536 }
2537
2538 if(ptrWnd)
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002539 {
Alexandre Julliarda69b88b1998-03-15 20:29:56 +00002540 TRACE(msg,"hwnd = %04x, %d %d - %d %d\n",
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002541 ptrWnd->hwndSelf, ptrWnd->rectWindow.left, ptrWnd->rectWindow.top,
2542 ptrWnd->rectWindow.right, ptrWnd->rectWindow.bottom );
2543 if( !(ptrWnd->dwStyle & WS_DISABLED) )
Alexandre Julliard75d86e11996-11-17 18:59:11 +00002544 bResult = DRAG_QueryUpdate(ptrWnd->hwndSelf, spDragInfo, bNoSend);
Alexandre Julliard59730ae1996-03-24 16:20:51 +00002545 }
Alexandre Julliardade697e1995-11-26 13:59:11 +00002546
2547 if(bResult) return bResult;
2548 }
2549 else wParam = 1;
2550 }
2551 else wParam = 1;
2552
Alexandre Julliarde2bfa4c1996-05-16 18:21:06 +00002553 ScreenToClient16(hQueryWnd,&ptrDragInfo->pt);
Alexandre Julliardade697e1995-11-26 13:59:11 +00002554
2555 ptrDragInfo->hScope = hQueryWnd;
2556
Alexandre Julliard75d86e11996-11-17 18:59:11 +00002557 bResult = ( bNoSend )
2558 ? ptrQueryWnd->dwExStyle & WS_EX_ACCEPTFILES
2559 : SendMessage16( hQueryWnd ,WM_QUERYDROPOBJECT ,
Alexandre Julliard530ee841996-10-23 16:59:13 +00002560 (WPARAM16)wParam ,(LPARAM) spDragInfo );
Alexandre Julliardade697e1995-11-26 13:59:11 +00002561 if( !bResult )
Alexandre Julliardd37eb361997-07-20 16:23:21 +00002562 CONV_POINT32TO16( &pt, &ptrDragInfo->pt );
Alexandre Julliardade697e1995-11-26 13:59:11 +00002563
2564 return bResult;
2565}
2566
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002567
Alexandre Julliardade697e1995-11-26 13:59:11 +00002568/*******************************************************************
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002569 * DragDetect (USER.465)
Alexandre Julliardade697e1995-11-26 13:59:11 +00002570 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002571BOOL16 WINAPI DragDetect16( HWND16 hWnd, POINT16 pt )
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002572{
2573 POINT32 pt32;
2574 CONV_POINT16TO32( &pt, &pt32 );
2575 return DragDetect32( hWnd, pt32 );
2576}
2577
2578/*******************************************************************
Alexandre Julliarda11d7b11998-03-01 20:05:02 +00002579 * DragDetect32 (USER32.151)
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002580 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002581BOOL32 WINAPI DragDetect32( HWND32 hWnd, POINT32 pt )
Alexandre Julliardade697e1995-11-26 13:59:11 +00002582{
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002583 MSG16 msg;
2584 RECT16 rect;
Alexandre Julliardade697e1995-11-26 13:59:11 +00002585
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002586 rect.left = pt.x - wDragWidth;
2587 rect.right = pt.x + wDragWidth;
Alexandre Julliardade697e1995-11-26 13:59:11 +00002588
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002589 rect.top = pt.y - wDragHeight;
2590 rect.bottom = pt.y + wDragHeight;
Alexandre Julliardade697e1995-11-26 13:59:11 +00002591
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002592 SetCapture32(hWnd);
Alexandre Julliardade697e1995-11-26 13:59:11 +00002593
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002594 while(1)
2595 {
2596 while(PeekMessage16(&msg ,0 ,WM_MOUSEFIRST ,WM_MOUSELAST ,PM_REMOVE))
2597 {
2598 if( msg.message == WM_LBUTTONUP )
2599 {
2600 ReleaseCapture();
2601 return 0;
2602 }
2603 if( msg.message == WM_MOUSEMOVE )
2604 {
2605 if( !PtInRect16( &rect, MAKEPOINT16(msg.lParam) ) )
Alexandre Julliardade697e1995-11-26 13:59:11 +00002606 {
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002607 ReleaseCapture();
2608 return 1;
Alexandre Julliardade697e1995-11-26 13:59:11 +00002609 }
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002610 }
2611 }
2612 WaitMessage();
2613 }
2614 return 0;
Alexandre Julliardade697e1995-11-26 13:59:11 +00002615}
2616
2617/******************************************************************************
Alexandre Julliard21979011997-03-05 08:22:35 +00002618 * DragObject16 (USER.464)
Alexandre Julliardade697e1995-11-26 13:59:11 +00002619 */
Alexandre Julliard670cdc41997-08-24 16:00:30 +00002620DWORD WINAPI DragObject16( HWND16 hwndScope, HWND16 hWnd, UINT16 wObj,
2621 HANDLE16 hOfStruct, WORD szList, HCURSOR16 hCursor )
Alexandre Julliardade697e1995-11-26 13:59:11 +00002622{
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002623 MSG16 msg;
2624 LPDRAGINFO lpDragInfo;
2625 SEGPTR spDragInfo;
2626 HCURSOR16 hDragCursor=0, hOldCursor=0, hBummer=0;
2627 HGLOBAL16 hDragInfo = GlobalAlloc16( GMEM_SHARE | GMEM_ZEROINIT, 2*sizeof(DRAGINFO));
2628 WND *wndPtr = WIN_FindWndPtr(hWnd);
2629 HCURSOR16 hCurrentCursor = 0;
2630 HWND16 hCurrentWnd = 0;
Alexandre Julliardade697e1995-11-26 13:59:11 +00002631
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002632 lpDragInfo = (LPDRAGINFO) GlobalLock16(hDragInfo);
2633 spDragInfo = (SEGPTR) WIN16_GlobalLock16(hDragInfo);
Alexandre Julliardade697e1995-11-26 13:59:11 +00002634
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002635 if( !lpDragInfo || !spDragInfo ) return 0L;
Alexandre Julliardade697e1995-11-26 13:59:11 +00002636
Alexandre Julliardc7c217b1998-04-13 12:21:30 +00002637 hBummer = LoadCursor16(0, IDC_BUMMER16);
Alexandre Julliardade697e1995-11-26 13:59:11 +00002638
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002639 if( !hBummer || !wndPtr )
2640 {
Alexandre Julliard1285c2f1996-05-06 16:06:24 +00002641 GlobalFree16(hDragInfo);
Alexandre Julliardade697e1995-11-26 13:59:11 +00002642 return 0L;
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002643 }
Alexandre Julliardade697e1995-11-26 13:59:11 +00002644
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002645 if(hCursor)
2646 {
Alexandre Julliard75d86e11996-11-17 18:59:11 +00002647 if( !(hDragCursor = CURSORICON_IconToCursor(hCursor, FALSE)) )
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002648 {
2649 GlobalFree16(hDragInfo);
2650 return 0L;
2651 }
Alexandre Julliardade697e1995-11-26 13:59:11 +00002652
2653 if( hDragCursor == hCursor ) hDragCursor = 0;
2654 else hCursor = hDragCursor;
2655
Alexandre Julliardf0cbfa01997-02-15 14:29:56 +00002656 hOldCursor = SetCursor32(hDragCursor);
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002657 }
Alexandre Julliardade697e1995-11-26 13:59:11 +00002658
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002659 lpDragInfo->hWnd = hWnd;
2660 lpDragInfo->hScope = 0;
2661 lpDragInfo->wFlags = wObj;
2662 lpDragInfo->hList = szList; /* near pointer! */
2663 lpDragInfo->hOfStruct = hOfStruct;
2664 lpDragInfo->l = 0L;
Alexandre Julliardade697e1995-11-26 13:59:11 +00002665
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002666 SetCapture32(hWnd);
2667 ShowCursor32( TRUE );
Alexandre Julliardade697e1995-11-26 13:59:11 +00002668
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002669 do
2670 {
2671 do{ WaitMessage(); }
2672 while( !PeekMessage16(&msg,0,WM_MOUSEFIRST,WM_MOUSELAST,PM_REMOVE) );
Alexandre Julliardade697e1995-11-26 13:59:11 +00002673
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002674 *(lpDragInfo+1) = *lpDragInfo;
Alexandre Julliardade697e1995-11-26 13:59:11 +00002675
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002676 lpDragInfo->pt = msg.pt;
Alexandre Julliardade697e1995-11-26 13:59:11 +00002677
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002678 /* update DRAGINFO struct */
Alexandre Julliarda69b88b1998-03-15 20:29:56 +00002679 TRACE(msg,"lpDI->hScope = %04x\n",lpDragInfo->hScope);
Alexandre Julliardade697e1995-11-26 13:59:11 +00002680
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002681 if( DRAG_QueryUpdate(hwndScope, spDragInfo, FALSE) > 0 )
2682 hCurrentCursor = hCursor;
2683 else
Alexandre Julliardade697e1995-11-26 13:59:11 +00002684 {
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002685 hCurrentCursor = hBummer;
2686 lpDragInfo->hScope = 0;
Alexandre Julliardade697e1995-11-26 13:59:11 +00002687 }
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002688 if( hCurrentCursor )
2689 SetCursor32(hCurrentCursor);
Alexandre Julliardade697e1995-11-26 13:59:11 +00002690
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002691 /* send WM_DRAGLOOP */
2692 SendMessage16( hWnd, WM_DRAGLOOP, (WPARAM16)(hCurrentCursor != hBummer),
2693 (LPARAM) spDragInfo );
2694 /* send WM_DRAGSELECT or WM_DRAGMOVE */
2695 if( hCurrentWnd != lpDragInfo->hScope )
Alexandre Julliardade697e1995-11-26 13:59:11 +00002696 {
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002697 if( hCurrentWnd )
2698 SendMessage16( hCurrentWnd, WM_DRAGSELECT, 0,
Alexandre Julliardade697e1995-11-26 13:59:11 +00002699 (LPARAM)MAKELONG(LOWORD(spDragInfo)+sizeof(DRAGINFO),
2700 HIWORD(spDragInfo)) );
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002701 hCurrentWnd = lpDragInfo->hScope;
2702 if( hCurrentWnd )
2703 SendMessage16( hCurrentWnd, WM_DRAGSELECT, 1, (LPARAM)spDragInfo);
Alexandre Julliardade697e1995-11-26 13:59:11 +00002704 }
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002705 else
2706 if( hCurrentWnd )
2707 SendMessage16( hCurrentWnd, WM_DRAGMOVE, 0, (LPARAM)spDragInfo);
2708
2709 } while( msg.message != WM_LBUTTONUP && msg.message != WM_NCLBUTTONUP );
2710
2711 ReleaseCapture();
2712 ShowCursor32( FALSE );
2713
2714 if( hCursor )
2715 {
2716 SetCursor32( hOldCursor );
2717 if (hDragCursor) DestroyCursor32( hDragCursor );
2718 }
2719
2720 if( hCurrentCursor != hBummer )
2721 msg.lParam = SendMessage16( lpDragInfo->hScope, WM_DROPOBJECT,
2722 (WPARAM16)hWnd, (LPARAM)spDragInfo );
Alexandre Julliardade697e1995-11-26 13:59:11 +00002723 else
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002724 msg.lParam = 0;
2725 GlobalFree16(hDragInfo);
Alexandre Julliardade697e1995-11-26 13:59:11 +00002726
Alexandre Julliard23946ad1997-06-16 17:43:53 +00002727 return (DWORD)(msg.lParam);
Alexandre Julliardade697e1995-11-26 13:59:11 +00002728}