I have been trying to make SetKeyboardState press keys for an application, kind of just to see if it will work. Originally, I made this, because I thought scanf would block and I needed this to make keypresses
Code:
DWORD WINAPI ThreadRoutine(LPVOID lpParam)
{
BYTE o[256];
BYTE n[256];
::GetKeyboardState(o);
::CopyMemory(n, o, sizeof(o));
n['A'] = 1;
::SetKeyboardState(n); // Make changes
::SetKeyboardState(o); // Restore old
return 0;
}
int main(void)
{
char junk;
HANDLE hThread;
hThread = ::CreateThread(NULL, 0, ThreadRoutine, NULL, 0, NULL);
scanf("%c", &junk);
::WaitForSingleObject(hThread, INFINITE);
::CloseHandle(hThread);
return 0;
}
But MSDN says something about 'the SetKeyboardState function alters the input state of the calling thread', so I guess that would not work? I then tried this with a win32 app that would recieve WM_KEYDOWN messages that might be generated by the API, buit it also fails.
Code:
LRESULT CALLBACK WndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
switch(uMsg)
{
case WM_CREATE:
::SetTimer(hWnd, 0x1000, 100, NULL);
case WM_TIMER:
{
BYTE o[256];
BYTE n[256];
::GetKeyboardState(o);
::CopyMemory(n, o, sizeof(o));
n['T'] = 1;
::SetKeyboardState(n); // Make changes
::SetKeyboardState(o); // Restore old
break;
}
case WM_DESTROY:
::KillTimer(hWnd, 0x1000);
::PostQuitMessage(WM_QUIT);
break;
case WM_KEYDOWN:
TCHAR sZ[256];
wsprintf(sZ, _T("%c"), wParam);
::MessageBox
(hWnd, sZ, sZ, MB_OK);
break;
case WM_CLOSE:
::DestroyWindow(hWnd);
break;
default: return ::DefWindowProc(hWnd, uMsg, wParam, lParam);
}
return 0;
}
Is there something else I should be looking for when using this API?