imm32: Use thread data from target HWND.
This commit is contained in:
parent
f3967902c5
commit
455ca1adb0
|
@ -246,6 +246,21 @@ static IMMThreadData* IMM_GetThreadData(DWORD id)
|
||||||
return data;
|
return data;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static IMMThreadData* IMM_GetThreadDataForWindow(HWND hwnd)
|
||||||
|
{
|
||||||
|
DWORD process;
|
||||||
|
DWORD thread = 0;
|
||||||
|
|
||||||
|
if (hwnd)
|
||||||
|
{
|
||||||
|
thread = GetWindowThreadProcessId(hwnd, &process);
|
||||||
|
if (process != GetCurrentProcessId())
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
return IMM_GetThreadData(thread);
|
||||||
|
}
|
||||||
|
|
||||||
static BOOL IMM_IsDefaultContext(HIMC imc)
|
static BOOL IMM_IsDefaultContext(HIMC imc)
|
||||||
{
|
{
|
||||||
InputContextData *data = get_imc_data(imc);
|
InputContextData *data = get_imc_data(imc);
|
||||||
|
@ -478,21 +493,21 @@ static InputContextData* get_imc_data(HIMC hIMC)
|
||||||
return data;
|
return data;
|
||||||
}
|
}
|
||||||
|
|
||||||
static IMMThreadData* IMM_GetInitializedThreadData(void)
|
static IMMThreadData* IMM_GetInitializedThreadData(HWND hWnd)
|
||||||
{
|
{
|
||||||
IMMThreadData* thread_data = IMM_GetThreadData(0);
|
IMMThreadData* thread_data = IMM_GetThreadDataForWindow(hWnd);
|
||||||
|
|
||||||
if (!thread_data)
|
if (!thread_data)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
if (!thread_data->defaultContext)
|
if (!thread_data->defaultContext && thread_data->threadID == GetCurrentThreadId())
|
||||||
{
|
{
|
||||||
HIMC defaultContext;
|
HIMC defaultContext;
|
||||||
LeaveCriticalSection(&threaddata_cs);
|
LeaveCriticalSection(&threaddata_cs);
|
||||||
defaultContext = ImmCreateContext();
|
defaultContext = ImmCreateContext();
|
||||||
if (defaultContext)
|
if (defaultContext)
|
||||||
((InputContextData*)defaultContext)->threadDefault = TRUE;
|
((InputContextData*)defaultContext)->threadDefault = TRUE;
|
||||||
thread_data = IMM_GetThreadData(0);
|
thread_data = IMM_GetThreadDataForWindow(hWnd);
|
||||||
if (!thread_data)
|
if (!thread_data)
|
||||||
{
|
{
|
||||||
IMM_DestroyContext(defaultContext);
|
IMM_DestroyContext(defaultContext);
|
||||||
|
@ -528,7 +543,7 @@ HIMC WINAPI ImmAssociateContext(HWND hWnd, HIMC hIMC)
|
||||||
if (hIMC && data->IMC.hWnd == hWnd)
|
if (hIMC && data->IMC.hWnd == hWnd)
|
||||||
return hIMC;
|
return hIMC;
|
||||||
|
|
||||||
thread_data = IMM_GetInitializedThreadData();
|
thread_data = IMM_GetInitializedThreadData(hWnd);
|
||||||
if (!thread_data)
|
if (!thread_data)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
|
@ -603,7 +618,7 @@ BOOL WINAPI ImmAssociateContextEx(HWND hWnd, HIMC hIMC, DWORD dwFlags)
|
||||||
|
|
||||||
TRACE("(%p, %p, 0x%x):\n", hWnd, hIMC, dwFlags);
|
TRACE("(%p, %p, 0x%x):\n", hWnd, hIMC, dwFlags);
|
||||||
|
|
||||||
thread_data = IMM_GetInitializedThreadData();
|
thread_data = IMM_GetInitializedThreadData(hWnd);
|
||||||
if (!thread_data)
|
if (!thread_data)
|
||||||
return FALSE;
|
return FALSE;
|
||||||
|
|
||||||
|
@ -1470,7 +1485,7 @@ HIMC WINAPI ImmGetContext(HWND hWnd)
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
thread_data = IMM_GetInitializedThreadData();
|
thread_data = IMM_GetInitializedThreadData(hWnd);
|
||||||
if (!thread_data)
|
if (!thread_data)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
|
@ -1595,18 +1610,21 @@ BOOL WINAPI ImmGetConversionStatus(
|
||||||
HWND WINAPI ImmGetDefaultIMEWnd(HWND hWnd)
|
HWND WINAPI ImmGetDefaultIMEWnd(HWND hWnd)
|
||||||
{
|
{
|
||||||
HWND ret, new = NULL;
|
HWND ret, new = NULL;
|
||||||
IMMThreadData* thread_data = IMM_GetThreadData(0);
|
IMMThreadData* thread_data = IMM_GetThreadDataForWindow(hWnd);
|
||||||
if (!thread_data)
|
if (!thread_data)
|
||||||
return NULL;
|
return NULL;
|
||||||
if (thread_data->hwndDefault == NULL)
|
if (thread_data->hwndDefault == NULL && thread_data->threadID == GetCurrentThreadId())
|
||||||
{
|
{
|
||||||
/* Do not create the window inside of a critical section */
|
/* Do not create the window inside of a critical section */
|
||||||
LeaveCriticalSection(&threaddata_cs);
|
LeaveCriticalSection(&threaddata_cs);
|
||||||
new = CreateWindowExW( WS_EX_TOOLWINDOW,
|
new = CreateWindowExW( WS_EX_TOOLWINDOW,
|
||||||
szwIME, NULL, WS_POPUP, 0, 0, 1, 1, 0, 0, 0, 0);
|
szwIME, NULL, WS_POPUP, 0, 0, 1, 1, 0, 0, 0, 0);
|
||||||
thread_data = IMM_GetThreadData(0);
|
thread_data = IMM_GetThreadDataForWindow(hWnd);
|
||||||
if (!thread_data)
|
if (!thread_data)
|
||||||
|
{
|
||||||
|
DestroyWindow(new);
|
||||||
return NULL;
|
return NULL;
|
||||||
|
}
|
||||||
/* See if anyone beat us */
|
/* See if anyone beat us */
|
||||||
if (thread_data->hwndDefault == NULL)
|
if (thread_data->hwndDefault == NULL)
|
||||||
{
|
{
|
||||||
|
@ -1622,6 +1640,7 @@ HWND WINAPI ImmGetDefaultIMEWnd(HWND hWnd)
|
||||||
{
|
{
|
||||||
DestroyWindow(new);
|
DestroyWindow(new);
|
||||||
}
|
}
|
||||||
|
TRACE("Default is %p\n",ret);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -425,15 +425,17 @@ static DWORD WINAPI ImmGetContextThreadFunc( LPVOID lpParam)
|
||||||
HWND hwnd2;
|
HWND hwnd2;
|
||||||
COMPOSITIONFORM cf;
|
COMPOSITIONFORM cf;
|
||||||
POINT pt;
|
POINT pt;
|
||||||
|
MSG msg;
|
||||||
|
|
||||||
igc_threadinfo *info= (igc_threadinfo*)lpParam;
|
igc_threadinfo *info= (igc_threadinfo*)lpParam;
|
||||||
info->hwnd = CreateWindowExA(WS_EX_CLIENTEDGE, wndcls, "Wine imm32.dll test",
|
info->hwnd = CreateWindowExA(WS_EX_CLIENTEDGE, wndcls, "Wine imm32.dll test",
|
||||||
WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT,
|
WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT,
|
||||||
240, 120, NULL, NULL, GetModuleHandleW(NULL), NULL);
|
240, 120, NULL, NULL, GetModuleHandleW(NULL), NULL);
|
||||||
|
|
||||||
h1 = ImmGetContext(hwnd);
|
h1 = ImmGetContext(hwnd);
|
||||||
todo_wine ok(info->himc == h1, "hwnd context changed in new thread\n");
|
ok(info->himc == h1, "hwnd context changed in new thread\n");
|
||||||
h2 = ImmGetContext(info->hwnd);
|
h2 = ImmGetContext(info->hwnd);
|
||||||
todo_wine ok(h2 != h1, "new hwnd in new thread should have different context\n");
|
ok(h2 != h1, "new hwnd in new thread should have different context\n");
|
||||||
info->himc = h2;
|
info->himc = h2;
|
||||||
ImmReleaseContext(hwnd,h1);
|
ImmReleaseContext(hwnd,h1);
|
||||||
|
|
||||||
|
@ -452,7 +454,12 @@ static DWORD WINAPI ImmGetContextThreadFunc( LPVOID lpParam)
|
||||||
ImmSetStatusWindowPos(h1, &pt);
|
ImmSetStatusWindowPos(h1, &pt);
|
||||||
|
|
||||||
SetEvent(info->event);
|
SetEvent(info->event);
|
||||||
Sleep(INFINITE);
|
|
||||||
|
while(GetMessageW(&msg, 0, 0, 0))
|
||||||
|
{
|
||||||
|
TranslateMessage(&msg);
|
||||||
|
DispatchMessageW(&msg);
|
||||||
|
}
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -477,8 +484,8 @@ static void test_ImmThreads(void)
|
||||||
|
|
||||||
otherHimc = ImmGetContext(threadinfo.hwnd);
|
otherHimc = ImmGetContext(threadinfo.hwnd);
|
||||||
|
|
||||||
todo_wine ok(himc != otherHimc, "Windows from other threads should have different himc\n");
|
ok(himc != otherHimc, "Windows from other threads should have different himc\n");
|
||||||
todo_wine ok(otherHimc == threadinfo.himc, "Context from other thread should not change in main thread\n");
|
ok(otherHimc == threadinfo.himc, "Context from other thread should not change in main thread\n");
|
||||||
|
|
||||||
if (0) /* FIXME: Causes wine to hang */
|
if (0) /* FIXME: Causes wine to hang */
|
||||||
{
|
{
|
||||||
|
@ -566,7 +573,7 @@ static void test_ImmThreads(void)
|
||||||
ok (rc == 1, "ImmGetCandidateWindow should succeed\n");
|
ok (rc == 1, "ImmGetCandidateWindow should succeed\n");
|
||||||
|
|
||||||
rc = ImmGetCandidateWindow(otherHimc, 0, &cdf);
|
rc = ImmGetCandidateWindow(otherHimc, 0, &cdf);
|
||||||
todo_wine ok (rc == 0, "ImmGetCandidateWindow should fail\n");
|
ok (rc == 0, "ImmGetCandidateWindow should fail\n");
|
||||||
rc = ImmSetCandidateWindow(otherHimc, &cdf);
|
rc = ImmSetCandidateWindow(otherHimc, &cdf);
|
||||||
todo_wine ok (rc == 0, "ImmSetCandidateWindow should fail\n");
|
todo_wine ok (rc == 0, "ImmSetCandidateWindow should fail\n");
|
||||||
|
|
||||||
|
@ -577,7 +584,7 @@ static void test_ImmThreads(void)
|
||||||
TerminateThread(hThread, 1);
|
TerminateThread(hThread, 1);
|
||||||
|
|
||||||
himc = ImmGetContext(GetDesktopWindow());
|
himc = ImmGetContext(GetDesktopWindow());
|
||||||
todo_wine ok(himc == NULL, "Should not be able to get himc from other process window\n");
|
ok(himc == NULL, "Should not be able to get himc from other process window\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
static void test_ImmIsUIMessage(void)
|
static void test_ImmIsUIMessage(void)
|
||||||
|
|
Loading…
Reference in New Issue