2009-02-11 20:47:41 +00:00
|
|
|
#include "Global.h"
|
2009-09-25 08:36:42 +00:00
|
|
|
#include "InputManager.h"
|
2009-02-11 09:24:56 +00:00
|
|
|
#include "WindowsMessaging.h"
|
|
|
|
#include "VKey.h"
|
|
|
|
#include "DeviceEnumerator.h"
|
|
|
|
#include "WndProcEater.h"
|
|
|
|
#include "WindowsKeyboard.h"
|
|
|
|
#include "WindowsMouse.h"
|
|
|
|
|
2009-09-21 00:24:04 +00:00
|
|
|
ExtraWndProcResult WindowsMessagingWndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, LRESULT *output);
|
|
|
|
|
|
|
|
class WindowsMessagingKeyboard;
|
|
|
|
class WindowsMessagingMouse;
|
|
|
|
|
|
|
|
static WindowsMessagingKeyboard *wmk = 0;
|
|
|
|
static WindowsMessagingMouse *wmm = 0;
|
|
|
|
|
2009-02-11 09:24:56 +00:00
|
|
|
class WindowsMessagingKeyboard : public WindowsKeyboard {
|
|
|
|
public:
|
|
|
|
|
|
|
|
WindowsMessagingKeyboard() : WindowsKeyboard(WM, L"WM Keyboard") {
|
|
|
|
}
|
|
|
|
|
2009-09-20 10:48:22 +00:00
|
|
|
int Activate(InitInfo *initInfo) {
|
2009-09-21 00:24:04 +00:00
|
|
|
// Redundant. Should match the next line.
|
|
|
|
// Deactivate();
|
|
|
|
if (wmk) wmk->Deactivate();
|
|
|
|
HWND hWnd = initInfo->hWnd;
|
|
|
|
if (initInfo->hWndButton) {
|
|
|
|
hWnd = initInfo->hWndButton;
|
|
|
|
}
|
|
|
|
if (!wmm && !EatWndProc(hWnd, WindowsMessagingWndProc, EATPROC_NO_UPDATE_WHILE_UPDATING_DEVICES)) {
|
|
|
|
Deactivate();
|
|
|
|
return 0;
|
|
|
|
}
|
2009-02-11 09:24:56 +00:00
|
|
|
|
2009-09-21 00:24:04 +00:00
|
|
|
wmk = this;
|
2009-02-11 09:24:56 +00:00
|
|
|
InitState();
|
|
|
|
|
|
|
|
active = 1;
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
void Deactivate() {
|
2009-09-21 00:24:04 +00:00
|
|
|
if (active) {
|
|
|
|
if (!wmm)
|
|
|
|
ReleaseExtraProc(WindowsMessagingWndProc);
|
|
|
|
wmk = 0;
|
|
|
|
active = 0;
|
|
|
|
FreeState();
|
2009-09-20 10:48:22 +00:00
|
|
|
}
|
|
|
|
}
|
2009-02-11 09:24:56 +00:00
|
|
|
|
2009-09-21 00:24:04 +00:00
|
|
|
|
2009-02-11 09:24:56 +00:00
|
|
|
void CheckKey(int vkey) {
|
|
|
|
UpdateKey(vkey, 1&(((unsigned short)GetAsyncKeyState(vkey))>>15));
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
class WindowsMessagingMouse : public WindowsMouse {
|
|
|
|
public:
|
2009-09-21 00:24:04 +00:00
|
|
|
|
2009-02-11 09:24:56 +00:00
|
|
|
WindowsMessagingMouse() : WindowsMouse(WM, 1, L"WM Mouse") {
|
|
|
|
}
|
|
|
|
|
2009-09-20 10:48:22 +00:00
|
|
|
int Activate(InitInfo *initInfo) {
|
2009-02-11 09:24:56 +00:00
|
|
|
// Redundant. Should match the next line.
|
2009-09-21 00:24:04 +00:00
|
|
|
// Deactivate();
|
2009-02-11 09:24:56 +00:00
|
|
|
if (wmm) wmm->Deactivate();
|
2009-09-20 10:48:22 +00:00
|
|
|
HWND hWnd = initInfo->hWnd;
|
|
|
|
if (initInfo->hWndButton) {
|
|
|
|
hWnd = initInfo->hWndButton;
|
2009-02-11 09:24:56 +00:00
|
|
|
}
|
|
|
|
|
2009-09-21 00:24:04 +00:00
|
|
|
if (!wmk && !EatWndProc(hWnd, WindowsMessagingWndProc, EATPROC_NO_UPDATE_WHILE_UPDATING_DEVICES)) {
|
2009-02-11 09:24:56 +00:00
|
|
|
Deactivate();
|
|
|
|
return 0;
|
|
|
|
}
|
2009-03-31 08:15:38 +00:00
|
|
|
GetMouseCapture(hWnd);
|
2009-02-11 09:24:56 +00:00
|
|
|
|
|
|
|
active = 1;
|
2009-02-17 04:54:46 +00:00
|
|
|
|
2009-02-11 09:24:56 +00:00
|
|
|
wmm = this;
|
|
|
|
AllocState();
|
|
|
|
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
void Deactivate() {
|
|
|
|
if (active) {
|
2009-09-21 00:24:04 +00:00
|
|
|
if (!wmk)
|
|
|
|
ReleaseExtraProc(WindowsMessagingWndProc);
|
2009-04-19 23:04:21 +00:00
|
|
|
ReleaseMouseCapture();
|
2009-02-11 09:24:56 +00:00
|
|
|
wmm = 0;
|
2009-04-19 23:04:21 +00:00
|
|
|
active = 0;
|
|
|
|
FreeState();
|
2009-02-11 09:24:56 +00:00
|
|
|
}
|
|
|
|
}
|
2009-09-21 00:24:04 +00:00
|
|
|
};
|
2009-02-11 09:24:56 +00:00
|
|
|
|
2009-09-21 00:24:04 +00:00
|
|
|
ExtraWndProcResult WindowsMessagingWndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, LRESULT *output) {
|
|
|
|
if (wmk) {
|
|
|
|
if (uMsg == WM_KEYDOWN || uMsg == WM_SYSKEYDOWN || uMsg == WM_KEYUP || uMsg == WM_SYSKEYUP) {
|
|
|
|
if (wParam == VK_SHIFT) {
|
|
|
|
wmk->CheckKey(VK_RSHIFT);
|
|
|
|
wmk->CheckKey(VK_LSHIFT);
|
2009-02-11 09:24:56 +00:00
|
|
|
}
|
2009-09-21 00:24:04 +00:00
|
|
|
else if (wParam == VK_CONTROL) {
|
|
|
|
wmk->CheckKey(VK_RCONTROL);
|
|
|
|
wmk->CheckKey(VK_LCONTROL);
|
2009-02-11 09:24:56 +00:00
|
|
|
}
|
2009-09-21 00:24:04 +00:00
|
|
|
else if (wParam == VK_MENU) {
|
|
|
|
wmk->CheckKey(VK_RMENU);
|
|
|
|
wmk->CheckKey(VK_LMENU);
|
2009-02-11 09:24:56 +00:00
|
|
|
}
|
2009-09-21 00:24:04 +00:00
|
|
|
else
|
|
|
|
wmk->UpdateKey(wParam, (uMsg == WM_KEYDOWN || uMsg == WM_SYSKEYDOWN));
|
|
|
|
return NO_WND_PROC;
|
|
|
|
}
|
|
|
|
// Needed to prevent default handling of keys in some situations.
|
|
|
|
else if (uMsg == WM_CHAR || uMsg == WM_UNICHAR) {
|
|
|
|
return NO_WND_PROC;
|
|
|
|
}
|
|
|
|
else if (uMsg == WM_ACTIVATE) {
|
|
|
|
// Not really needed, but doesn't hurt.
|
|
|
|
memset(wmk->physicalControlState, 0, sizeof(int) * wmk->numPhysicalControls);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if (wmm) {
|
|
|
|
if (uMsg == WM_MOUSEMOVE) {
|
|
|
|
POINT p;
|
|
|
|
GetCursorPos(&p);
|
|
|
|
// Need check to prevent cursor movement cascade.
|
|
|
|
if (p.x != wmm->center.x || p.y != wmm->center.y) {
|
|
|
|
wmm->UpdateAxis(0, p.x - wmm->center.x);
|
|
|
|
wmm->UpdateAxis(1, p.y - wmm->center.y);
|
|
|
|
|
|
|
|
SetCursorPos(wmm->center.x, wmm->center.y);
|
2009-09-20 10:48:22 +00:00
|
|
|
}
|
2009-09-21 00:24:04 +00:00
|
|
|
return NO_WND_PROC;
|
|
|
|
}
|
|
|
|
else if (uMsg == WM_LBUTTONDOWN || uMsg == WM_LBUTTONUP) {
|
|
|
|
wmm->UpdateButton(0, uMsg == WM_LBUTTONDOWN);
|
|
|
|
return NO_WND_PROC;
|
|
|
|
}
|
|
|
|
else if (uMsg == WM_RBUTTONDOWN || uMsg == WM_RBUTTONUP) {
|
|
|
|
wmm->UpdateButton(1, uMsg == WM_RBUTTONDOWN);
|
|
|
|
return NO_WND_PROC;
|
|
|
|
}
|
|
|
|
else if (uMsg == WM_MBUTTONDOWN || uMsg == WM_MBUTTONUP) {
|
|
|
|
wmm->UpdateButton(2, uMsg == WM_MBUTTONDOWN);
|
|
|
|
return NO_WND_PROC;
|
|
|
|
}
|
|
|
|
else if (uMsg == WM_XBUTTONDOWN || uMsg == WM_XBUTTONUP) {
|
|
|
|
wmm->UpdateButton(3+((wParam>>16) == XBUTTON2), uMsg == WM_XBUTTONDOWN);
|
|
|
|
return NO_WND_PROC;
|
2009-03-31 08:15:38 +00:00
|
|
|
}
|
2009-09-21 00:24:04 +00:00
|
|
|
else if (uMsg == WM_MOUSEWHEEL) {
|
|
|
|
wmm->UpdateAxis(2, ((int)wParam>>16)/WHEEL_DELTA);
|
|
|
|
return NO_WND_PROC;
|
|
|
|
}
|
|
|
|
else if (uMsg == WM_MOUSEHWHEEL) {
|
|
|
|
wmm->UpdateAxis(3, ((int)wParam>>16)/WHEEL_DELTA);
|
|
|
|
return NO_WND_PROC;
|
|
|
|
}
|
|
|
|
else if (uMsg == WM_SIZE && wmm->active) {
|
|
|
|
WindowsMouse::WindowResized(hWnd);
|
|
|
|
}
|
|
|
|
// Taken care of elsewhere. When binding, killing focus means stop reading input.
|
|
|
|
// When running PCSX2, I release all mouse and keyboard input elsewhere.
|
|
|
|
/*else if (uMsg == WM_KILLFOCUS) {
|
|
|
|
wmm->Deactivate();
|
|
|
|
}//*/
|
2009-02-11 09:24:56 +00:00
|
|
|
}
|
2009-09-21 00:24:04 +00:00
|
|
|
return CONTINUE_BLISSFULLY;
|
|
|
|
}
|
2009-02-11 09:24:56 +00:00
|
|
|
|
|
|
|
void EnumWindowsMessagingDevices() {
|
|
|
|
dm->AddDevice(new WindowsMessagingKeyboard());
|
|
|
|
dm->AddDevice(new WindowsMessagingMouse());
|
|
|
|
}
|