Clean up "ControllerInterface" a bit.

git-svn-id: https://dolphin-emu.googlecode.com/svn/trunk@7339 8ced0084-cf51-0410-be5f-012b33b47a6e
This commit is contained in:
Jordan Woyak 2011-03-14 01:20:11 +00:00
parent 37e31f2df6
commit 8fedc3db38
16 changed files with 416 additions and 659 deletions

View File

@ -15,10 +15,10 @@
#ifdef CIFACE_USE_SDL #ifdef CIFACE_USE_SDL
#include "SDL/SDL.h" #include "SDL/SDL.h"
#endif #endif
#include "Thread.h" #include "Thread.h"
#define INPUT_DETECT_THRESHOLD 0.85f
#define INPUT_DETECT_THRESHOLD 0.85
ControllerInterface g_controller_interface; ControllerInterface g_controller_interface;
@ -71,7 +71,7 @@ void ControllerInterface::Shutdown()
oe = (*d)->Outputs().end(); oe = (*d)->Outputs().end();
// set outputs to ZERO before destroying device // set outputs to ZERO before destroying device
for ( ;o!=oe; ++o) for ( ;o!=oe; ++o)
(*d)->SetOutputState(*o, 0); (*o)->SetState(0);
// update output // update output
(*d)->UpdateOutput(); (*d)->UpdateOutput();
@ -234,14 +234,14 @@ ControlState ControllerInterface::InputReference::State( const ControlState igno
ci = m_controls.begin(), ci = m_controls.begin(),
ce = m_controls.end(); ce = m_controls.end();
// bit of hax for NOT to work at start of expression // bit of hax for "NOT" to work at start of expression
if (ci != ce) if (ci != ce)
if (ci->mode == 2) if (ci->mode == 2)
state = 1; state = 1;
for (; ci!=ce; ++ci) for (; ci!=ce; ++ci)
{ {
const ControlState istate = ci->device->GetInputState((Device::Input*)ci->control); const ControlState istate = ci->control->ToInput()->GetState();
switch (ci->mode) switch (ci->mode)
{ {
@ -284,7 +284,7 @@ ControlState ControllerInterface::OutputReference::State(const ControlState stat
ci = m_controls.begin(), ci = m_controls.begin(),
ce = m_controls.end(); ce = m_controls.end();
for (; ci != ce; ++ci) for (; ci != ce; ++ci)
ci->device->SetOutputState((Device::Output*)ci->control, tmp_state); ci->control->ToOutput()->SetState(tmp_state);
return state; // just return the output, watever return state; // just return the output, watever
} }
@ -345,11 +345,6 @@ bool ControllerInterface::DeviceQualifier::operator==(const ControllerInterface:
return false; return false;
} }
bool ControllerInterface::Device::Control::operator==(const std::string& name) const
{
return GetName() == name;
}
bool ControllerInterface::DeviceQualifier::operator==(const ControllerInterface::DeviceQualifier& devq) const bool ControllerInterface::DeviceQualifier::operator==(const ControllerInterface::DeviceQualifier& devq) const
{ {
if (cid == devq.cid) if (cid == devq.cid)
@ -399,74 +394,21 @@ void ControllerInterface::UpdateReference(ControllerInterface::ControlReference*
devq.FromString(dev_str); devq.FromString(dev_str);
// find device // find device
devc.device = FindDevice(devq); Device* const def_device = FindDevice(devq);
if (devc.device) if (def_device)
{ {
// control
// inputs or outputs, i don't like this
if (ref->is_input) if (ref->is_input)
{ devc.control = FindInput(ctrl_str, def_device);
std::vector<Device::Input*>::const_iterator i;
// FIXME: Use std::find instead of a for loop
// i = std::find(devc.device->Inputs().begin(), devc.device->Inputs().end(), ctrl_str);
for(i = devc.device->Inputs().begin(); i < devc.device->Inputs().end(); ++i)
if(*(*i) == ctrl_str)
break;
if (devc.device->Inputs().end() != i)
{
devc.control = *i;
ref->m_controls.push_back(devc);
}
else
{
// the input wasn't found, look through all the other devices
std::vector<Device*>::const_iterator
deviter = m_devices.begin(),
devend = m_devices.end();
for(; deviter != devend; ++deviter)
{
for(i = (*deviter)->Inputs().begin(); i < (*deviter)->Inputs().end(); ++i)
if(*(*i) == ctrl_str)
break;
if ((*deviter)->Inputs().end() != i)
{
devc.device = *deviter;
devc.control = *i;
ref->m_controls.push_back(devc);
break;
}
}
}
}
else else
{ devc.control = FindOutput(ctrl_str, def_device);
std::vector<Device::Output*>::const_iterator i;
// FIXME: Use std::find instead of a for loop
// i = std::find(devc.device->Outputs().begin(), devc.device->Outputs().end(), ctrl_str);
for(i = devc.device->Outputs().begin(); i < devc.device->Outputs().end(); ++i)
if(*(*i) == ctrl_str)
break;
if (devc.device->Outputs().end() != i)
{
devc.control = *i;
ref->m_controls.push_back(devc);
}
}
if (devc.control)
ref->m_controls.push_back(devc);
} }
} }
// reset stuff for next ctrl // reset stuff for next ctrl
devc.mode = (int)f; devc.mode = (int)f;
devc.device = NULL;
ctrl_str.clear(); ctrl_str.clear();
} }
else if ('`' == c) else if ('`' == c)
@ -516,7 +458,7 @@ ControllerInterface::Device::Control* ControllerInterface::InputReference::Detec
i = device->Inputs().begin(), i = device->Inputs().begin(),
e = device->Inputs().end(); e = device->Inputs().end();
for (bool* state=states; i != e; ++i) for (bool* state=states; i != e; ++i)
*state++ = (device->GetInputState(*i) > INPUT_DETECT_THRESHOLD); *state++ = ((*i)->GetState() > INPUT_DETECT_THRESHOLD);
while (time < ms) while (time < ms)
{ {
@ -525,7 +467,7 @@ ControllerInterface::Device::Control* ControllerInterface::InputReference::Detec
for (bool* state=states; i != e; ++i,++state) for (bool* state=states; i != e; ++i,++state)
{ {
// detected an input // detected an input
if ((*i)->IsDetectable() && device->GetInputState(*i) > INPUT_DETECT_THRESHOLD) if ((*i)->IsDetectable() && (*i)->GetState() > INPUT_DETECT_THRESHOLD)
{ {
// input was released at some point during Detect call // input was released at some point during Detect call
// return the detected input // return the detected input
@ -575,3 +517,51 @@ ControllerInterface::Device::Control* ControllerInterface::OutputReference::Dete
} }
return NULL; return NULL;
} }
ControllerInterface::Device::Input* ControllerInterface::Device::FindInput(const std::string &name) const
{
std::vector<Input*>::const_iterator
it = m_inputs.begin(),
itend = m_inputs.end();
for (; it != itend; ++it)
if ((*it)->GetName() == name)
return *it;
return NULL;
}
ControllerInterface::Device::Output* ControllerInterface::Device::FindOutput(const std::string &name) const
{
std::vector<Output*>::const_iterator
it = m_outputs.begin(),
itend = m_outputs.end();
for (; it != itend; ++it)
if ((*it)->GetName() == name)
return *it;
return NULL;
}
ControllerInterface::Device::Input* ControllerInterface::FindInput(const std::string& name, const Device* def_dev) const
{
if (def_dev)
return def_dev->FindInput(name);
std::vector<Device*>::const_iterator
di = m_devices.begin(),
de = m_devices.end();
for (; di != de; ++di)
{
Device::Input* const i = (*di)->FindInput(name);
if (i)
return i;
}
return NULL;
}
ControllerInterface::Device::Output* ControllerInterface::FindOutput(const std::string& name, const Device* def_dev) const
{
return def_dev->FindOutput(name);
}

View File

@ -54,6 +54,8 @@ public:
class Device class Device
{ {
public: public:
class Input;
class Output;
// //
// Control // Control
@ -65,7 +67,9 @@ public:
public: public:
virtual std::string GetName() const = 0; virtual std::string GetName() const = 0;
virtual ~Control() {} virtual ~Control() {}
bool operator==(const std::string& name) const;
virtual Input* ToInput() { return NULL; }
virtual Output* ToOutput() { return NULL; }
}; };
// //
@ -78,6 +82,10 @@ public:
public: public:
// things like absolute axes/ absolute mouse position will override this // things like absolute axes/ absolute mouse position will override this
virtual bool IsDetectable() { return true; } virtual bool IsDetectable() { return true; }
virtual ControlState GetState() const = 0;
Input* ToInput() { return this; }
}; };
// //
@ -89,6 +97,10 @@ public:
{ {
public: public:
virtual ~Output() {} virtual ~Output() {}
virtual void SetState(ControlState state) = 0;
Output* ToOutput() { return this; }
}; };
virtual ~Device(); virtual ~Device();
@ -96,10 +108,6 @@ public:
virtual std::string GetName() const = 0; virtual std::string GetName() const = 0;
virtual int GetId() const = 0; virtual int GetId() const = 0;
virtual std::string GetSource() const = 0; virtual std::string GetSource() const = 0;
virtual ControlState GetInputState( const Input* const input ) const = 0;
virtual void SetOutputState( const Output* const output, const ControlState state ) = 0;
virtual bool UpdateInput() = 0; virtual bool UpdateInput() = 0;
virtual bool UpdateOutput() = 0; virtual bool UpdateOutput() = 0;
@ -108,6 +116,9 @@ public:
const std::vector<Input*>& Inputs() const { return m_inputs; } const std::vector<Input*>& Inputs() const { return m_inputs; }
const std::vector<Output*>& Outputs() const { return m_outputs; } const std::vector<Output*>& Outputs() const { return m_outputs; }
Input* FindInput(const std::string& name) const;
Output* FindOutput(const std::string& name) const;
protected: protected:
void AddInput(Input* const i); void AddInput(Input* const i);
void AddOutput(Output* const o); void AddOutput(Output* const o);
@ -115,7 +126,6 @@ public:
private: private:
std::vector<Input*> m_inputs; std::vector<Input*> m_inputs;
std::vector<Output*> m_outputs; std::vector<Output*> m_outputs;
}; };
// //
@ -171,9 +181,8 @@ public:
struct DeviceControl struct DeviceControl
{ {
DeviceControl() : device(NULL), control(NULL), mode(0) {} DeviceControl() : control(NULL), mode(0) {}
Device* device;
Device::Control* control; Device::Control* control;
int mode; int mode;
}; };
@ -211,7 +220,6 @@ public:
void SetHwnd(void* const hwnd); void SetHwnd(void* const hwnd);
void Initialize(); void Initialize();
// TODO: remove this hack param
void Shutdown(); void Shutdown();
bool IsInit() const { return m_is_init; } bool IsInit() const { return m_is_init; }
@ -219,6 +227,9 @@ public:
bool UpdateInput(const bool force = false); bool UpdateInput(const bool force = false);
bool UpdateOutput(const bool force = false); bool UpdateOutput(const bool force = false);
Device::Input* FindInput(const std::string& name, const Device* def_dev) const;
Device::Output* FindOutput(const std::string& name, const Device* def_dev) const;
const std::vector<Device*>& Devices() const { return m_devices; } const std::vector<Device*>& Devices() const { return m_devices; }
Device* FindDevice(const DeviceQualifier& devq) const; Device* FindDevice(const DeviceQualifier& devq) const;
@ -230,6 +241,8 @@ private:
void* m_hwnd; void* m_hwnd;
}; };
typedef std::vector<ControllerInterface::Device*> DeviceList;
extern ControllerInterface g_controller_interface; extern ControllerInterface g_controller_interface;
#endif #endif

