Owen Wang
[wine.git] / windows / property.c
blob2ed6527de5105f4e6e6cdc64a7a61899c8893b43
1 /*
2 * Window properties
4 * Copyright 1995, 1996 Alexandre Julliard
5 */
7 #include <string.h>
9 #include "windef.h"
10 #include "wingdi.h"
11 #include "wine/winuser16.h"
12 #include "win.h"
13 #include "heap.h"
14 #include "debugtools.h"
16 DEFAULT_DEBUG_CHANNEL(prop)
19 typedef struct tagPROPERTY
21 struct tagPROPERTY *next; /* Next property in window list */
22 HANDLE handle; /* User's data */
23 LPSTR string; /* Property string (or atom) */
24 } PROPERTY;
27 /***********************************************************************
28 * PROP_FindProp
30 static PROPERTY *PROP_FindProp( HWND hwnd, LPCSTR str )
32 ATOM atom;
33 PROPERTY *prop;
34 WND *pWnd = WIN_FindWndPtr( hwnd );
36 if (!pWnd) return NULL;
37 if (HIWORD(str))
39 atom = GlobalFindAtomA( str );
40 for (prop = pWnd->pProp; prop; prop = prop->next)
42 if (HIWORD(prop->string))
44 if (!lstrcmpiA( prop->string, str )) goto END;
46 else if (LOWORD(prop->string) == atom) goto END;
49 else /* atom */
51 atom = LOWORD(str);
52 for (prop = pWnd->pProp; (prop); prop = prop->next)
54 if (HIWORD(prop->string))
56 if (GlobalFindAtomA( prop->string ) == atom) goto END;
58 else if (LOWORD(prop->string) == atom) goto END;
61 prop = NULL;
62 END:
63 WIN_ReleaseWndPtr(pWnd);
64 return prop;
68 /***********************************************************************
69 * GetProp16 (USER.25)
71 HANDLE16 WINAPI GetProp16( HWND16 hwnd, LPCSTR str )
73 return (HANDLE16)GetPropA( hwnd, str );
77 /***********************************************************************
78 * GetPropA (USER32.281)
80 HANDLE WINAPI GetPropA( HWND hwnd, LPCSTR str )
82 PROPERTY *prop = PROP_FindProp( hwnd, str );
84 if (HIWORD(str))
85 TRACE("(%08x,'%s'): returning %08x\n",
86 hwnd, str, prop ? prop->handle : 0 );
87 else
88 TRACE("(%08x,#%04x): returning %08x\n",
89 hwnd, LOWORD(str), prop ? prop->handle : 0 );
91 return prop ? prop->handle : 0;
95 /***********************************************************************
96 * GetPropW (USER32.282)
98 HANDLE WINAPI GetPropW( HWND hwnd, LPCWSTR str )
100 LPSTR strA;
101 HANDLE ret;
103 if (!HIWORD(str)) return GetPropA( hwnd, (LPCSTR)(UINT)LOWORD(str) );
104 strA = HEAP_strdupWtoA( GetProcessHeap(), 0, str );
105 ret = GetPropA( hwnd, strA );
106 HeapFree( GetProcessHeap(), 0, strA );
107 return ret;
111 /***********************************************************************
112 * SetProp16 (USER.26)
114 BOOL16 WINAPI SetProp16( HWND16 hwnd, LPCSTR str, HANDLE16 handle )
116 return (BOOL16)SetPropA( hwnd, str, handle );
120 /***********************************************************************
121 * SetPropA (USER32.497)
123 BOOL WINAPI SetPropA( HWND hwnd, LPCSTR str, HANDLE handle )
125 PROPERTY *prop;
127 if (HIWORD(str))
128 TRACE("%04x '%s' %08x\n", hwnd, str, handle );
129 else
130 TRACE("%04x #%04x %08x\n",
131 hwnd, LOWORD(str), handle );
133 if (!(prop = PROP_FindProp( hwnd, str )))
135 /* We need to create it */
136 WND *pWnd = WIN_FindWndPtr( hwnd );
137 if (!pWnd) return FALSE;
138 if (!(prop = HeapAlloc( SystemHeap, 0, sizeof(*prop) )))
140 WIN_ReleaseWndPtr(pWnd);
141 return FALSE;
143 if (!(prop->string = SEGPTR_STRDUP(str)))
145 HeapFree( SystemHeap, 0, prop );
146 WIN_ReleaseWndPtr(pWnd);
147 return FALSE;
150 prop->next = pWnd->pProp;
151 pWnd->pProp = prop;
152 WIN_ReleaseWndPtr(pWnd);
154 prop->handle = handle;
155 return TRUE;
159 /***********************************************************************
160 * SetPropW (USER32.498)
162 BOOL WINAPI SetPropW( HWND hwnd, LPCWSTR str, HANDLE handle )
164 BOOL ret;
165 LPSTR strA;
167 if (!HIWORD(str))
168 return SetPropA( hwnd, (LPCSTR)(UINT)LOWORD(str), handle );
169 strA = HEAP_strdupWtoA( GetProcessHeap(), 0, str );
170 ret = SetPropA( hwnd, strA, handle );
171 HeapFree( GetProcessHeap(), 0, strA );
172 return ret;
176 /***********************************************************************
177 * RemoveProp16 (USER.24)
179 HANDLE16 WINAPI RemoveProp16( HWND16 hwnd, LPCSTR str )
181 return (HANDLE16)RemovePropA( hwnd, str );
185 /***********************************************************************
186 * RemovePropA (USER32.442)
188 HANDLE WINAPI RemovePropA( HWND hwnd, LPCSTR str )
190 ATOM atom;
191 HANDLE handle;
192 PROPERTY **pprop, *prop;
193 WND *pWnd = WIN_FindWndPtr( hwnd );
195 if (HIWORD(str))
196 TRACE("%04x '%s'\n", hwnd, str );
197 else
198 TRACE("%04x #%04x\n", hwnd, LOWORD(str));
201 if (!pWnd) return (HANDLE)0;
202 if (HIWORD(str))
204 atom = GlobalFindAtomA( str );
205 for (pprop=(PROPERTY**)&pWnd->pProp; (*pprop); pprop = &(*pprop)->next)
207 if (HIWORD((*pprop)->string))
209 if (!lstrcmpiA( (*pprop)->string, str )) break;
211 else if (LOWORD((*pprop)->string) == atom) break;
214 else /* atom */
216 atom = LOWORD(str);
217 for (pprop=(PROPERTY**)&pWnd->pProp; (*pprop); pprop = &(*pprop)->next)
219 if (HIWORD((*pprop)->string))
221 if (GlobalFindAtomA( (*pprop)->string ) == atom) break;
223 else if (LOWORD((*pprop)->string) == atom) break;
226 WIN_ReleaseWndPtr(pWnd);
227 if (!*pprop) return 0;
228 prop = *pprop;
229 handle = prop->handle;
230 *pprop = prop->next;
231 SEGPTR_FREE(prop->string);
232 HeapFree( SystemHeap, 0, prop );
233 return handle;
237 /***********************************************************************
238 * RemovePropW (USER32.443)
240 HANDLE WINAPI RemovePropW( HWND hwnd, LPCWSTR str )
242 LPSTR strA;
243 HANDLE ret;
245 if (!HIWORD(str))
246 return RemovePropA( hwnd, (LPCSTR)(UINT)LOWORD(str) );
247 strA = HEAP_strdupWtoA( GetProcessHeap(), 0, str );
248 ret = RemovePropA( hwnd, strA );
249 HeapFree( GetProcessHeap(), 0, strA );
250 return ret;
254 /***********************************************************************
255 * PROPERTY_RemoveWindowProps
257 * Remove all properties of a window.
259 void PROPERTY_RemoveWindowProps( WND *pWnd )
261 PROPERTY *prop, *next;
263 for (prop = pWnd->pProp; (prop); prop = next)
265 next = prop->next;
266 SEGPTR_FREE( prop->string );
267 HeapFree( SystemHeap, 0, prop );
269 pWnd->pProp = NULL;
273 /***********************************************************************
274 * EnumProps16 (USER.27)
276 INT16 WINAPI EnumProps16( HWND16 hwnd, PROPENUMPROC16 func )
278 PROPERTY *prop, *next;
279 WND *pWnd;
280 INT16 ret = -1;
282 TRACE("%04x %08x\n", hwnd, (UINT)func );
283 if (!(pWnd = WIN_FindWndPtr( hwnd ))) return -1;
284 for (prop = pWnd->pProp; (prop); prop = next)
286 /* Already get the next in case the callback */
287 /* function removes the current property. */
288 next = prop->next;
290 TRACE(" Callback: handle=%08x str='%s'\n",
291 prop->handle, prop->string );
292 ret = func( hwnd, SEGPTR_GET(prop->string), prop->handle );
293 if (!ret) break;
295 WIN_ReleaseWndPtr(pWnd);
296 return ret;
300 /***********************************************************************
301 * EnumPropsA (USER32.186)
303 INT WINAPI EnumPropsA( HWND hwnd, PROPENUMPROCA func )
305 return EnumPropsExA( hwnd, (PROPENUMPROCEXA)func, 0 );
309 /***********************************************************************
310 * EnumPropsW (USER32.189)
312 INT WINAPI EnumPropsW( HWND hwnd, PROPENUMPROCW func )
314 return EnumPropsExW( hwnd, (PROPENUMPROCEXW)func, 0 );
318 /***********************************************************************
319 * EnumPropsExA (USER32.187)
321 INT WINAPI EnumPropsExA(HWND hwnd, PROPENUMPROCEXA func, LPARAM lParam)
323 PROPERTY *prop, *next;
324 WND *pWnd;
325 INT ret = -1;
327 TRACE("%04x %08x %08lx\n",
328 hwnd, (UINT)func, lParam );
329 if (!(pWnd = WIN_FindWndPtr( hwnd ))) return -1;
330 for (prop = pWnd->pProp; (prop); prop = next)
332 /* Already get the next in case the callback */
333 /* function removes the current property. */
334 next = prop->next;
336 TRACE(" Callback: handle=%08x str='%s'\n",
337 prop->handle, prop->string );
338 ret = func( hwnd, prop->string, prop->handle, lParam );
339 if (!ret) break;
341 WIN_ReleaseWndPtr(pWnd);
342 return ret;
346 /***********************************************************************
347 * EnumPropsExW (USER32.188)
349 INT WINAPI EnumPropsExW(HWND hwnd, PROPENUMPROCEXW func, LPARAM lParam)
351 PROPERTY *prop, *next;
352 WND *pWnd;
353 INT ret = -1;
355 TRACE("%04x %08x %08lx\n",
356 hwnd, (UINT)func, lParam );
357 if (!(pWnd = WIN_FindWndPtr( hwnd ))) return -1;
358 for (prop = pWnd->pProp; (prop); prop = next)
360 /* Already get the next in case the callback */
361 /* function removes the current property. */
362 next = prop->next;
364 TRACE(" Callback: handle=%08x str='%s'\n",
365 prop->handle, prop->string );
366 if (HIWORD(prop->string))
368 LPWSTR str = HEAP_strdupAtoW( GetProcessHeap(), 0, prop->string );
369 ret = func( hwnd, str, prop->handle, lParam );
370 HeapFree( GetProcessHeap(), 0, str );
372 else
373 ret = func( hwnd, (LPCWSTR)(UINT)LOWORD( prop->string ),
374 prop->handle, lParam );
375 if (!ret) break;
377 WIN_ReleaseWndPtr(pWnd);
378 return ret;