391 lines
9.3 KiB
C++
391 lines
9.3 KiB
C++
/* RageInputDevice - User input types. */
|
|
#ifndef RAGE_INPUT_DEVICE_H
|
|
#define RAGE_INPUT_DEVICE_H
|
|
|
|
#include "RageTimer.h"
|
|
#include "EnumHelper.h"
|
|
|
|
const int NUM_JOYSTICKS = 32;
|
|
const int NUM_PUMPS = 2;
|
|
|
|
enum InputDevice
|
|
{
|
|
DEVICE_KEYBOARD = 0,
|
|
DEVICE_JOY1,
|
|
DEVICE_JOY2,
|
|
DEVICE_JOY3,
|
|
DEVICE_JOY4,
|
|
DEVICE_JOY5,
|
|
DEVICE_JOY6,
|
|
DEVICE_JOY7,
|
|
DEVICE_JOY8,
|
|
DEVICE_JOY9,
|
|
DEVICE_JOY10,
|
|
DEVICE_JOY11,
|
|
DEVICE_JOY12,
|
|
DEVICE_JOY13,
|
|
DEVICE_JOY14,
|
|
DEVICE_JOY15,
|
|
DEVICE_JOY16,
|
|
DEVICE_JOY17,
|
|
DEVICE_JOY18,
|
|
DEVICE_JOY19,
|
|
DEVICE_JOY20,
|
|
DEVICE_JOY21,
|
|
DEVICE_JOY22,
|
|
DEVICE_JOY23,
|
|
DEVICE_JOY24,
|
|
DEVICE_JOY25,
|
|
DEVICE_JOY26,
|
|
DEVICE_JOY27,
|
|
DEVICE_JOY28,
|
|
DEVICE_JOY29,
|
|
DEVICE_JOY30,
|
|
DEVICE_JOY31,
|
|
DEVICE_JOY32,
|
|
DEVICE_PUMP1,
|
|
DEVICE_PUMP2,
|
|
DEVICE_MIDI,
|
|
DEVICE_MOUSE,
|
|
NUM_InputDevice, // leave this at the end
|
|
InputDevice_Invalid // means this is NULL
|
|
};
|
|
/** @brief A special foreach loop for each input device. */
|
|
#define FOREACH_InputDevice( i ) FOREACH_ENUM( InputDevice, i )
|
|
const RString& InputDeviceToString( InputDevice i );
|
|
InputDevice StringToInputDevice( const RString& s );
|
|
inline bool IsJoystick( InputDevice id ) { return DEVICE_JOY1 <= id && id < DEVICE_JOY1+NUM_JOYSTICKS; }
|
|
inline bool IsPump( InputDevice id ) { return DEVICE_PUMP1 <= id && id < DEVICE_PUMP1+NUM_PUMPS; }
|
|
inline bool IsMouse( InputDevice id ) { return id == DEVICE_MOUSE; }
|
|
|
|
struct InputDeviceInfo
|
|
{
|
|
InputDeviceInfo( InputDevice id_, RString sDesc_ ):
|
|
id(id_), sDesc(sDesc_) {}
|
|
|
|
InputDevice id;
|
|
RString sDesc;
|
|
|
|
bool operator==( const InputDeviceInfo &other ) const
|
|
{
|
|
return id == other.id &&
|
|
sDesc == other.sDesc;
|
|
}
|
|
};
|
|
|
|
enum InputDeviceState
|
|
{
|
|
InputDeviceState_Connected, // has an InputHandler and controller is plugged in
|
|
InputDeviceState_Unplugged, // has an InputHandler but controller is unplugged or lost wireless link
|
|
InputDeviceState_NeedsMultitap, // has an InputHandler but needs a multitap to function
|
|
InputDeviceState_NoInputHandler, // there is no InputHandler that implements this InputDevice
|
|
NUM_InputDeviceState,
|
|
InputDeviceState_Invalid
|
|
};
|
|
const RString& InputDeviceStateToString( InputDeviceState ids );
|
|
|
|
/* Only raw, unshifted keys go in this table; this doesn't include
|
|
* internationalized keyboards, only keys that we might actually want to test
|
|
* for programmatically. Any other keys are mapped to KEY_OTHER_0 and up. (If we
|
|
* want to support real international input, stick a wchar_t in DeviceInput.) */
|
|
|
|
enum DeviceButton
|
|
{
|
|
KEY_SPACE = 32,
|
|
KEY_EXCL = 33,
|
|
KEY_QUOTE = 34,
|
|
KEY_HASH = 35,
|
|
KEY_DOLLAR = 36,
|
|
KEY_PERCENT = 37,
|
|
KEY_AMPER = 38,
|
|
KEY_SQUOTE = 39,
|
|
KEY_LPAREN = 40,
|
|
KEY_RPAREN = 41,
|
|
KEY_ASTERISK= 42,
|
|
KEY_PLUS = 43,
|
|
KEY_COMMA = 44,
|
|
KEY_HYPHEN = 45,
|
|
KEY_PERIOD = 46,
|
|
KEY_SLASH = 47,
|
|
KEY_C0 = 48,
|
|
KEY_C1 = 49,
|
|
KEY_C2 = 50,
|
|
KEY_C3 = 51,
|
|
KEY_C4 = 52,
|
|
KEY_C5 = 53,
|
|
KEY_C6 = 54,
|
|
KEY_C7 = 55,
|
|
KEY_C8 = 56,
|
|
KEY_C9 = 57,
|
|
KEY_COLON = 58,
|
|
KEY_SEMICOLON = 59,
|
|
KEY_LANGLE = 60,
|
|
KEY_EQUAL = 61,
|
|
KEY_RANGLE = 62,
|
|
KEY_QUESTION= 63,
|
|
KEY_AT = 64,
|
|
KEY_CA = 65,
|
|
KEY_CB = 66,
|
|
KEY_CC = 67,
|
|
KEY_CD = 68,
|
|
KEY_CE = 69,
|
|
KEY_CF = 70,
|
|
KEY_CG = 71,
|
|
KEY_CH = 72,
|
|
KEY_CI = 73,
|
|
KEY_CJ = 74,
|
|
KEY_CK = 75,
|
|
KEY_CL = 76,
|
|
KEY_CM = 77,
|
|
KEY_CN = 78,
|
|
KEY_CO = 79,
|
|
KEY_CP = 80,
|
|
KEY_CQ = 81,
|
|
KEY_CR = 82,
|
|
KEY_CS = 83,
|
|
KEY_CT = 84,
|
|
KEY_CU = 85,
|
|
KEY_CV = 86,
|
|
KEY_CW = 87,
|
|
KEY_CX = 88,
|
|
KEY_CY = 89,
|
|
KEY_CZ = 90,
|
|
KEY_LBRACKET= 91,
|
|
KEY_BACKSLASH= 92,
|
|
KEY_RBRACKET= 93,
|
|
KEY_CARAT = 94,
|
|
KEY_UNDERSCORE= 95,
|
|
KEY_ACCENT = 96,
|
|
KEY_Ca = 97,
|
|
KEY_Cb = 98,
|
|
KEY_Cc = 99,
|
|
KEY_Cd = 100,
|
|
KEY_Ce = 101,
|
|
KEY_Cf = 102,
|
|
KEY_Cg = 103,
|
|
KEY_Ch = 104,
|
|
KEY_Ci = 105,
|
|
KEY_Cj = 106,
|
|
KEY_Ck = 107,
|
|
KEY_Cl = 108,
|
|
KEY_Cm = 109,
|
|
KEY_Cn = 110,
|
|
KEY_Co = 111,
|
|
KEY_Cp = 112,
|
|
KEY_Cq = 113,
|
|
KEY_Cr = 114,
|
|
KEY_Cs = 115,
|
|
KEY_Ct = 116,
|
|
KEY_Cu = 117,
|
|
KEY_Cv = 118,
|
|
KEY_Cw = 119,
|
|
KEY_Cx = 120,
|
|
KEY_Cy = 121,
|
|
KEY_Cz = 122,
|
|
KEY_LBRACE = 123,
|
|
KEY_PIPE = 124,
|
|
KEY_RBRACE = 125,
|
|
KEY_DEL = 127,
|
|
|
|
KEY_BACK,
|
|
KEY_TAB,
|
|
KEY_ENTER,
|
|
KEY_PAUSE,
|
|
KEY_ESC,
|
|
|
|
KEY_F1,
|
|
KEY_F2,
|
|
KEY_F3,
|
|
KEY_F4,
|
|
KEY_F5,
|
|
KEY_F6,
|
|
KEY_F7,
|
|
KEY_F8,
|
|
KEY_F9,
|
|
KEY_F10,
|
|
KEY_F11,
|
|
KEY_F12,
|
|
KEY_F13,
|
|
KEY_F14,
|
|
KEY_F15,
|
|
KEY_F16,
|
|
|
|
KEY_LCTRL,
|
|
KEY_RCTRL,
|
|
KEY_LSHIFT,
|
|
KEY_RSHIFT,
|
|
KEY_LALT,
|
|
KEY_RALT,
|
|
KEY_LMETA,
|
|
KEY_RMETA,
|
|
KEY_LSUPER,
|
|
KEY_RSUPER,
|
|
KEY_MENU,
|
|
|
|
KEY_NUMLOCK,
|
|
KEY_SCRLLOCK,
|
|
KEY_CAPSLOCK,
|
|
KEY_PRTSC,
|
|
|
|
KEY_UP,
|
|
KEY_DOWN,
|
|
KEY_LEFT,
|
|
KEY_RIGHT,
|
|
|
|
KEY_INSERT,
|
|
KEY_HOME,
|
|
KEY_END,
|
|
KEY_PGUP,
|
|
KEY_PGDN,
|
|
|
|
KEY_KP_C0,
|
|
KEY_KP_C1,
|
|
KEY_KP_C2,
|
|
KEY_KP_C3,
|
|
KEY_KP_C4,
|
|
KEY_KP_C5,
|
|
KEY_KP_C6,
|
|
KEY_KP_C7,
|
|
KEY_KP_C8,
|
|
KEY_KP_C9,
|
|
KEY_KP_SLASH,
|
|
KEY_KP_ASTERISK,
|
|
KEY_KP_HYPHEN,
|
|
KEY_KP_PLUS,
|
|
KEY_KP_PERIOD,
|
|
KEY_KP_EQUAL,
|
|
KEY_KP_ENTER,
|
|
|
|
KEY_OTHER_0,
|
|
// ...
|
|
KEY_LAST_OTHER=511,
|
|
|
|
/* Joystick inputs. We try to have enough input names so any input on a
|
|
* reasonable joystick has an obvious mapping, but keep it generic and don't
|
|
* try to handle odd special cases. For example, many controllers have two
|
|
* sticks, so the JOY_LEFT_2, etc. pairs are useful for many types of sticks. */
|
|
// Standard axis:
|
|
JOY_LEFT, JOY_RIGHT, JOY_UP, JOY_DOWN,
|
|
|
|
// Secondary sticks:
|
|
JOY_LEFT_2, JOY_RIGHT_2, JOY_UP_2, JOY_DOWN_2,
|
|
|
|
JOY_Z_UP, JOY_Z_DOWN,
|
|
JOY_ROT_UP, JOY_ROT_DOWN, JOY_ROT_LEFT, JOY_ROT_RIGHT, JOY_ROT_Z_UP, JOY_ROT_Z_DOWN,
|
|
JOY_HAT_LEFT, JOY_HAT_RIGHT, JOY_HAT_UP, JOY_HAT_DOWN,
|
|
JOY_AUX_1, JOY_AUX_2, JOY_AUX_3, JOY_AUX_4,
|
|
|
|
// Buttons:
|
|
JOY_BUTTON_1, JOY_BUTTON_2, JOY_BUTTON_3, JOY_BUTTON_4, JOY_BUTTON_5,
|
|
JOY_BUTTON_6, JOY_BUTTON_7, JOY_BUTTON_8, JOY_BUTTON_9, JOY_BUTTON_10,
|
|
JOY_BUTTON_11, JOY_BUTTON_12, JOY_BUTTON_13, JOY_BUTTON_14, JOY_BUTTON_15,
|
|
JOY_BUTTON_16, JOY_BUTTON_17, JOY_BUTTON_18, JOY_BUTTON_19, JOY_BUTTON_20,
|
|
JOY_BUTTON_21, JOY_BUTTON_22, JOY_BUTTON_23, JOY_BUTTON_24, JOY_BUTTON_25,
|
|
JOY_BUTTON_26, JOY_BUTTON_27, JOY_BUTTON_28, JOY_BUTTON_29, JOY_BUTTON_30,
|
|
JOY_BUTTON_31, JOY_BUTTON_32,
|
|
|
|
MIDI_FIRST = 600,
|
|
MIDI_LAST = 699,
|
|
|
|
// Mouse buttons
|
|
MOUSE_LEFT = 700,
|
|
MOUSE_RIGHT,
|
|
MOUSE_MIDDLE,
|
|
// axis
|
|
MOUSE_X_LEFT, MOUSE_X_RIGHT,
|
|
MOUSE_Y_UP, MOUSE_Y_DOWN,
|
|
// Mouse wheel (z axis)
|
|
MOUSE_WHEELUP, MOUSE_WHEELDOWN,
|
|
|
|
NUM_DeviceButton,
|
|
DeviceButton_Invalid
|
|
};
|
|
|
|
RString DeviceButtonToString( DeviceButton i );
|
|
DeviceButton StringToDeviceButton( const RString& s );
|
|
|
|
struct DeviceInput
|
|
{
|
|
public:
|
|
InputDevice device;
|
|
DeviceButton button;
|
|
|
|
/* This is usually 0 or 1. Analog joystick inputs can set this to a percentage
|
|
* (0..1). This should be 0 for analog axes within the dead zone. */
|
|
float level;
|
|
|
|
// Mouse coordinates
|
|
//unsigned x;
|
|
//unsigned y;
|
|
int z; // mousewheel
|
|
|
|
/* Whether this button is pressed. This is level with a threshold and
|
|
* debouncing applied. */
|
|
bool bDown;
|
|
|
|
RageTimer ts;
|
|
|
|
DeviceInput(): device(InputDevice_Invalid), button(DeviceButton_Invalid), level(0), z(0), bDown(false), ts(RageZeroTimer) { }
|
|
DeviceInput( InputDevice d, DeviceButton b, float l=0 ): device(d), button(b), level(l), z(0), bDown(l > 0.5f), ts(RageZeroTimer) { }
|
|
DeviceInput( InputDevice d, DeviceButton b, float l, const RageTimer &t ):
|
|
device(d), button(b), level(l), z(0), bDown(level > 0.5f), ts(t) { }
|
|
DeviceInput( InputDevice d, DeviceButton b, const RageTimer &t, int zVal=0 ):
|
|
device(d), button(b), level(0), z(zVal), bDown(false), ts(t) { }
|
|
|
|
bool operator==( const DeviceInput &other ) const
|
|
{
|
|
/* Return true if we represent the same button on the same device.
|
|
* Don't compare level or ts. */
|
|
return device == other.device && button == other.button;
|
|
}
|
|
bool operator!=( const DeviceInput &other ) const
|
|
{
|
|
return ! operator==( other );
|
|
}
|
|
bool operator<( const DeviceInput &other ) const
|
|
{
|
|
/* Return true if we represent the same button on the same device.
|
|
* Don't compare level or ts. */
|
|
if( device != other.device )
|
|
return device < other.device;
|
|
return button < other.button;
|
|
}
|
|
|
|
RString ToString() const;
|
|
bool FromString( const RString &s );
|
|
|
|
bool IsValid() const { return device != InputDevice_Invalid; };
|
|
void MakeInvalid() { device = InputDevice_Invalid; };
|
|
|
|
bool IsJoystick() const { return ::IsJoystick(device); }
|
|
bool IsMouse() const { return ::IsMouse(device); }
|
|
};
|
|
|
|
typedef vector<DeviceInput> DeviceInputList;
|
|
|
|
#endif
|
|
/*
|
|
* Copyright (c) 2001-2002 Chris Danford
|
|
* All rights reserved.
|
|
*
|
|
* Permission is hereby granted, free of charge, to any person obtaining a
|
|
* copy of this software and associated documentation files (the
|
|
* "Software"), to deal in the Software without restriction, including
|
|
* without limitation the rights to use, copy, modify, merge, publish,
|
|
* distribute, and/or sell copies of the Software, and to permit persons to
|
|
* whom the Software is furnished to do so, provided that the above
|
|
* copyright notice(s) and this permission notice appear in all copies of
|
|
* the Software and that both the above copyright notice(s) and this
|
|
* permission notice appear in supporting documentation.
|
|
*
|
|
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
|
* OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
|
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT OF
|
|
* THIRD PARTY RIGHTS. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR HOLDERS
|
|
* INCLUDED IN THIS NOTICE BE LIABLE FOR ANY CLAIM, OR ANY SPECIAL INDIRECT
|
|
* OR CONSEQUENTIAL DAMAGES, OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
|
|
* OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
|
* OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
|
* PERFORMANCE OF THIS SOFTWARE.
|
|
*/
|