View File

@ -233,15 +233,15 @@ Joystick::Joystick( /*const LPCDIDEVICEINSTANCE lpddi, */const LPDIRECTINPUTDEVI
//m_must_poll = (js_caps.dwFlags & DIDC_POLLEDDATAFORMAT) != 0; //m_must_poll = (js_caps.dwFlags & DIDC_POLLEDDATAFORMAT) != 0;
// buttons // buttons
for ( unsigned int i = 0; i < js_caps.dwButtons; ++i ) for (u8 i = 0; i != js_caps.dwButtons; ++i)
AddInput( new Button( i ) ); AddInput(new Button(i, m_state_in.rgbButtons[m_index]));
// hats // hats
for ( unsigned int i = 0; i < js_caps.dwPOVs; ++i ) for (u8 i = 0; i != js_caps.dwPOVs; ++i)
{ {
// each hat gets 4 input instances associated with it, (up down left right) // each hat gets 4 input instances associated with it, (up down left right)
for ( unsigned int d = 0; d<4; ++d ) for (u8 d = 0; d != 4; ++d)
AddInput( new Hat( i, d ) ); AddInput(new Hat(i, m_state_in.rgdwPOV[m_index], d));
} }
// get up to 6 axes and 2 sliders // get up to 6 axes and 2 sliders
@ -264,9 +264,11 @@ Joystick::Joystick( /*const LPCDIDEVICEINSTANCE lpddi, */const LPDIRECTINPUTDEVI
if (SUCCEEDED(m_device->GetProperty(DIPROP_RANGE, &range.diph))) if (SUCCEEDED(m_device->GetProperty(DIPROP_RANGE, &range.diph)))
{ {
const LONG base = (range.lMin + range.lMax) / 2; const LONG base = (range.lMin + range.lMax) / 2;
const LONG& ax = (&m_state_in.lX)[m_index];
// each axis gets a negative and a positive input instance associated with it // each axis gets a negative and a positive input instance associated with it
AddInput(new Axis(offset, base, range.lMin-base)); AddInput(new Axis(offset, ax, base, range.lMin-base));
AddInput(new Axis(offset, base, range.lMax-base)); AddInput(new Axis(offset, ax, base, range.lMax-base));
} }
} }
@ -319,11 +321,11 @@ Joystick::Joystick( /*const LPCDIDEVICEINSTANCE lpddi, */const LPDIRECTINPUTDEVI
{ {
// ugly if ladder again :/ // ugly if ladder again :/
if (0 == f) if (0 == f)
AddOutput(new ForceConstant(i, f)); AddOutput(new ForceConstant(f, m_state_out[i]));
else if (1 == f) else if (1 == f)
AddOutput(new ForceRamp(i, f)); AddOutput(new ForceRamp(f, m_state_out[i]));
else else
AddOutput(new ForcePeriodic(i, f)); AddOutput(new ForcePeriodic(f, m_state_out[i]));
++i; ++i;
m_state_out.push_back(EffectState(pEffect)); m_state_out.push_back(EffectState(pEffect));
@ -501,44 +503,31 @@ std::string Joystick::Hat::GetName() const
template <typename P> template <typename P>
std::string Joystick::Force<P>::GetName() const std::string Joystick::Force<P>::GetName() const
{ {
return force_type_names[m_type].name; return force_type_names[m_index].name;
} }
// get / set state // get / set state
ControlState Joystick::GetInputState( const ControllerInterface::Device::Input* const input ) const ControlState Joystick::Axis::GetState() const
{ {
return ((Input*)input)->GetState( &m_state_in ); return std::max(0.0f, ControlState(m_axis - m_base) / m_range);
} }
void Joystick::SetOutputState( const ControllerInterface::Device::Output* const output, const ControlState state ) ControlState Joystick::Button::GetState() const
{ {
((Output*)output)->SetState( state, &m_state_out[0] ); return ControlState(m_button > 0);
} }
// get / set state ControlState Joystick::Hat::GetState() const
ControlState Joystick::Axis::GetState( const DIJOYSTATE* const joystate ) const
{
return std::max( 0.0f, ControlState((&joystate->lX)[m_index]-m_base) / m_range );
}
ControlState Joystick::Button::GetState( const DIJOYSTATE* const joystate ) const
{
return ControlState( joystate->rgbButtons[m_index] > 0 );
}
ControlState Joystick::Hat::GetState( const DIJOYSTATE* const joystate ) const
{ {
// can this func be simplified ? // can this func be simplified ?
const DWORD val = joystate->rgdwPOV[m_index];
// hat centered code from msdn // hat centered code from msdn
if ( 0xFFFF == LOWORD(val) ) if (0xFFFF == LOWORD(m_hat))
return 0; return 0;
return ( abs( (int)(val/4500-m_direction*2+8)%8 - 4) > 2 ); return (abs((int)(m_hat / 4500 - m_direction * 2 + 8) % 8 - 4) > 2);
} }
void Joystick::ForceConstant::SetState(const ControlState state, Joystick::EffectState* const joystate) void Joystick::ForceConstant::SetState(const ControlState state)
{ {
const LONG new_val = LONG(10000 * state); const LONG new_val = LONG(10000 * state);
@ -546,28 +535,28 @@ void Joystick::ForceConstant::SetState(const ControlState state, Joystick::Effec
if (val != new_val) if (val != new_val)
{ {
val = new_val; val = new_val;
joystate[m_index].params = &params; // tells UpdateOutput the state has changed m_state.params = &params; // tells UpdateOutput the state has changed
// tells UpdateOutput to either start or stop the force // tells UpdateOutput to either start or stop the force
joystate[m_index].size = new_val ? sizeof(params) : 0; m_state.size = new_val ? sizeof(params) : 0;
} }
} }
void Joystick::ForceRamp::SetState(const ControlState state, Joystick::EffectState* const joystate) void Joystick::ForceRamp::SetState(const ControlState state)
{ {
const LONG new_val = LONG(10000 * state); const LONG new_val = LONG(10000 * state);
if (params.lStart != new_val) if (params.lStart != new_val)
{ {
params.lStart = params.lEnd = new_val; params.lStart = params.lEnd = new_val;
joystate[m_index].params = &params; // tells UpdateOutput the state has changed m_state.params = &params; // tells UpdateOutput the state has changed
// tells UpdateOutput to either start or stop the force // tells UpdateOutput to either start or stop the force
joystate[m_index].size = new_val ? sizeof(params) : 0; m_state.size = new_val ? sizeof(params) : 0;
} }
} }
void Joystick::ForcePeriodic::SetState(const ControlState state, Joystick::EffectState* const joystate) void Joystick::ForcePeriodic::SetState(const ControlState state)
{ {
const LONG new_val = LONG(10000 * state); const LONG new_val = LONG(10000 * state);
@ -577,16 +566,16 @@ void Joystick::ForcePeriodic::SetState(const ControlState state, Joystick::Effec
val = new_val; val = new_val;
//params.dwPeriod = 0;//DWORD(0.05 * DI_SECONDS); // zero is working fine for me //params.dwPeriod = 0;//DWORD(0.05 * DI_SECONDS); // zero is working fine for me
joystate[m_index].params = &params; // tells UpdateOutput the state has changed m_state.params = &params; // tells UpdateOutput the state has changed
// tells UpdateOutput to either start or stop the force // tells UpdateOutput to either start or stop the force
joystate[m_index].size = new_val ? sizeof(params) : 0; m_state.size = new_val ? sizeof(params) : 0;
} }
} }
template <typename P> template <typename P>
Joystick::Force<P>::Force(const unsigned int index, const unsigned int type) Joystick::Force<P>::Force(u8 index, EffectState& state)
: m_index(index), m_type(type) : m_index(index), m_state(state)
{ {
ZeroMemory(&params, sizeof(params)); ZeroMemory(&params, sizeof(params));
} }

View File

@ -25,11 +25,7 @@ void InitJoystick(IDirectInput8* const idi8, std::vector<ControllerInterface::De
class Joystick : public ControllerInterface::Device class Joystick : public ControllerInterface::Device
{ {
friend class ControllerInterface; private:
friend class ControllerInterface::ControlReference;
protected:
struct EffectState struct EffectState
{ {
EffectState(LPDIRECTINPUTEFFECT eff) : iface(eff), params(NULL), size(0) {} EffectState(LPDIRECTINPUTEFFECT eff) : iface(eff), params(NULL), size(0) {}
@ -39,88 +35,63 @@ protected:
u8 size; // zero when force should stop u8 size; // zero when force should stop
}; };
class Input : public ControllerInterface::Device::Input
{
friend class Joystick;
protected:
virtual ControlState GetState( const DIJOYSTATE* const joystate ) const = 0;
};
// can probably eliminate this base class
class Output : public ControllerInterface::Device::Output
{
friend class Joystick;
protected:
virtual void SetState( const ControlState state, EffectState* const joystate ) = 0;
};
class Button : public Input class Button : public Input
{ {
friend class Joystick;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Button(u8 index, const BYTE& button) : m_index(index), m_button(button) {}
Button( const unsigned int index ) : m_index(index) {} ControlState GetState() const;
ControlState GetState( const DIJOYSTATE* const joystate ) const;
private: private:
const unsigned int m_index; const BYTE& m_button;
const u8 m_index;
}; };
class Axis : public Input class Axis : public Input
{ {
friend class Joystick;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Axis(u8 index, const LONG& axis, LONG base, LONG range) : m_index(index), m_axis(axis), m_base(base), m_range(range) {}
Axis( const unsigned int index, const LONG base, const LONG range ) : m_index(index), m_base(base), m_range(range) {} ControlState GetState() const;
ControlState GetState( const DIJOYSTATE* const joystate ) const;
private: private:
const unsigned int m_index; const LONG& m_axis;
const LONG m_base; const LONG m_base, m_range;
const LONG m_range; const u8 m_index;
}; };
class Hat : public Input class Hat : public Input
{ {
friend class Joystick;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Hat(u8 index, const DWORD& hat, u8 direction) : m_index(index), m_hat(hat), m_direction(direction) {}
Hat( const unsigned int index, const unsigned int direction ) : m_index(index), m_direction(direction) {} ControlState GetState() const;
ControlState GetState( const DIJOYSTATE* const joystate ) const;
private: private:
const unsigned int m_index; const DWORD& m_hat;
const unsigned int m_direction; const u8 m_index, m_direction;
}; };
template <typename P> template <typename P>
class Force : public Output class Force : public Output
{ {
friend class Joystick;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Force(u8 index, EffectState& state);
Force(const unsigned int index, const unsigned int type); void SetState(ControlState state);
void SetState(const ControlState state, EffectState* const joystate);
private: private:
const unsigned int m_index; EffectState& m_state;
const unsigned int m_type; P params;
P params; const u8 m_index;
}; };
typedef Force<DICONSTANTFORCE> ForceConstant; typedef Force<DICONSTANTFORCE> ForceConstant;
typedef Force<DIRAMPFORCE> ForceRamp; typedef Force<DIRAMPFORCE> ForceRamp;
typedef Force<DIPERIODIC> ForcePeriodic; typedef Force<DIPERIODIC> ForcePeriodic;
public:
bool UpdateInput(); bool UpdateInput();
bool UpdateOutput(); bool UpdateOutput();
ControlState GetInputState( const ControllerInterface::Device::Input* const input ) const;
void SetOutputState( const ControllerInterface::Device::Output* const input, const ControlState state );
void ClearInputState(); void ClearInputState();
public: Joystick(const LPDIRECTINPUTDEVICE8 device, const unsigned int index);
Joystick( /*const LPCDIDEVICEINSTANCE lpddi, */const LPDIRECTINPUTDEVICE8 device, const unsigned int index );
~Joystick(); ~Joystick();
std::string GetName() const; std::string GetName() const;
@ -130,7 +101,6 @@ public:
private: private:
const LPDIRECTINPUTDEVICE8 m_device; const LPDIRECTINPUTDEVICE8 m_device;
const unsigned int m_index; const unsigned int m_index;
//const std::string m_name;
DIJOYSTATE m_state_in; DIJOYSTATE m_state_in;
std::vector<EffectState> m_state_out; std::vector<EffectState> m_state_out;

View File

@ -101,10 +101,10 @@ KeyboardMouse::KeyboardMouse(const LPDIRECTINPUTDEVICE8 kb_device, const LPDIREC
// KEYBOARD // KEYBOARD
// add keys // add keys
for (unsigned int i = 0; i < sizeof(named_keys)/sizeof(*named_keys); ++i) for (u8 i = 0; i < sizeof(named_keys)/sizeof(*named_keys); ++i)
AddInput(new Key(i)); AddInput(new Key(i, m_state_in.keyboard[named_keys[i].code]));
// add lights // add lights
for (unsigned int i = 0; i < sizeof(named_lights)/sizeof(*named_lights); ++i) for (u8 i = 0; i < sizeof(named_lights)/sizeof(*named_lights); ++i)
AddOutput(new Light(i)); AddOutput(new Light(i));
// MOUSE // MOUSE
@ -114,18 +114,20 @@ KeyboardMouse::KeyboardMouse(const LPDIRECTINPUTDEVICE8 kb_device, const LPDIREC
mouse_caps.dwSize = sizeof(mouse_caps); mouse_caps.dwSize = sizeof(mouse_caps);
m_mo_device->GetCapabilities(&mouse_caps); m_mo_device->GetCapabilities(&mouse_caps);
// mouse buttons // mouse buttons
for (unsigned int i = 0; i < mouse_caps.dwButtons; ++i) for (u8 i = 0; i < mouse_caps.dwButtons; ++i)
AddInput(new Button(i)); AddInput(new Button(i, m_state_in.mouse.rgbButtons[i]));
// mouse axes // mouse axes
for (unsigned int i = 0; i < mouse_caps.dwAxes; ++i) for (unsigned int i = 0; i < mouse_caps.dwAxes; ++i)
{ {
const LONG& ax = (&m_state_in.mouse.lX)[i];
// each axis gets a negative and a positive input instance associated with it // each axis gets a negative and a positive input instance associated with it
AddInput(new Axis(i, (2==i) ? -1 : -MOUSE_AXIS_SENSITIVITY)); AddInput(new Axis(i, ax, (2==i) ? -1 : -MOUSE_AXIS_SENSITIVITY));
AddInput(new Axis(i, -(2==i) ? 1 : MOUSE_AXIS_SENSITIVITY)); AddInput(new Axis(i, ax, -(2==i) ? 1 : MOUSE_AXIS_SENSITIVITY));
} }
// cursor, with a hax for-loop // cursor, with a hax for-loop
for (unsigned int i=0; i<4; ++i) for (unsigned int i=0; i<4; ++i)
AddInput(new Cursor(!!(i&2), !!(i&1))); AddInput(new Cursor(!!(i&2), (&m_state_in.cursor.x)[i/2], !!(i&1)));
} }
void GetMousePos(float* const x, float* const y) void GetMousePos(float* const x, float* const y)
@ -244,15 +246,15 @@ std::string KeyboardMouse::GetSource() const
return DINPUT_SOURCE_NAME; return DINPUT_SOURCE_NAME;
} }
ControlState KeyboardMouse::GetInputState(const ControllerInterface::Device::Input* const input) const //ControlState KeyboardMouse::GetInputState(const ControllerInterface::Device::Input* const input) const
{ //{
return (((Input*)input)->GetState(&m_state_in)); // return (((Input*)input)->GetState(&m_state_in));
} //}
//
void KeyboardMouse::SetOutputState(const ControllerInterface::Device::Output* const output, const ControlState state) //void KeyboardMouse::SetOutputState(const ControllerInterface::Device::Output* const output, const ControlState state)
{ //{
((Output*)output)->SetState(state, m_state_out); // ((Output*)output)->SetState(state, m_state_out);
} //}
// names // names
std::string KeyboardMouse::Key::GetName() const std::string KeyboardMouse::Key::GetName() const
@ -283,33 +285,33 @@ std::string KeyboardMouse::Cursor::GetName() const
std::string KeyboardMouse::Light::GetName() const std::string KeyboardMouse::Light::GetName() const
{ {
return named_lights[ m_index ].name; return named_lights[m_index].name;
} }
// get/set state // get/set state
ControlState KeyboardMouse::Key::GetState(const State* const state) const ControlState KeyboardMouse::Key::GetState() const
{ {
return (state->keyboard[named_keys[m_index].code] != 0); return (m_key != 0);
} }
ControlState KeyboardMouse::Button::GetState(const State* const state) const ControlState KeyboardMouse::Button::GetState() const
{ {
return (state->mouse.rgbButtons[m_index] != 0); return (m_button != 0);
} }
ControlState KeyboardMouse::Axis::GetState(const State* const state) const ControlState KeyboardMouse::Axis::GetState() const
{ {
return std::max(0.0f, ControlState((&state->mouse.lX)[m_index]) / m_range); return std::max(0.0f, ControlState(m_axis) / m_range);
} }
ControlState KeyboardMouse::Cursor::GetState(const State* const state) const ControlState KeyboardMouse::Cursor::GetState() const
{ {
return std::max(0.0f, ControlState((&state->cursor.x)[m_index]) / (m_positive ? 1.0f : -1.0f)); return std::max(0.0f, ControlState(m_axis) / (m_positive ? 1.0f : -1.0f));
} }
void KeyboardMouse::Light::SetState(const ControlState state, unsigned char* const state_out) void KeyboardMouse::Light::SetState(const ControlState state)
{ {
state_out[m_index] = (unsigned char)(state * 255); //state_out[m_index] = (unsigned char)(state * 255);
} }
} }

View File

@ -18,11 +18,7 @@ void InitKeyboardMouse(IDirectInput8* const idi8, std::vector<ControllerInterfac
class KeyboardMouse : public ControllerInterface::Device class KeyboardMouse : public ControllerInterface::Device
{ {
friend class ControllerInterface; private:
friend class ControllerInterface::ControlReference;
protected:
struct State struct State
{ {
BYTE keyboard[256]; BYTE keyboard[256];
@ -33,90 +29,67 @@ protected:
} cursor; } cursor;
}; };
class Input : public ControllerInterface::Device::Input
{
friend class KeyboardMouse;
protected:
virtual ControlState GetState(const State* const boardstate) const = 0;
};
class Output : public ControllerInterface::Device::Output
{
friend class KeyboardMouse;
protected:
virtual void SetState(const ControlState state, unsigned char* const state_out) = 0;
};
class Key : public Input class Key : public Input
{ {
friend class KeyboardMouse;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Key(u8 index, const BYTE& key) : m_index(index), m_key(key) {}
Key( const unsigned int index ) : m_index(index) {} ControlState GetState() const;
ControlState GetState(const State* const state) const;
private: private:
const unsigned int m_index; const BYTE& m_key;
const u8 m_index;
}; };
class Button : public Input class Button : public Input
{ {
friend class KeyboardMouse;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Button(u8 index, const BYTE& button) : m_index(index), m_button(button) {}
Button( const unsigned int index ) : m_index(index) {} ControlState GetState() const;
ControlState GetState(const State* const state) const;
private: private:
const unsigned int m_index; const BYTE& m_button;
const u8 m_index;
}; };
class Axis : public Input class Axis : public Input
{ {
friend class KeyboardMouse;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Axis(u8 index, const LONG& axis, LONG range) : m_index(index), m_axis(axis), m_range(range) {}
Axis( const unsigned int index, const LONG range ) : m_index(index), m_range(range) {} ControlState GetState() const;
ControlState GetState(const State* const state) const;
private: private:
const unsigned int m_index; const LONG& m_axis;
const LONG m_range; const LONG m_range;
const u8 m_index;
}; };
class Cursor : public Input class Cursor : public Input
{ {
friend class KeyboardMouse;
public: public:
std::string GetName() const; std::string GetName() const;
bool IsDetectable() { return false; } bool IsDetectable() { return false; }
protected: Cursor(u8 index, const float& axis, const bool positive) : m_index(index), m_axis(axis), m_positive(positive) {}
Cursor(const unsigned int index, const bool positive) : m_index(index), m_positive(positive) {} ControlState GetState() const;
ControlState GetState(const State* const state) const;
private: private:
const unsigned int m_index; const float& m_axis;
const bool m_positive; const u8 m_index;
const bool m_positive;
}; };
class Light : public Output class Light : public Output
{ {
friend class KeyboardMouse;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Light(u8 index) : m_index(index) {}
Light( const unsigned int index ) : m_index(index) {} void SetState(ControlState state);
void SetState( const ControlState state, unsigned char* const state_out );
private: private:
const unsigned int m_index; const u8 m_index;
}; };
public:
bool UpdateInput(); bool UpdateInput();
bool UpdateOutput(); bool UpdateOutput();
ControlState GetInputState( const ControllerInterface::Device::Input* const input ) const;
void SetOutputState( const ControllerInterface::Device::Output* const input, const ControlState state );
public:
KeyboardMouse(const LPDIRECTINPUTDEVICE8 kb_device, const LPDIRECTINPUTDEVICE8 mo_device); KeyboardMouse(const LPDIRECTINPUTDEVICE8 kb_device, const LPDIRECTINPUTDEVICE8 mo_device);
~KeyboardMouse(); ~KeyboardMouse();

View File

@ -9,53 +9,40 @@ namespace OSX
class Joystick : public ControllerInterface::Device class Joystick : public ControllerInterface::Device
{ {
friend class ControllerInterface; private:
friend class ControllerInterface::ControlReference;
protected:
class Input : public ControllerInterface::Device::Input
{
friend class Joystick;
protected:
virtual ControlState GetState(IOHIDDeviceRef device) const = 0;
};
class Button : public Input class Button : public Input
{ {
friend class Joystick;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Button(IOHIDElementRef element, IOHIDDeviceRef device)
Button(IOHIDElementRef element); : m_element(element), m_device(device) {}
ControlState GetState(IOHIDDeviceRef device) const; ControlState GetState() const;
private: private:
IOHIDElementRef m_element; const IOHIDElementRef m_element;
std::string m_name; const IOHIDDeviceRef m_device;
}; };
class Axis : public Input class Axis : public Input
{ {
friend class Joystick;
public: public:
enum direction { enum direction {
positive = 0, positive = 0,
negative negative
}; };
std::string GetName() const; std::string GetName() const;
protected: Axis(IOHIDElementRef element, IOHIDDeviceRef device, direction dir);
Axis(IOHIDElementRef element, direction dir); ControlState GetState() const;
ControlState GetState(IOHIDDeviceRef device) const;
private: private:
IOHIDElementRef m_element; const IOHIDElementRef m_element;
const IOHIDDeviceRef m_device;
std::string m_name; std::string m_name;
direction m_direction; const direction m_direction;
float m_neutral; float m_neutral;
float m_scale; float m_scale;
}; };
class Hat : public Input class Hat : public Input
{ {
friend class Joystick;
public: public:
enum direction { enum direction {
up = 0, up = 0,
@ -64,25 +51,19 @@ protected:
left left
}; };
std::string GetName() const; std::string GetName() const;
protected: Hat(IOHIDElementRef element, IOHIDDeviceRef device, direction dir);
Hat(IOHIDElementRef element, direction dir); ControlState GetState() const;
ControlState GetState(IOHIDDeviceRef device) const;
private: private:
IOHIDElementRef m_element; const IOHIDElementRef m_element;
std::string m_name; const IOHIDDeviceRef m_device;
direction m_direction; const char* m_name;
const direction m_direction;
}; };
public:
bool UpdateInput(); bool UpdateInput();
bool UpdateOutput(); bool UpdateOutput();
ControlState GetInputState(
const ControllerInterface::Device::Input* const input) const;
void SetOutputState(
const ControllerInterface::Device::Output* const output,
const ControlState state);
public:
Joystick(IOHIDDeviceRef device, std::string name, int index); Joystick(IOHIDDeviceRef device, std::string name, int index);
std::string GetName() const; std::string GetName() const;
@ -90,9 +71,9 @@ public:
int GetId() const; int GetId() const;
private: private:
IOHIDDeviceRef m_device; const IOHIDDeviceRef m_device;
std::string m_device_name; const std::string m_device_name;
int m_index; const int m_index;
}; };
} }

View File

@ -35,7 +35,7 @@ Joystick::Joystick(IOHIDDeviceRef device, std::string name, int index)
(IOHIDElementRef)CFArrayGetValueAtIndex(buttons, i); (IOHIDElementRef)CFArrayGetValueAtIndex(buttons, i);
//DeviceElementDebugPrint(e, NULL); //DeviceElementDebugPrint(e, NULL);
AddInput(new Button(e)); AddInput(new Button(e, m_device));
} }
CFRelease(buttons); CFRelease(buttons);
} }
@ -59,31 +59,19 @@ Joystick::Joystick(IOHIDDeviceRef device, std::string name, int index)
//DeviceElementDebugPrint(e, NULL); //DeviceElementDebugPrint(e, NULL);
if (IOHIDElementGetUsage(e) == kHIDUsage_GD_Hatswitch) { if (IOHIDElementGetUsage(e) == kHIDUsage_GD_Hatswitch) {
AddInput(new Hat(e, Hat::up)); AddInput(new Hat(e, m_device, Hat::up));
AddInput(new Hat(e, Hat::right)); AddInput(new Hat(e, m_device, Hat::right));
AddInput(new Hat(e, Hat::down)); AddInput(new Hat(e, m_device, Hat::down));
AddInput(new Hat(e, Hat::left)); AddInput(new Hat(e, m_device, Hat::left));
} else { } else {
AddInput(new Axis(e, Axis::negative)); AddInput(new Axis(e, m_device, Axis::negative));
AddInput(new Axis(e, Axis::positive)); AddInput(new Axis(e, m_device, Axis::positive));
} }
} }
CFRelease(axes); CFRelease(axes);
} }
} }
ControlState Joystick::GetInputState(
const ControllerInterface::Device::Input* const input) const
{
return ((Input*)input)->GetState(m_device);
}
void Joystick::SetOutputState(
const ControllerInterface::Device::Output* const output,
const ControlState state)
{
}
bool Joystick::UpdateInput() bool Joystick::UpdateInput()
{ {
return true; return true;
@ -109,18 +97,10 @@ int Joystick::GetId() const
return m_index; return m_index;
} }
Joystick::Button::Button(IOHIDElementRef element) ControlState Joystick::Button::GetState() const
: m_element(element)
{
std::ostringstream s;
s << IOHIDElementGetUsage(m_element);
m_name = std::string("Button ") + s.str();
}
ControlState Joystick::Button::GetState(IOHIDDeviceRef device) const
{ {
IOHIDValueRef value; IOHIDValueRef value;
if (IOHIDDeviceGetValue(device, m_element, &value) == kIOReturnSuccess) if (IOHIDDeviceGetValue(m_device, m_element, &value) == kIOReturnSuccess)
return IOHIDValueGetIntegerValue(value); return IOHIDValueGetIntegerValue(value);
else else
return 0; return 0;
@ -128,12 +108,14 @@ ControlState Joystick::Button::GetState(IOHIDDeviceRef device) const
std::string Joystick::Button::GetName() const std::string Joystick::Button::GetName() const
{ {
return m_name; std::ostringstream s;
s << IOHIDElementGetUsage(m_element);
return std::string("Button ") + s.str();
} }
Joystick::Axis::Axis(IOHIDElementRef element, IOHIDDeviceRef device, direction dir)
Joystick::Axis::Axis(IOHIDElementRef element, direction dir)
: m_element(element) : m_element(element)
, m_device(device)
, m_direction(dir) , m_direction(dir)
{ {
// Need to parse the element a bit first // Need to parse the element a bit first
@ -174,11 +156,11 @@ Joystick::Axis::Axis(IOHIDElementRef element, direction dir)
m_scale = 1 / fabs(IOHIDElementGetLogicalMax(m_element) - m_neutral); m_scale = 1 / fabs(IOHIDElementGetLogicalMax(m_element) - m_neutral);
} }
ControlState Joystick::Axis::GetState(IOHIDDeviceRef device) const ControlState Joystick::Axis::GetState() const
{ {
IOHIDValueRef value; IOHIDValueRef value;
if (IOHIDDeviceGetValue(device, m_element, &value) == kIOReturnSuccess) if (IOHIDDeviceGetValue(m_device, m_element, &value) == kIOReturnSuccess)
{ {
// IOHIDValueGetIntegerValue() crashes when trying // IOHIDValueGetIntegerValue() crashes when trying
// to convert unusually large element values. // to convert unusually large element values.
@ -201,8 +183,9 @@ std::string Joystick::Axis::GetName() const
return m_name; return m_name;
} }
Joystick::Hat::Hat(IOHIDElementRef element, direction dir) Joystick::Hat::Hat(IOHIDElementRef element, IOHIDDeviceRef device, direction dir)
: m_element(element) : m_element(element)
, m_device(device)
, m_direction(dir) , m_direction(dir)
{ {
switch (dir) { switch (dir) {
@ -223,12 +206,12 @@ Joystick::Hat::Hat(IOHIDElementRef element, direction dir)
} }
} }
ControlState Joystick::Hat::GetState(IOHIDDeviceRef device) const ControlState Joystick::Hat::GetState() const
{ {
IOHIDValueRef value; IOHIDValueRef value;
int position; int position;
if (IOHIDDeviceGetValue(device, m_element, &value) == kIOReturnSuccess) if (IOHIDDeviceGetValue(m_device, m_element, &value) == kIOReturnSuccess)
{ {
position = IOHIDValueGetIntegerValue(value); position = IOHIDValueGetIntegerValue(value);

View File

@ -9,40 +9,23 @@ namespace OSX
class Keyboard : public ControllerInterface::Device class Keyboard : public ControllerInterface::Device
{ {
friend class ControllerInterface; private:
friend class ControllerInterface::ControlReference;
protected:
class Input : public ControllerInterface::Device::Input
{
friend class Keyboard;
protected:
virtual ControlState GetState(IOHIDDeviceRef device) const = 0;
};
class Key : public Input class Key : public Input
{ {
friend class Keyboard;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Key(IOHIDElementRef element, IOHIDDeviceRef device);
Key(IOHIDElementRef element); ControlState GetState() const;
ControlState GetState(IOHIDDeviceRef device) const;
private: private:
IOHIDElementRef m_element; const IOHIDElementRef m_element;
const IOHIDDeviceRef m_device;
std::string m_name; std::string m_name;
}; };
public:
bool UpdateInput(); bool UpdateInput();
bool UpdateOutput(); bool UpdateOutput();
ControlState GetInputState(
const ControllerInterface::Device::Input* const input) const;
void SetOutputState(
const ControllerInterface::Device::Output* const output,
const ControlState state);
public:
Keyboard(IOHIDDeviceRef device, std::string name, int index); Keyboard(IOHIDDeviceRef device, std::string name, int index);
std::string GetName() const; std::string GetName() const;
@ -50,8 +33,8 @@ public:
int GetId() const; int GetId() const;
private: private:
IOHIDDeviceRef m_device; const IOHIDDeviceRef m_device;
std::string m_device_name; const std::string m_device_name;
int m_index; int m_index;
}; };

View File

@ -9,7 +9,6 @@ namespace ciface
namespace OSX namespace OSX
{ {
Keyboard::Keyboard(IOHIDDeviceRef device, std::string name, int index) Keyboard::Keyboard(IOHIDDeviceRef device, std::string name, int index)
: m_device(device) : m_device(device)
, m_device_name(name) , m_device_name(name)
@ -36,24 +35,12 @@ Keyboard::Keyboard(IOHIDDeviceRef device, std::string name, int index)
(IOHIDElementRef)CFArrayGetValueAtIndex(elements, i); (IOHIDElementRef)CFArrayGetValueAtIndex(elements, i);
//DeviceElementDebugPrint(e, NULL); //DeviceElementDebugPrint(e, NULL);
AddInput(new Key(e)); AddInput(new Key(e, m_device));
} }
CFRelease(elements); CFRelease(elements);
} }
} }
ControlState Keyboard::GetInputState(
const ControllerInterface::Device::Input* const input) const
{
return ((Input*)input)->GetState(m_device);
}
void Keyboard::SetOutputState(
const ControllerInterface::Device::Output * const output,
const ControlState state)
{
}
bool Keyboard::UpdateInput() bool Keyboard::UpdateInput()
{ {
return true; return true;
@ -79,10 +66,11 @@ int Keyboard::GetId() const
return m_index; return m_index;
} }
Keyboard::Key::Key(IOHIDElementRef element) Keyboard::Key::Key(IOHIDElementRef element, IOHIDDeviceRef device)
: m_element(element) : m_element(element)
, m_device(device)
{ {
const struct PrettyKeys { static const struct PrettyKeys {
const uint32_t code; const uint32_t code;
const char *const name; const char *const name;
} named_keys[] = { } named_keys[] = {
@ -190,25 +178,24 @@ Keyboard::Key::Key(IOHIDElementRef element)
{ kHIDUsage_KeyboardRightGUI, "Right Command" }, { kHIDUsage_KeyboardRightGUI, "Right Command" },
{ 184, "Eject" }, { 184, "Eject" },
}; };
std::stringstream ss;
uint32_t i, keycode;
keycode = IOHIDElementGetUsage(m_element); const uint32_t keycode = IOHIDElementGetUsage(m_element);
for (i = 0; i < sizeof named_keys / sizeof *named_keys; i++) for (uint32_t i = 0; i < sizeof named_keys / sizeof *named_keys; i++)
if (named_keys[i].code == keycode) { if (named_keys[i].code == keycode) {
m_name = named_keys[i].name; m_name = named_keys[i].name;
return; return;
} }
std::stringstream ss;
ss << "Key " << keycode; ss << "Key " << keycode;
m_name = ss.str(); m_name = ss.str();
} }
ControlState Keyboard::Key::GetState(IOHIDDeviceRef device) const ControlState Keyboard::Key::GetState() const
{ {
IOHIDValueRef value; IOHIDValueRef value;
if (IOHIDDeviceGetValue(device, m_element, &value) == kIOReturnSuccess) if (IOHIDDeviceGetValue(m_device, m_element, &value) == kIOReturnSuccess)
return IOHIDValueGetIntegerValue(value); return IOHIDValueGetIntegerValue(value);
else else
return 0; return 0;
@ -219,6 +206,5 @@ std::string Keyboard::Key::GetName() const
return m_name; return m_name;
} }
} }
} }

