mirror of
git://source.winehq.org/git/wine.git
synced 2024-10-14 17:27:18 +00:00
user32: Introduce get_class_info.
And use it in WIN_CreateWindowEx to trigger class registration. Signed-off-by: Jacek Caban <jacek@codeweavers.com> Signed-off-by: Huw Davies <huw@codeweavers.com> Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
parent
ea79e50f98
commit
5e75e5f66d
|
@ -211,6 +211,16 @@ static BOOL set_server_info( HWND hwnd, INT offset, LONG_PTR newval, UINT size )
|
|||
}
|
||||
|
||||
|
||||
static void init_class_name( UNICODE_STRING *str, const WCHAR *name )
|
||||
{
|
||||
if (IS_INTRESOURCE( name ))
|
||||
{
|
||||
str->Buffer = (WCHAR *)name;
|
||||
str->Length = str->MaximumLength = 0;
|
||||
}
|
||||
else RtlInitUnicodeString( str, name );
|
||||
}
|
||||
|
||||
/***********************************************************************
|
||||
* CLASS_GetMenuNameA
|
||||
*
|
||||
|
@ -253,7 +263,6 @@ static void CLASS_SetMenuNameA( CLASS *classPtr, LPCSTR name )
|
|||
else classPtr->menuName = (LPWSTR)name;
|
||||
}
|
||||
|
||||
|
||||
/***********************************************************************
|
||||
* CLASS_SetMenuNameW
|
||||
*
|
||||
|
@ -313,7 +322,7 @@ static CLASS *find_class( HINSTANCE module, const WCHAR *name )
|
|||
{
|
||||
if (wcsicmp( class->name, name )) continue;
|
||||
}
|
||||
if (!class->local || (class->instance & ~0xffff) == instance)
|
||||
if (!class->local || !module || (class->instance & ~0xffff) == instance)
|
||||
{
|
||||
TRACE("%s %Ix -> %p\n", debugstr_w(name), instance, class);
|
||||
return class;
|
||||
|
@ -323,7 +332,7 @@ static CLASS *find_class( HINSTANCE module, const WCHAR *name )
|
|||
return NULL;
|
||||
}
|
||||
|
||||
const WCHAR *CLASS_GetVersionedName( const WCHAR *name, UINT *basename_offset, WCHAR *combined, BOOL register_class )
|
||||
static const WCHAR *CLASS_GetVersionedName( const WCHAR *name, UINT *basename_offset, WCHAR *combined, BOOL register_class )
|
||||
{
|
||||
ACTCTX_SECTION_KEYED_DATA data;
|
||||
struct wndclass_redirect_data
|
||||
|
@ -397,11 +406,12 @@ const WCHAR *CLASS_GetVersionedName( const WCHAR *name, UINT *basename_offset, W
|
|||
*
|
||||
* Return a pointer to the class.
|
||||
*/
|
||||
static CLASS *CLASS_FindClass( LPCWSTR name, HINSTANCE hinstance )
|
||||
static CLASS *CLASS_FindClass( LPCWSTR name, HINSTANCE hinstance, UNICODE_STRING *name_str )
|
||||
{
|
||||
CLASS *class;
|
||||
|
||||
GetDesktopWindow(); /* create the desktop window to trigger builtin class registration */
|
||||
if (name != (LPCWSTR)DESKTOP_CLASS_ATOM && (IS_INTRESOURCE(name) || wcsicmp( name, L"Message" )))
|
||||
GetDesktopWindow(); /* create the desktop window to trigger builtin class registration */
|
||||
|
||||
if (!name) return NULL;
|
||||
|
||||
|
@ -417,6 +427,7 @@ static CLASS *CLASS_FindClass( LPCWSTR name, HINSTANCE hinstance )
|
|||
}
|
||||
|
||||
if (!class) TRACE("%s %p -> not found\n", debugstr_w(name), hinstance);
|
||||
else if (name_str) init_class_name( name_str, name );
|
||||
return class;
|
||||
}
|
||||
|
||||
|
@ -1253,6 +1264,21 @@ BOOL WINAPI GetClassInfoW( HINSTANCE hInstance, LPCWSTR name, WNDCLASSW *wc )
|
|||
return ret;
|
||||
}
|
||||
|
||||
ATOM get_class_info( HINSTANCE instance, const WCHAR *name, UNICODE_STRING *name_str )
|
||||
{
|
||||
CLASS *class;
|
||||
ATOM atom;
|
||||
|
||||
if (!(class = CLASS_FindClass( name, instance, name_str )))
|
||||
{
|
||||
SetLastError( ERROR_CLASS_DOES_NOT_EXIST );
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
atom = class->atomName;
|
||||
release_class_ptr( class );
|
||||
return atom;
|
||||
}
|
||||
|
||||
/***********************************************************************
|
||||
* GetClassInfoExA (USER32.@)
|
||||
|
@ -1277,9 +1303,9 @@ BOOL WINAPI GetClassInfoExA( HINSTANCE hInstance, LPCSTR name, WNDCLASSEXA *wc )
|
|||
WCHAR nameW[MAX_ATOM_LEN + 1];
|
||||
if (!MultiByteToWideChar( CP_ACP, 0, name, -1, nameW, ARRAY_SIZE( nameW )))
|
||||
return FALSE;
|
||||
classPtr = CLASS_FindClass( nameW, hInstance );
|
||||
classPtr = CLASS_FindClass( nameW, hInstance, NULL );
|
||||
}
|
||||
else classPtr = CLASS_FindClass( (LPCWSTR)name, hInstance );
|
||||
else classPtr = CLASS_FindClass( (LPCWSTR)name, hInstance, NULL );
|
||||
|
||||
if (!classPtr)
|
||||
{
|
||||
|
@ -1323,7 +1349,7 @@ BOOL WINAPI GetClassInfoExW( HINSTANCE hInstance, LPCWSTR name, WNDCLASSEXW *wc
|
|||
|
||||
if (!hInstance) hInstance = user32_module;
|
||||
|
||||
if (!(classPtr = CLASS_FindClass( name, hInstance )))
|
||||
if (!(classPtr = CLASS_FindClass( name, hInstance, NULL )))
|
||||
{
|
||||
SetLastError( ERROR_CLASS_DOES_NOT_EXIST );
|
||||
return FALSE;
|
||||
|
|
|
@ -160,8 +160,7 @@ extern BOOL WINPROC_call_window( HWND hwnd, UINT msg, WPARAM wParam, LPARAM lPar
|
|||
LRESULT *result, BOOL unicode, enum wm_char_mapping mapping ) DECLSPEC_HIDDEN;
|
||||
extern void winproc_init(void) DECLSPEC_HIDDEN;
|
||||
|
||||
extern const WCHAR *CLASS_GetVersionedName(const WCHAR *classname, UINT *basename_offset,
|
||||
WCHAR *combined, BOOL register_class) DECLSPEC_HIDDEN;
|
||||
extern ATOM get_class_info( HINSTANCE instance, const WCHAR *name, UNICODE_STRING *name_str ) DECLSPEC_HIDDEN;
|
||||
|
||||
/* kernel callbacks */
|
||||
|
||||
|
|
|
@ -126,7 +126,7 @@ void *free_user_handle( HANDLE handle, unsigned int type )
|
|||
*
|
||||
* Create a window handle with the server.
|
||||
*/
|
||||
static WND *create_window_handle( HWND parent, HWND owner, LPCWSTR name,
|
||||
static WND *create_window_handle( HWND parent, HWND owner, UNICODE_STRING *name,
|
||||
HINSTANCE instance, BOOL unicode,
|
||||
DWORD style, DWORD ex_style )
|
||||
{
|
||||
|
@ -146,8 +146,8 @@ static WND *create_window_handle( HWND parent, HWND owner, LPCWSTR name,
|
|||
req->awareness = awareness;
|
||||
req->style = style;
|
||||
req->ex_style = ex_style;
|
||||
if (!(req->atom = get_int_atom_value( name )) && name)
|
||||
wine_server_add_data( req, name, lstrlenW(name)*sizeof(WCHAR) );
|
||||
if (!(req->atom = get_int_atom_value( name->Buffer )) && name->Length)
|
||||
wine_server_add_data( req, name->Buffer, name->Length );
|
||||
if (!wine_server_call_err( req ))
|
||||
{
|
||||
handle = wine_server_ptr_handle( reply->handle );
|
||||
|
@ -184,7 +184,7 @@ static WND *create_window_handle( HWND parent, HWND owner, LPCWSTR name,
|
|||
{
|
||||
struct user_thread_info *thread_info = get_user_thread_info();
|
||||
|
||||
if (name == (LPCWSTR)DESKTOP_CLASS_ATOM)
|
||||
if (name->Buffer == (LPCWSTR)DESKTOP_CLASS_ATOM)
|
||||
{
|
||||
if (!thread_info->top_window) thread_info->top_window = full_parent ? full_parent : handle;
|
||||
else assert( full_parent == thread_info->top_window );
|
||||
|
@ -1395,18 +1395,19 @@ HWND WIN_CreateWindowEx( CREATESTRUCTW *cs, LPCWSTR className, HINSTANCE module,
|
|||
RECT rect;
|
||||
WND *wndPtr;
|
||||
HWND hwnd, parent, owner, top_child = 0;
|
||||
const WCHAR *p = className;
|
||||
UINT win_dpi, thread_dpi = get_thread_dpi();
|
||||
DPI_AWARENESS_CONTEXT context;
|
||||
MDICREATESTRUCTW mdi_cs;
|
||||
UNICODE_STRING class;
|
||||
CBT_CREATEWNDW cbtc;
|
||||
CREATESTRUCTW cbcs;
|
||||
|
||||
className = CLASS_GetVersionedName(className, NULL, NULL, TRUE);
|
||||
if (!get_class_info( module, className, &class )) return FALSE;
|
||||
|
||||
TRACE("%s %s%s%s ex=%08x style=%08x %d,%d %dx%d parent=%p menu=%p inst=%p params=%p\n",
|
||||
unicode ? debugstr_w(cs->lpszName) : debugstr_a((LPCSTR)cs->lpszName),
|
||||
debugstr_w(p), p != className ? "->" : "", p != className ? debugstr_w(className) : "",
|
||||
debugstr_w(className), class.Buffer != className ? "->" : "",
|
||||
class.Buffer != className ? debugstr_wn(class.Buffer, class.Length / sizeof(WCHAR)) : "",
|
||||
cs->dwExStyle, cs->style, cs->x, cs->y, cs->cx, cs->cy,
|
||||
cs->hwndParent, cs->hMenu, cs->hInstance, cs->lpCreateParams );
|
||||
if(TRACE_ON(win)) dump_window_styles( cs->style, cs->dwExStyle );
|
||||
|
@ -1524,17 +1525,9 @@ HWND WIN_CreateWindowEx( CREATESTRUCTW *cs, LPCWSTR className, HINSTANCE module,
|
|||
|
||||
style = cs->style & ~WS_VISIBLE;
|
||||
ex_style = cs->dwExStyle & ~WS_EX_LAYERED;
|
||||
if (!(wndPtr = create_window_handle( parent, owner, className, module,
|
||||
unicode, style, ex_style )))
|
||||
{
|
||||
WNDCLASSW wc;
|
||||
/* if it's a comctl32 class, GetClassInfo will load it, then we can retry */
|
||||
if (GetLastError() != ERROR_INVALID_HANDLE ||
|
||||
!GetClassInfoW( 0, className, &wc ) ||
|
||||
!(wndPtr = create_window_handle( parent, owner, className, module,
|
||||
unicode, style, ex_style )))
|
||||
return 0;
|
||||
}
|
||||
if (!(wndPtr = create_window_handle( parent, owner, &class, module,
|
||||
unicode, style, ex_style )))
|
||||
return 0;
|
||||
hwnd = wndPtr->obj.handle;
|
||||
|
||||
/* Fill the window structure */
|
||||
|
|
Loading…
Reference in a new issue