View File

@ -30,11 +30,11 @@ void Init( std::vector<ControllerInterface::Device*>& devices )
for(int i = 0; i < SDL_NumJoysticks(); ++i) for(int i = 0; i < SDL_NumJoysticks(); ++i)
{ {
SDL_Joystick* dev = SDL_JoystickOpen(i); SDL_Joystick* dev = SDL_JoystickOpen(i);
if ( dev ) if (dev)
{ {
Joystick* js = new Joystick(dev, i, name_counts[SDL_JoystickName(i)]++); Joystick* js = new Joystick(dev, i, name_counts[SDL_JoystickName(i)]++);
// only add if it has some inputs/outputs // only add if it has some inputs/outputs
if ( js->Inputs().size() || js->Outputs().size() ) if (js->Inputs().size() || js->Outputs().size())
devices.push_back( js ); devices.push_back( js );
else else
delete js; delete js;
@ -71,25 +71,23 @@ Joystick::Joystick(SDL_Joystick* const joystick, const int sdl_index, const unsi
#endif #endif
// get buttons // get buttons
for ( int i = 0; i < SDL_JoystickNumButtons( m_joystick ); ++i ) for (u8 i = 0; i != SDL_JoystickNumButtons(m_joystick); ++i)
{ AddInput(new Button(i, m_joystick));
AddInput( new Button( i ) );
}
// get hats // get hats
for ( int i = 0; i < SDL_JoystickNumHats( m_joystick ); ++i ) for (u8 i = 0; i != SDL_JoystickNumHats(m_joystick); ++i)
{ {
// each hat gets 4 input instances associated with it, (up down left right) // each hat gets 4 input instances associated with it, (up down left right)
for ( unsigned int d = 0; d < 4; ++d ) for (u8 d = 0; d != 4; ++d)
AddInput( new Hat( i, d ) ); AddInput(new Hat(i, m_joystick, d));
} }
// get axes // get axes
for ( int i = 0; i < SDL_JoystickNumAxes( m_joystick ); ++i ) for (u8 i = 0; i != SDL_JoystickNumAxes(m_joystick); ++i)
{ {
// each axis gets a negative and a positive input instance associated with it // each axis gets a negative and a positive input instance associated with it
AddInput( new Axis( i, -32768 ) ); AddInput(new Axis(i, m_joystick, -32768));
AddInput( new Axis( i, 32767 ) ); AddInput(new Axis(i, m_joystick, 32767));
} }
#ifdef USE_SDL_HAPTIC #ifdef USE_SDL_HAPTIC
@ -123,22 +121,22 @@ Joystick::Joystick(SDL_Joystick* const joystick, const int sdl_index, const unsi
Joystick::~Joystick() Joystick::~Joystick()
{ {
#ifdef USE_SDL_HAPTIC #ifdef USE_SDL_HAPTIC
if ( m_haptic ) if (m_haptic)
{ {
// stop/destroy all effects // stop/destroy all effects
SDL_HapticStopAll( m_haptic ); SDL_HapticStopAll(m_haptic);
std::vector<EffectIDState>::iterator i = m_state_out.begin(), std::vector<EffectIDState>::iterator i = m_state_out.begin(),
e = m_state_out.end(); e = m_state_out.end();
for ( ; i!=e; ++i ) for ( ; i!=e; ++i)
if ( i->id != -1 ) if (i->id != -1)
SDL_HapticDestroyEffect( m_haptic, i->id ); SDL_HapticDestroyEffect(m_haptic, i->id);
// close haptic first // close haptic first
SDL_HapticClose( m_haptic ); SDL_HapticClose(m_haptic);
} }
#endif #endif
// close joystick // close joystick
SDL_JoystickClose( m_joystick ); SDL_JoystickClose(m_joystick);
} }
#ifdef USE_SDL_HAPTIC #ifdef USE_SDL_HAPTIC
@ -154,7 +152,7 @@ std::string Joystick::RampEffect::GetName() const
void Joystick::ConstantEffect::SetState( const ControlState state, Joystick::EffectIDState* const effect ) void Joystick::ConstantEffect::SetState( const ControlState state, Joystick::EffectIDState* const effect )
{ {
if ( state ) if (state)
{ {
effect->effect.type = SDL_HAPTIC_CONSTANT; effect->effect.type = SDL_HAPTIC_CONSTANT;
effect->effect.constant.length = SDL_HAPTIC_INFINITY; effect->effect.constant.length = SDL_HAPTIC_INFINITY;
@ -164,13 +162,13 @@ void Joystick::ConstantEffect::SetState( const ControlState state, Joystick::Eff
Sint16 old = effect->effect.constant.level; Sint16 old = effect->effect.constant.level;
effect->effect.constant.level = state * 0x7FFF; effect->effect.constant.level = state * 0x7FFF;
if ( old != effect->effect.constant.level ) if (old != effect->effect.constant.level)
effect->changed = true; effect->changed = true;
} }
void Joystick::RampEffect::SetState( const ControlState state, Joystick::EffectIDState* const effect ) void Joystick::RampEffect::SetState( const ControlState state, Joystick::EffectIDState* const effect )
{ {
if ( state ) if (state)
{ {
effect->effect.type = SDL_HAPTIC_RAMP; effect->effect.type = SDL_HAPTIC_RAMP;
effect->effect.ramp.length = SDL_HAPTIC_INFINITY; effect->effect.ramp.length = SDL_HAPTIC_INFINITY;
@ -180,23 +178,11 @@ void Joystick::RampEffect::SetState( const ControlState state, Joystick::EffectI
Sint16 old = effect->effect.ramp.start; Sint16 old = effect->effect.ramp.start;
effect->effect.ramp.start = state * 0x7FFF; effect->effect.ramp.start = state * 0x7FFF;
if ( old != effect->effect.ramp.start ) if (old != effect->effect.ramp.start)
effect->changed = true; effect->changed = true;
} }
#endif #endif
ControlState Joystick::GetInputState(const ControllerInterface::Device::Input* input) const
{
return ((Input*)input)->GetState( m_joystick );
}
void Joystick::SetOutputState(const ControllerInterface::Device::Output* output, const ControlState state)
{
#ifdef USE_SDL_HAPTIC
((Output*)output)->SetState( state, &m_state_out[ ((Output*)output)->m_index ] );
#endif
}
bool Joystick::UpdateInput() bool Joystick::UpdateInput()
{ {
// each joystick is doin this, o well // each joystick is doin this, o well
@ -210,23 +196,23 @@ bool Joystick::UpdateOutput()
#ifdef USE_SDL_HAPTIC #ifdef USE_SDL_HAPTIC
std::vector<EffectIDState>::iterator i = m_state_out.begin(), std::vector<EffectIDState>::iterator i = m_state_out.begin(),
e = m_state_out.end(); e = m_state_out.end();
for ( ; i!=e; ++i ) for ( ; i!=e; ++i)
if ( i->changed ) // if SetState was called on this output if (i->changed) // if SetState was called on this output
{ {
if ( -1 == i->id ) // effect isn't currently uploaded if (-1 == i->id) // effect isn't currently uploaded
{ {
if ( i->effect.type ) // if outputstate is >0 this would be true if (i->effect.type) // if outputstate is >0 this would be true
if ( (i->id = SDL_HapticNewEffect( m_haptic, &i->effect )) > -1 ) // upload the effect if ((i->id = SDL_HapticNewEffect( m_haptic, &i->effect )) > -1) // upload the effect
SDL_HapticRunEffect( m_haptic, i->id, 1 ); // run the effect SDL_HapticRunEffect(m_haptic, i->id, 1); // run the effect
} }
else // effect is already uploaded else // effect is already uploaded
{ {
if ( i->effect.type ) // if ouputstate >0 if (i->effect.type) // if ouputstate >0
SDL_HapticUpdateEffect( m_haptic, i->id, &i->effect ); // update the effect SDL_HapticUpdateEffect(m_haptic, i->id, &i->effect); // update the effect
else else
{ {
SDL_HapticStopEffect( m_haptic, i->id ); // else, stop and remove the effect SDL_HapticStopEffect(m_haptic, i->id); // else, stop and remove the effect
SDL_HapticDestroyEffect( m_haptic, i->id ); SDL_HapticDestroyEffect(m_haptic, i->id);
i->id = -1; // mark it as not uploaded i->id = -1; // mark it as not uploaded
} }
} }
@ -275,23 +261,21 @@ std::string Joystick::Hat::GetName() const
return tmpstr; return tmpstr;
} }
ControlState Joystick::Button::GetState( SDL_Joystick* const js ) const ControlState Joystick::Button::GetState() const
{ {
return SDL_JoystickGetButton( js, m_index ); return SDL_JoystickGetButton(m_js, m_index);
} }
ControlState Joystick::Axis::GetState( SDL_Joystick* const js ) const ControlState Joystick::Axis::GetState() const
{ {
return std::max( 0.0f, ControlState(SDL_JoystickGetAxis( js, m_index )) / m_range ); return std::max(0.0f, ControlState(SDL_JoystickGetAxis(m_js, m_index)) / m_range);
} }
ControlState Joystick::Hat::GetState( SDL_Joystick* const js ) const ControlState Joystick::Hat::GetState() const
{ {
return (SDL_JoystickGetHat( js, m_index ) & ( 1 << m_direction )) > 0; return (SDL_JoystickGetHat(m_js, m_index) & (1 << m_direction)) > 0;
} }
} }
} }

View File

@ -33,108 +33,80 @@ void Init( std::vector<ControllerInterface::Device*>& devices );
class Joystick : public ControllerInterface::Device class Joystick : public ControllerInterface::Device
{ {
friend class ControllerInterface; private:
friend class ControllerInterface::ControlReference;
protected:
#ifdef USE_SDL_HAPTIC #ifdef USE_SDL_HAPTIC
class EffectIDState struct EffectIDState
{ {
friend class Joystick;
protected:
EffectIDState() : id(-1), changed(false) { memset( &effect, 0, sizeof(effect)); } EffectIDState() : id(-1), changed(false) { memset( &effect, 0, sizeof(effect)); }
protected:
SDL_HapticEffect effect; SDL_HapticEffect effect;
int id; int id;
bool changed; bool changed;
}; };
#endif #endif
class Input : public ControllerInterface::Device::Input
{
friend class Joystick;
protected:
Input( const unsigned int index ) : m_index(index) {}
virtual ControlState GetState( SDL_Joystick* const js ) const = 0;
const unsigned int m_index;
};
#ifdef USE_SDL_HAPTIC
class Output : public ControllerInterface::Device::Output
{
friend class Joystick;
protected:
Output( const size_t index ) : m_index(index) {}
virtual void SetState( const ControlState state, EffectIDState* const effect ) = 0;
const size_t m_index;
};
#endif
class Button : public Input class Button : public Input
{ {
friend class Joystick;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Button(u8 index, SDL_Joystick* js) : m_js(js), m_index(index) {}
Button( const unsigned int index ) : Input(index) {} ControlState GetState() const;
ControlState GetState( SDL_Joystick* const js ) const; private:
SDL_Joystick* const m_js;
const u8 m_index;
}; };
class Axis : public Input class Axis : public Input
{ {
friend class Joystick;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Axis(u8 index, SDL_Joystick* js, Sint16 range) : m_js(js), m_range(range), m_index(index) {}
Axis( const unsigned int index, const Sint16 range ) : Input(index), m_range(range) {} ControlState GetState() const;
ControlState GetState( SDL_Joystick* const js ) const;
private: private:
const Sint16 m_range; SDL_Joystick* const m_js;
const Sint16 m_range;
const u8 m_index;
}; };
class Hat : public Input class Hat : public Input
{ {
friend class Joystick;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Hat(u8 index, SDL_Joystick* js, u8 direction) : m_js(js), m_direction(direction), m_index(index) {}
Hat( const unsigned int index, const unsigned int direction ) : Input(index), m_direction(direction) {} ControlState GetState() const;
ControlState GetState( SDL_Joystick* const js ) const;
private: private:
const unsigned int m_direction; SDL_Joystick* const m_js;
const u8 m_direction;
const u8 m_index;
}; };
#ifdef USE_SDL_HAPTIC #ifdef USE_SDL_HAPTIC
class ConstantEffect : public Output class ConstantEffect : public Output
{ {
friend class Joystick;
public: public:
std::string GetName() const; std::string GetName() const;
protected:
ConstantEffect( const size_t index ) : Output(index) {} ConstantEffect( const size_t index ) : Output(index) {}
void SetState( const ControlState state, EffectIDState* const effect ); void SetState( const ControlState state, EffectIDState* const effect );
private:
SDL_Joystick* const m_js;
}; };
class RampEffect : public Output class RampEffect : public Output
{ {
friend class Joystick;
public: public:
std::string GetName() const; std::string GetName() const;
protected:
RampEffect( const size_t index ) : Output(index) {} RampEffect( const size_t index ) : Output(index) {}
void SetState( const ControlState state, EffectIDState* const effect ); void SetState( const ControlState state, EffectIDState* const effect );
private:
SDL_Joystick* const m_js;
}; };
#endif #endif
public:
bool UpdateInput(); bool UpdateInput();
bool UpdateOutput(); bool UpdateOutput();
ControlState GetInputState( const ControllerInterface::Device::Input* const input ) const;
void SetOutputState( const ControllerInterface::Device::Output* const output, const ControlState state );
public:
Joystick(SDL_Joystick* const joystick, const int sdl_index, const unsigned int index); Joystick(SDL_Joystick* const joystick, const int sdl_index, const unsigned int index);
~Joystick(); ~Joystick();
@ -153,7 +125,6 @@ private:
#endif #endif
}; };
} }
} }

View File

@ -51,64 +51,64 @@ static const char* const named_motors[] =
"Motor R" "Motor R"
}; };
void Init( std::vector<ControllerInterface::Device*>& devices ) void Init(DeviceList& devices)
{ {
XINPUT_CAPABILITIES caps; XINPUT_CAPABILITIES caps;
for ( int i = 0; i < 4; ++i ) for (int i = 0; i != 4; ++i)
if ( ERROR_SUCCESS == XInputGetCapabilities( i, 0, &caps ) ) if (ERROR_SUCCESS == XInputGetCapabilities(i, 0, &caps))
devices.push_back( new Device( &caps, i ) ); devices.push_back(new Device(caps, i));
} }
Device::Device( const XINPUT_CAPABILITIES* const caps, const unsigned int index ) Device::Device(const XINPUT_CAPABILITIES& caps, u8 index)
: m_index(index), m_subtype(caps->SubType) : m_index(index), m_subtype(caps.SubType)
{ {
ZeroMemory( &m_state_out, sizeof(m_state_out) ); ZeroMemory(&m_state_out, sizeof(m_state_out));
ZeroMemory( &m_current_state_out, sizeof(m_current_state_out) ); ZeroMemory(&m_current_state_out, sizeof(m_current_state_out));
// XInputGetCaps seems to always claim all capabilities are supported // XInputGetCaps seems to always claim all capabilities are supported
// but i will leave all this stuff in, incase m$ fixes xinput up a bit // but i will leave all this stuff in, incase m$ fixes xinput up a bit
// get supported buttons // get supported buttons
for ( int i = 0; i < sizeof(named_buttons)/sizeof(*named_buttons); ++i ) for (int i = 0; i != sizeof(named_buttons)/sizeof(*named_buttons); ++i)
if ( named_buttons[i].bitmask & caps->Gamepad.wButtons ) if (named_buttons[i].bitmask & caps.Gamepad.wButtons)
AddInput( new Button( /*xinput_named_buttons[i].bitmask, */i ) ); AddInput(new Button(i, m_state_in.Gamepad.wButtons));
// get supported triggers // get supported triggers
for ( int i = 0; i < sizeof(named_triggers)/sizeof(*named_triggers); ++i ) for (int i = 0; i != sizeof(named_triggers)/sizeof(*named_triggers); ++i)
{ {
//BYTE val = (&caps->Gamepad.bLeftTrigger)[i]; // should be max value / msdn lies //BYTE val = (&caps.Gamepad.bLeftTrigger)[i]; // should be max value / msdn lies
if ( (&caps->Gamepad.bLeftTrigger)[i] ) if ((&caps.Gamepad.bLeftTrigger)[i])
AddInput( new Trigger( i, 255 ) ); AddInput(new Trigger(i, (&m_state_in.Gamepad.bLeftTrigger)[i], 255 ));
} }
// get supported axes // get supported axes
for ( int i = 0; i < sizeof(named_axes)/sizeof(*named_axes); ++i ) for (int i = 0; i != sizeof(named_axes)/sizeof(*named_axes); ++i)
{ {
//SHORT val = (&caps->Gamepad.sThumbLX)[i]; // xinput doesnt give the range / msdn is lier //SHORT val = (&caps.Gamepad.sThumbLX)[i]; // xinput doesnt give the range / msdn is lier
if ( (&caps->Gamepad.sThumbLX)[i] ) if ((&caps.Gamepad.sThumbLX)[i])
{ {
const SHORT& ax = (&m_state_in.Gamepad.sThumbLX)[i];
// each axis gets a negative and a positive input instance associated with it // each axis gets a negative and a positive input instance associated with it
AddInput( new Axis( i, -32768 ) ); AddInput(new Axis(i, ax, -32768));
AddInput( new Axis( i, 32767 ) ); AddInput(new Axis(i, ax, 32767));
} }
} }
// get supported motors // get supported motors
for ( int i = 0; i < sizeof(named_motors)/sizeof(*named_motors); ++i ) for (int i = 0; i != sizeof(named_motors)/sizeof(*named_motors); ++i)
{ {
//WORD val = (&caps->Vibration.wLeftMotorSpeed)[i]; // should be max value / nope, more lies //WORD val = (&caps.Vibration.wLeftMotorSpeed)[i]; // should be max value / nope, more lies
if ( (&caps->Vibration.wLeftMotorSpeed)[i] ) if ((&caps.Vibration.wLeftMotorSpeed)[i])
AddOutput( new Motor(i, 65535 ) ); AddOutput(new Motor(i, (&m_state_out.wLeftMotorSpeed)[i], 65535));
} }
ClearInputState(); ClearInputState();
} }
void Device::ClearInputState() void Device::ClearInputState()
{ {
ZeroMemory( &m_state_in, sizeof(m_state_in) ); ZeroMemory(&m_state_in, sizeof(m_state_in));
} }
std::string Device::GetName() const std::string Device::GetName() const
@ -117,7 +117,7 @@ std::string Device::GetName() const
// subtype doesn't seem to work, i tested with 2 diff arcade sticks, both were shown as gamepad // subtype doesn't seem to work, i tested with 2 diff arcade sticks, both were shown as gamepad
// ill leave it in anyway, maybe m$ will fix it // ill leave it in anyway, maybe m$ will fix it
switch ( m_subtype ) switch (m_subtype)
{ {
case XINPUT_DEVSUBTYPE_GAMEPAD : return "Gamepad"; break; case XINPUT_DEVSUBTYPE_GAMEPAD : return "Gamepad"; break;
case 0x02 /*XINPUT_DEVSUBTYPE_WHEEL*/ : return "Wheel"; break; case 0x02 /*XINPUT_DEVSUBTYPE_WHEEL*/ : return "Wheel"; break;
@ -144,17 +144,17 @@ std::string Device::GetSource() const
bool Device::UpdateInput() bool Device::UpdateInput()
{ {
return ( ERROR_SUCCESS == XInputGetState( m_index, &m_state_in ) ); return (ERROR_SUCCESS == XInputGetState(m_index, &m_state_in));
} }
bool Device::UpdateOutput() bool Device::UpdateOutput()
{ {
// this if statement is to make rumble work better when multiple ControllerInterfaces are using the device // this if statement is to make rumble work better when multiple ControllerInterfaces are using the device
// only calls XInputSetState if the state changed // only calls XInputSetState if the state changed
if ( memcmp( &m_state_out, &m_current_state_out, sizeof(m_state_out) ) ) if (memcmp(&m_state_out, &m_current_state_out, sizeof(m_state_out)))
{ {
m_current_state_out = m_state_out; m_current_state_out = m_state_out;
return ( ERROR_SUCCESS == XInputSetState( m_index, &m_state_out ) ); return (ERROR_SUCCESS == XInputSetState(m_index, &m_state_out));
} }
else else
return true; return true;
@ -162,7 +162,6 @@ bool Device::UpdateOutput()
// GET name/source/id // GET name/source/id
std::string Device::Button::GetName() const std::string Device::Button::GetName() const
{ {
return named_buttons[m_index].name; return named_buttons[m_index].name;
@ -183,38 +182,26 @@ std::string Device::Motor::GetName() const
return named_motors[m_index]; return named_motors[m_index];
} }
// get/set control state
ControlState Device::GetInputState( const ControllerInterface::Device::Input* const input ) const
{
return ((Input*)input)->GetState( &m_state_in.Gamepad );
}
void Device::SetOutputState( const ControllerInterface::Device::Output* const output, const ControlState state )
{
return ((Output*)output)->SetState( state, &m_state_out );
}
// GET / SET STATES // GET / SET STATES
ControlState Device::Button::GetState( const XINPUT_GAMEPAD* const gamepad ) const ControlState Device::Button::GetState() const
{ {
return (gamepad->wButtons & named_buttons[m_index].bitmask) > 0; return (m_buttons & named_buttons[m_index].bitmask) > 0;
} }
ControlState Device::Trigger::GetState( const XINPUT_GAMEPAD* const gamepad ) const ControlState Device::Trigger::GetState() const
{ {
return ControlState((&gamepad->bLeftTrigger)[m_index]) / m_range; return ControlState(m_trigger) / m_range;
} }
ControlState Device::Axis::GetState( const XINPUT_GAMEPAD* const gamepad ) const ControlState Device::Axis::GetState() const
{ {
return std::max( 0.0f, ControlState((&gamepad->sThumbLX)[m_index]) / m_range ); return std::max( 0.0f, ControlState(m_axis) / m_range );
} }
void Device::Motor::SetState( const ControlState state, XINPUT_VIBRATION* const vibration ) void Device::Motor::SetState(ControlState state)
{ {
(&vibration->wLeftMotorSpeed)[m_index] = (WORD)(state * m_range); m_motor = (WORD)(state * m_range);
} }
} }

View File

@ -12,101 +12,75 @@ namespace ciface
namespace XInput namespace XInput
{ {
void Init( std::vector<ControllerInterface::Device*>& devices ); void Init(DeviceList& devices);
class Device : public ControllerInterface::Device class Device : public ControllerInterface::Device
{ {
friend class ControllerInterface; private:
friend class ControllerInterface::ControlReference;
protected:
class Input : public ControllerInterface::Device::Input
{
friend class Device;
protected:
virtual ControlState GetState( const XINPUT_GAMEPAD* const gamepad ) const = 0;
};
class Output : public ControllerInterface::Device::Output
{
friend class Device;
protected:
virtual void SetState( const ControlState state, XINPUT_VIBRATION* const vibration ) = 0;
};
class Button : public Input class Button : public Input
{ {
friend class Device;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Button(u8 index, const WORD& buttons) : m_index(index), m_buttons(buttons) {}
Button( const unsigned int index ) : m_index(index) {} ControlState GetState() const;
ControlState GetState( const XINPUT_GAMEPAD* const gamepad ) const;
private: private:
const unsigned int m_index; const WORD& m_buttons;
u8 m_index;
}; };
class Axis : public Input class Axis : public Input
{ {
friend class Device;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Axis(u8 index, const SHORT& axis, SHORT range) : m_index(index), m_axis(axis), m_range(range) {}
Axis( const unsigned int index, const SHORT range ) : m_index(index), m_range(range) {} ControlState GetState() const;
ControlState GetState( const XINPUT_GAMEPAD* const gamepad ) const;
private: private:
const unsigned int m_index; const SHORT& m_axis;
const SHORT m_range; const SHORT m_range;
const u8 m_index;
}; };
class Trigger : public Input class Trigger : public Input
{ {
friend class Device;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Trigger(u8 index, const BYTE& trigger, BYTE range) : m_index(index), m_trigger(trigger), m_range(range) {}
Trigger( const unsigned int index, const BYTE range ) : m_index(index), m_range(range) {} ControlState GetState() const;
ControlState GetState( const XINPUT_GAMEPAD* const gamepad ) const;
private: private:
const unsigned int m_index; const BYTE& m_trigger;
const BYTE m_range; const BYTE m_range;
const u8 m_index;
}; };
class Motor : public Output class Motor : public Output
{ {
friend class Device;
public: public:
std::string GetName() const; std::string GetName() const;
protected: Motor(u8 index, WORD& motor, WORD range) : m_index(index), m_motor(motor), m_range(range) {}
Motor( const unsigned int index, const WORD range ) : m_index(index), m_range(range) {} void SetState(ControlState state);
void SetState( const ControlState state, XINPUT_VIBRATION* const vibration );
private: private:
const unsigned int m_index; WORD& m_motor;
const WORD m_range; const WORD m_range;
const u8 m_index;
}; };
public:
bool UpdateInput(); bool UpdateInput();
bool UpdateOutput(); bool UpdateOutput();
ControlState GetInputState( const ControllerInterface::Device::Input* const input ) const;
void SetOutputState( const ControllerInterface::Device::Output* const input, const ControlState state );
void ClearInputState(); void ClearInputState();
public: Device(const XINPUT_CAPABILITIES& capabilities, u8 index);
Device( const XINPUT_CAPABILITIES* const capabilities, const unsigned int index );
std::string GetName() const; std::string GetName() const;
int GetId() const; int GetId() const;
std::string GetSource() const; std::string GetSource() const;
private: private:
const unsigned int m_index; XINPUT_STATE m_state_in;
XINPUT_STATE m_state_in; XINPUT_VIBRATION m_state_out, m_current_state_out;
XINPUT_VIBRATION m_state_out; const BYTE m_subtype;
XINPUT_VIBRATION m_current_state_out; const u8 m_index;
const unsigned int m_subtype;
}; };

View File

@ -22,7 +22,7 @@ KeyboardMouse::KeyboardMouse(Window window) : m_window(window)
// Keyboard Keys // Keyboard Keys
for (int i = min_keycode; i <= max_keycode; ++i) for (int i = min_keycode; i <= max_keycode; ++i)
{ {
Key *temp_key = new Key(m_display, i); Key *temp_key = new Key(m_display, i, m_state.keyboard);
if (temp_key->m_keyname.length()) if (temp_key->m_keyname.length())
AddInput(temp_key); AddInput(temp_key);
else else
@ -30,15 +30,15 @@ KeyboardMouse::KeyboardMouse(Window window) : m_window(window)
} }
// Mouse Buttons // Mouse Buttons
AddInput(new Button(Button1Mask)); AddInput(new Button(Button1Mask, m_state.buttons));
AddInput(new Button(Button2Mask)); AddInput(new Button(Button2Mask, m_state.buttons));
AddInput(new Button(Button3Mask)); AddInput(new Button(Button3Mask, m_state.buttons));
AddInput(new Button(Button4Mask)); AddInput(new Button(Button4Mask, m_state.buttons));
AddInput(new Button(Button5Mask)); AddInput(new Button(Button5Mask, m_state.buttons));
// Mouse Cursor, X-/+ and Y-/+ // Mouse Cursor, X-/+ and Y-/+
for (unsigned int i=0; i<4; ++i) for (int i = 0; i != 4; ++i)
AddInput(new Cursor(!!(i&2), !!(i&1))); AddInput(new Cursor(!!(i & 2), !!(i & 1), (&m_state.cursor.x)[!!(i & 2)]));
} }
KeyboardMouse::~KeyboardMouse() KeyboardMouse::~KeyboardMouse()
@ -46,16 +46,6 @@ KeyboardMouse::~KeyboardMouse()
XCloseDisplay(m_display); XCloseDisplay(m_display);
} }
ControlState KeyboardMouse::GetInputState(const ControllerInterface::Device::Input* const input) const
{
return ((Input*)input)->GetState(&m_state);
}
void KeyboardMouse::SetOutputState(const ControllerInterface::Device::Output* const output, const ControlState state)
{
}
bool KeyboardMouse::UpdateInput() bool KeyboardMouse::UpdateInput()
{ {
XQueryKeymap(m_display, m_state.keyboard); XQueryKeymap(m_display, m_state.keyboard);
@ -96,9 +86,8 @@ int KeyboardMouse::GetId() const
return 0; return 0;
} }
KeyboardMouse::Key::Key(Display* const display, KeyCode keycode, const char* keyboard)
KeyboardMouse::Key::Key(Display* const display, KeyCode keycode) : m_display(display), m_keyboard(keyboard), m_keycode(keycode)
: m_display(display), m_keycode(keycode)
{ {
int i = 0; int i = 0;
KeySym keysym = 0; KeySym keysym = 0;
@ -122,21 +111,21 @@ KeyboardMouse::Key::Key(Display* const display, KeyCode keycode)
m_keyname = std::string(XKeysymToString(keysym)); m_keyname = std::string(XKeysymToString(keysym));
} }
ControlState KeyboardMouse::Key::GetState(const State* const state) const ControlState KeyboardMouse::Key::GetState() const
{ {
KeyCode shift = XKeysymToKeycode(m_display, XK_Shift_L); const KeyCode shift = XKeysymToKeycode(m_display, XK_Shift_L);
return (state->keyboard[m_keycode/8] & (1 << (m_keycode%8))) != 0 return (m_keyboard[m_keycode / 8] & (1 << (m_keycode % 8))) != 0
&& (state->keyboard[shift/8] & (1 << (shift%8))) == 0; && (m_keyboard[shift / 8] & (1 << (shift % 8))) == 0;
} }
ControlState KeyboardMouse::Button::GetState(const State* const state) const ControlState KeyboardMouse::Button::GetState() const
{ {
return ((state->buttons & m_index) > 0); return ((m_buttons & m_index) != 0);
} }
ControlState KeyboardMouse::Cursor::GetState(const State* const state) const ControlState KeyboardMouse::Cursor::GetState() const
{ {
return std::max(0.0f, ControlState((&state->cursor.x)[m_index]) / (m_positive ? 1.0f : -1.0f)); return std::max(0.0f, m_cursor / (m_positive ? 1.0f : -1.0f));
} }
std::string KeyboardMouse::Key::GetName() const std::string KeyboardMouse::Key::GetName() const

View File

@ -15,11 +15,8 @@ void Init(std::vector<ControllerInterface::Device*>& devices, void* const hwnd);
class KeyboardMouse : public ControllerInterface::Device class KeyboardMouse : public ControllerInterface::Device
{ {
friend class ControllerInterface;
friend class ControllerInterface::ControlReference;
protected:
private:
struct State struct State
{ {
char keyboard[32]; char keyboard[32];
@ -30,68 +27,53 @@ protected:
} cursor; } cursor;
}; };
class Input : public ControllerInterface::Device::Input
{
friend class KeyboardMouse;
protected:
virtual ControlState GetState(const State* const state) const = 0;
};
class Key : public Input class Key : public Input
{ {
friend class KeyboardMouse; friend class KeyboardMouse;
public: public:
std::string GetName() const; std::string GetName() const;
Key(Display* display, KeyCode keycode, const char* keyboard);
protected: ControlState GetState() const;
Key(Display* const display, KeyCode keycode);
ControlState GetState(const State* const state) const;
private: private:
std::string m_keyname;
Display* const m_display; Display* const m_display;
const char* const m_keyboard;
const KeyCode m_keycode; const KeyCode m_keycode;
std::string m_keyname;
}; };
class Button : public Input class Button : public Input
{ {
friend class KeyboardMouse;
public: public:
std::string GetName() const; std::string GetName() const;
Button(unsigned int index, unsigned int& buttons)
protected: : m_buttons(buttons), m_index(index) {}
Button(const unsigned int index) : m_index(index) {} ControlState GetState() const;
ControlState GetState(const State* const state) const;
private: private:
const unsigned int& m_buttons;
const unsigned int m_index; const unsigned int m_index;
}; };
class Cursor : public Input class Cursor : public Input
{ {
friend class KeyboardMouse;
public: public:
std::string GetName() const; std::string GetName() const;
bool IsDetectable() { return false; } bool IsDetectable() { return false; }
protected: Cursor(u8 index, bool positive, const float& cursor)
Cursor(const unsigned int index, const bool positive) : m_index(index), m_positive(positive) {} : m_cursor(cursor), m_index(index), m_positive(positive) {}
ControlState GetState(const State* const state) const; ControlState GetState() const;
private: private:
const unsigned int m_index; const float& m_cursor;
const bool m_positive; const u8 m_index;
const bool m_positive;
}; };
public:
bool UpdateInput(); bool UpdateInput();
bool UpdateOutput(); bool UpdateOutput();
ControlState GetInputState(const ControllerInterface::Device::Input* const input) const;
void SetOutputState(const ControllerInterface::Device::Output* const output, const ControlState state);
public:
KeyboardMouse(Window window); KeyboardMouse(Window window);
~KeyboardMouse(); ~KeyboardMouse();
@ -100,9 +82,9 @@ public:
int GetId() const; int GetId() const;
private: private:
Window m_window; Window m_window;
Display* m_display; Display* m_display;
State m_state; State m_state;
}; };
} }