Slightly cleaned up OSD input modules.

Removed support for DirectInput 7 and earlier.  It hasn't been tested in
years, and it's not relevant on any supported OS.  DirectInput is
effectively finalised at version 8, and is unlikely to get an API update
in the future.

Use more string[_view] and fewer C strings, and tightened up scope of a
few things.
This commit is contained in:
Vas Crabb 2021-07-29 15:22:51 +10:00
parent db1ddb7cee
commit 23bd2ecf6a
23 changed files with 839 additions and 922 deletions

View File

@ -27,7 +27,6 @@
# NO_OPENGL = 0 # NO_OPENGL = 0
# USE_DISPATCH_GL = 0 # USE_DISPATCH_GL = 0
# MODERN_WIN_API = 0 # MODERN_WIN_API = 0
# DIRECTINPUT = 7
# USE_SDL = 1 # USE_SDL = 1
# SDL_INI_PATH = .;$HOME/.mame/;ini; # SDL_INI_PATH = .;$HOME/.mame/;ini;
# SDL2_MULTIAPI = 1 # SDL2_MULTIAPI = 1
@ -783,10 +782,6 @@ ifdef MODERN_WIN_API
PARAMS += --MODERN_WIN_API='$(MODERN_WIN_API)' PARAMS += --MODERN_WIN_API='$(MODERN_WIN_API)'
endif endif
ifdef DIRECTINPUT
PARAMS += --DIRECTINPUT='$(DIRECTINPUT)'
endif
ifdef USE_SDL ifdef USE_SDL
PARAMS += --USE_SDL='$(USE_SDL)' PARAMS += --USE_SDL='$(USE_SDL)'
endif endif

View File

@ -22,17 +22,6 @@ function maintargetosdoptions(_target,_subtarget)
configuration { } configuration { }
if _OPTIONS["DIRECTINPUT"] == "8" then
links {
"dinput8",
}
else
links {
"dinput",
}
end
if _OPTIONS["USE_SDL"] == "1" then if _OPTIONS["USE_SDL"] == "1" then
links { links {
"SDL.dll", "SDL.dll",
@ -40,6 +29,7 @@ function maintargetosdoptions(_target,_subtarget)
end end
links { links {
"dinput8",
"comctl32", "comctl32",
"comdlg32", "comdlg32",
"psapi", "psapi",
@ -49,19 +39,6 @@ function maintargetosdoptions(_target,_subtarget)
end end
newoption {
trigger = "DIRECTINPUT",
description = "Minimum DirectInput version to support",
allowed = {
{ "7", "Support DirectInput 7 or later" },
{ "8", "Support DirectInput 8 or later" },
},
}
if not _OPTIONS["DIRECTINPUT"] then
_OPTIONS["DIRECTINPUT"] = "8"
end
newoption { newoption {
trigger = "USE_SDL", trigger = "USE_SDL",
description = "Enable SDL sound output", description = "Enable SDL sound output",
@ -124,17 +101,8 @@ project ("osd_" .. _OPTIONS["osd"])
defines { defines {
"DIRECT3D_VERSION=0x0900", "DIRECT3D_VERSION=0x0900",
}
if _OPTIONS["DIRECTINPUT"] == "8" then
defines {
"DIRECTINPUT_VERSION=0x0800", "DIRECTINPUT_VERSION=0x0800",
} }
else
defines {
"DIRECTINPUT_VERSION=0x0700",
}
end
includedirs { includedirs {
MAME_DIR .. "src/emu", MAME_DIR .. "src/emu",

View File

@ -800,7 +800,7 @@ std::string input_manager::code_name(input_code code) const
} }
// devcode part comes from the item name // devcode part comes from the item name
const char *devcode = item->name(); std::string_view devcode = item->name();
// determine the modifier part // determine the modifier part
const char *modifier = (*modifier_string_table)[code.item_modifier()]; const char *modifier = (*modifier_string_table)[code.item_modifier()];
@ -808,13 +808,13 @@ std::string input_manager::code_name(input_code code) const
// devcode is redundant with joystick switch left/right/up/down // devcode is redundant with joystick switch left/right/up/down
if (device_class == DEVICE_CLASS_JOYSTICK && code.item_class() == ITEM_CLASS_SWITCH) if (device_class == DEVICE_CLASS_JOYSTICK && code.item_class() == ITEM_CLASS_SWITCH)
if (code.item_modifier() >= ITEM_MODIFIER_LEFT && code.item_modifier() <= ITEM_MODIFIER_DOWN) if (code.item_modifier() >= ITEM_MODIFIER_LEFT && code.item_modifier() <= ITEM_MODIFIER_DOWN)
devcode = ""; devcode = std::string_view();
// concatenate the strings // concatenate the strings
std::string str(devclass); std::string str(devclass);
if (!devindex.empty()) if (!devindex.empty())
str.append(" ").append(devindex); str.append(" ").append(devindex);
if (devcode[0] != 0) if (!devcode.empty())
str.append(" ").append(devcode); str.append(" ").append(devcode);
if (modifier != nullptr) if (modifier != nullptr)
str.append(" ").append(modifier); str.append(" ").append(modifier);
@ -830,6 +830,8 @@ std::string input_manager::code_name(input_code code) const
std::string input_manager::code_to_token(input_code code) const std::string input_manager::code_to_token(input_code code) const
{ {
using namespace std::literals;
// determine the devclass part // determine the devclass part
const char *devclass = (*devclass_token_table)[code.device_class()]; const char *devclass = (*devclass_token_table)[code.device_class()];
if (devclass == nullptr) if (devclass == nullptr)
@ -842,14 +844,14 @@ std::string input_manager::code_to_token(input_code code) const
// determine the itemid part; look up in the table if we don't have a token // determine the itemid part; look up in the table if we don't have a token
input_device_item *item = item_from_code(code); input_device_item *item = item_from_code(code);
const char *devcode = (item != nullptr) ? item->token() : "UNKNOWN"; std::string_view devcode = item ? item->token() : "UNKNOWN"sv;
// determine the modifier part // determine the modifier part
const char *modifier = (*modifier_token_table)[code.item_modifier()]; const char *modifier = (*modifier_token_table)[code.item_modifier()];
// determine the itemclass part; if we match the native class, we don't include this // determine the itemclass part; if we match the native class, we don't include this
const char *itemclass = ""; const char *itemclass = "";
if (item == nullptr || item->itemclass() != code.item_class()) if (!item || (item->itemclass() != code.item_class()))
itemclass = (*itemclass_token_table)[code.item_class()]; itemclass = (*itemclass_token_table)[code.item_class()];
// concatenate the strings // concatenate the strings
@ -994,14 +996,16 @@ bool input_manager::seq_pressed(const input_seq &seq)
bool first = true; bool first = true;
for (int codenum = 0; ; codenum++) for (int codenum = 0; ; codenum++)
{ {
// handle NOT
input_code code = seq[codenum]; input_code code = seq[codenum];
if (code == input_seq::not_code) if (code == input_seq::not_code)
{
// handle NOT
invert = true; invert = true;
}
// handle OR and END
else if (code == input_seq::or_code || code == input_seq::end_code) else if (code == input_seq::or_code || code == input_seq::end_code)
{ {
// handle OR and END
// if we have a positive result from the previous set, we're done // if we have a positive result from the previous set, we're done
if (result || code == input_seq::end_code) if (result || code == input_seq::end_code)
break; break;
@ -1011,10 +1015,10 @@ bool input_manager::seq_pressed(const input_seq &seq)
invert = false; invert = false;
first = true; first = true;
} }
// handle everything else as a series of ANDs
else else
{ {
// handle everything else as a series of ANDs
// if this is the first in the sequence, result is set equal // if this is the first in the sequence, result is set equal
if (first) if (first)
result = code_pressed(code) ^ invert; result = code_pressed(code) ^ invert;
@ -1313,9 +1317,9 @@ void input_manager::seq_from_tokens(input_seq &seq, std::string_view string)
// controller based on device map table // controller based on device map table
//------------------------------------------------- //-------------------------------------------------
bool input_manager::map_device_to_controller(const devicemap_table_type &devicemap_table) bool input_manager::map_device_to_controller(const devicemap_table &table)
{ {
for (const auto &it : devicemap_table) for (const auto &it : table)
{ {
std::string_view deviceid = it.first; std::string_view deviceid = it.first;
std::string_view controllername = it.second; std::string_view controllername = it.second;

View File

@ -350,9 +350,6 @@ DECLARE_ENUM_INCDEC_OPERATORS(input_item_id)
// TYPE DEFINITIONS // TYPE DEFINITIONS
//************************************************************************** //**************************************************************************
// controller alias table typedef
typedef std::map<std::string, std::string> devicemap_table_type;
// ======================> input_code // ======================> input_code
// a combined code that describes a particular input on a particular device // a combined code that describes a particular input on a particular device
@ -493,6 +490,9 @@ private:
class input_manager class input_manager
{ {
public: public:
// controller alias table typedef
using devicemap_table = std::map<std::string, std::string>;
// construction/destruction // construction/destruction
input_manager(running_machine &machine); input_manager(running_machine &machine);
~input_manager(); ~input_manager();
@ -526,7 +526,7 @@ public:
void seq_from_tokens(input_seq &seq, std::string_view _token); void seq_from_tokens(input_seq &seq, std::string_view _token);
// misc // misc
bool map_device_to_controller(const devicemap_table_type &devicemap_table); bool map_device_to_controller(const devicemap_table &table);
private: private:
// internal helpers // internal helpers

View File

@ -15,6 +15,8 @@
#include "emuopts.h" #include "emuopts.h"
namespace {
//************************************************************************** //**************************************************************************
// TYPE DEFINITIONS // TYPE DEFINITIONS
//************************************************************************** //**************************************************************************
@ -26,7 +28,7 @@ class input_device_switch_item : public input_device_item
{ {
public: public:
// construction/destruction // construction/destruction
input_device_switch_item(input_device &device, const char *name, void *internal, input_item_id itemid, item_get_state_func getstate); input_device_switch_item(input_device &device, std::string_view name, void *internal, input_item_id itemid, item_get_state_func getstate);
// readers // readers
virtual s32 read_as_switch(input_item_modifier modifier) override; virtual s32 read_as_switch(input_item_modifier modifier) override;
@ -52,7 +54,7 @@ class input_device_relative_item : public input_device_item
{ {
public: public:
// construction/destruction // construction/destruction
input_device_relative_item(input_device &device, const char *name, void *internal, input_item_id itemid, item_get_state_func getstate); input_device_relative_item(input_device &device, std::string_view name, void *internal, input_item_id itemid, item_get_state_func getstate);
// readers // readers
virtual s32 read_as_switch(input_item_modifier modifier) override; virtual s32 read_as_switch(input_item_modifier modifier) override;
@ -69,7 +71,7 @@ class input_device_absolute_item : public input_device_item
{ {
public: public:
// construction/destruction // construction/destruction
input_device_absolute_item(input_device &device, const char *name, void *internal, input_item_id itemid, item_get_state_func getstate); input_device_absolute_item(input_device &device, std::string_view name, void *internal, input_item_id itemid, item_get_state_func getstate);
// readers // readers
virtual s32 read_as_switch(input_item_modifier modifier) override; virtual s32 read_as_switch(input_item_modifier modifier) override;
@ -78,6 +80,8 @@ public:
virtual bool item_check_axis(input_item_modifier modifier, s32 memory) override; virtual bool item_check_axis(input_item_modifier modifier, s32 memory) override;
}; };
} // anonymous namespace
//************************************************************************** //**************************************************************************
// GLOBAL VARIABLES // GLOBAL VARIABLES
@ -253,7 +257,7 @@ u8 joystick_map::update(s32 xaxisval, s32 yaxisval)
// input_device - constructor // input_device - constructor
//------------------------------------------------- //-------------------------------------------------
input_device::input_device(input_manager &manager, const char *name, const char *id, void *internal) input_device::input_device(input_manager &manager, std::string_view name, std::string_view id, void *internal)
: m_manager(manager), : m_manager(manager),
m_name(name), m_name(name),
m_id(id), m_id(id),
@ -279,11 +283,10 @@ input_device::~input_device()
// add_item - add a new item to an input device // add_item - add a new item to an input device
//------------------------------------------------- //-------------------------------------------------
input_item_id input_device::add_item(const char *name, input_item_id itemid, item_get_state_func getstate, void *internal) input_item_id input_device::add_item(std::string_view name, input_item_id itemid, item_get_state_func getstate, void *internal)
{ {
if (machine().phase() != machine_phase::INIT) if (machine().phase() != machine_phase::INIT)
throw emu_fatalerror("Can only call input_device::add_item at init time!"); throw emu_fatalerror("Can only call input_device::add_item at init time!");
assert(name != nullptr);
assert(itemid > ITEM_ID_INVALID && itemid < ITEM_ID_MAXIMUM); assert(itemid > ITEM_ID_INVALID && itemid < ITEM_ID_MAXIMUM);
assert(getstate != nullptr); assert(getstate != nullptr);
@ -346,7 +349,7 @@ bool input_device::match_device_id(std::string_view deviceid) const
// input_device_keyboard - constructor // input_device_keyboard - constructor
//------------------------------------------------- //-------------------------------------------------
input_device_keyboard::input_device_keyboard(input_manager &manager, const char *_name, const char *_id, void *_internal) input_device_keyboard::input_device_keyboard(input_manager &manager, std::string_view _name, std::string_view _id, void *_internal)
: input_device(manager, _name, _id, _internal) : input_device(manager, _name, _id, _internal)
{ {
} }
@ -387,7 +390,7 @@ void input_device_keyboard::apply_steadykey() const
// input_device_mouse - constructor // input_device_mouse - constructor
//------------------------------------------------- //-------------------------------------------------
input_device_mouse::input_device_mouse(input_manager &manager, const char *_name, const char *_id, void *_internal) input_device_mouse::input_device_mouse(input_manager &manager, std::string_view _name, std::string_view _id, void *_internal)
: input_device(manager, _name, _id, _internal) : input_device(manager, _name, _id, _internal)
{ {
} }
@ -397,7 +400,7 @@ input_device_mouse::input_device_mouse(input_manager &manager, const char *_name
// input_device_lightgun - constructor // input_device_lightgun - constructor
//------------------------------------------------- //-------------------------------------------------
input_device_lightgun::input_device_lightgun(input_manager &manager, const char *_name, const char *_id, void *_internal) input_device_lightgun::input_device_lightgun(input_manager &manager, std::string_view _name, std::string_view _id, void *_internal)
: input_device(manager, _name, _id, _internal) : input_device(manager, _name, _id, _internal)
{ {
} }
@ -407,7 +410,7 @@ input_device_lightgun::input_device_lightgun(input_manager &manager, const char
// input_device_joystick - constructor // input_device_joystick - constructor
//------------------------------------------------- //-------------------------------------------------
input_device_joystick::input_device_joystick(input_manager &manager, const char *_name, const char *_id, void *_internal) input_device_joystick::input_device_joystick(input_manager &manager, std::string_view _name, std::string_view _id, void *_internal)
: input_device(manager, _name, _id, _internal), : input_device(manager, _name, _id, _internal),
m_joystick_deadzone(s32(manager.machine().options().joystick_deadzone() * INPUT_ABSOLUTE_MAX)), m_joystick_deadzone(s32(manager.machine().options().joystick_deadzone() * INPUT_ABSOLUTE_MAX)),
m_joystick_saturation(s32(manager.machine().options().joystick_saturation() * INPUT_ABSOLUTE_MAX)) m_joystick_saturation(s32(manager.machine().options().joystick_saturation() * INPUT_ABSOLUTE_MAX))
@ -494,18 +497,16 @@ input_class::~input_class()
// add_device - add a new input device // add_device - add a new input device
//------------------------------------------------- //-------------------------------------------------
input_device *input_class::add_device(const char *name, const char *id, void *internal) input_device &input_class::add_device(std::string_view name, std::string_view id, void *internal)
{ {
if (machine().phase() != machine_phase::INIT) if (machine().phase() != machine_phase::INIT)
throw emu_fatalerror("Can only call input_class::add_device at init time!"); throw emu_fatalerror("Can only call input_class::add_device at init time!");
assert(name != nullptr);
assert(id != nullptr);
// allocate a new device and add it to the index // allocate a new device and add it to the index
return add_device(make_device(name, id, internal)); return add_device(make_device(name, id, internal));
} }
input_device *input_class::add_device(std::unique_ptr<input_device> &&new_device) input_device &input_class::add_device(std::unique_ptr<input_device> &&new_device)
{ {
assert(new_device->devclass() == m_devclass); assert(new_device->devclass() == m_devclass);
@ -523,7 +524,7 @@ input_device *input_class::add_device(std::unique_ptr<input_device> &&new_device
osd_printf_verbose("Input: Adding %s #%d: %s (device id: %s)\n", m_name, devindex, new_device->name(), new_device->id()); osd_printf_verbose("Input: Adding %s #%d: %s (device id: %s)\n", m_name, devindex, new_device->name(), new_device->id());
m_device[devindex] = std::move(new_device); m_device[devindex] = std::move(new_device);
return m_device[devindex].get(); return *m_device[devindex];
} }
throw emu_fatalerror("Input: Too many %s devices\n", m_name); throw emu_fatalerror("Input: Too many %s devices\n", m_name);
@ -666,7 +667,7 @@ bool input_class_joystick::set_global_joystick_map(const char *mapstring)
// input_device_item - constructor // input_device_item - constructor
//------------------------------------------------- //-------------------------------------------------
input_device_item::input_device_item(input_device &device, const char *name, void *internal, input_item_id itemid, item_get_state_func getstate, input_item_class itemclass) input_device_item::input_device_item(input_device &device, std::string_view name, void *internal, input_item_id itemid, item_get_state_func getstate, input_item_class itemclass)
: m_device(device), : m_device(device),
m_name(name), m_name(name),
m_internal(internal), m_internal(internal),
@ -720,7 +721,7 @@ bool input_device_item::check_axis(input_item_modifier modifier, s32 memory)
// input_device_switch_item - constructor // input_device_switch_item - constructor
//------------------------------------------------- //-------------------------------------------------
input_device_switch_item::input_device_switch_item(input_device &device, const char *name, void *internal, input_item_id itemid, item_get_state_func getstate) input_device_switch_item::input_device_switch_item(input_device &device, std::string_view name, void *internal, input_item_id itemid, item_get_state_func getstate)
: input_device_item(device, name, internal, itemid, getstate, ITEM_CLASS_SWITCH), : input_device_item(device, name, internal, itemid, getstate, ITEM_CLASS_SWITCH),
m_steadykey(0), m_steadykey(0),
m_oldkey(0) m_oldkey(0)
@ -825,7 +826,7 @@ bool input_device_switch_item::steadykey_changed()
// input_device_relative_item - constructor // input_device_relative_item - constructor
//------------------------------------------------- //-------------------------------------------------
input_device_relative_item::input_device_relative_item(input_device &device, const char *name, void *internal, input_item_id itemid, item_get_state_func getstate) input_device_relative_item::input_device_relative_item(input_device &device, std::string_view name, void *internal, input_item_id itemid, item_get_state_func getstate)
: input_device_item(device, name, internal, itemid, getstate, ITEM_CLASS_RELATIVE) : input_device_item(device, name, internal, itemid, getstate, ITEM_CLASS_RELATIVE)
{ {
} }
@ -896,7 +897,7 @@ bool input_device_relative_item::item_check_axis(input_item_modifier modifier, s
// input_device_absolute_item - constructor // input_device_absolute_item - constructor
//------------------------------------------------- //-------------------------------------------------
input_device_absolute_item::input_device_absolute_item(input_device &device, const char *name, void *internal, input_item_id itemid, item_get_state_func getstate) input_device_absolute_item::input_device_absolute_item(input_device &device, std::string_view name, void *internal, input_item_id itemid, item_get_state_func getstate)
: input_device_item(device, name, internal, itemid, getstate, ITEM_CLASS_ABSOLUTE) : input_device_item(device, name, internal, itemid, getstate, ITEM_CLASS_ABSOLUTE)
{ {
} }

View File

@ -87,10 +87,6 @@ private:
// a single item on an input device // a single item on an input device
class input_device_item class input_device_item
{ {
protected:
// construction/destruction
input_device_item(input_device &device, const char *name, void *internal, input_item_id itemid, item_get_state_func getstate, input_item_class itemclass);
public: public:
virtual ~input_device_item(); virtual ~input_device_item();
@ -98,12 +94,12 @@ public:
input_device &device() const { return m_device; } input_device &device() const { return m_device; }
input_manager &manager() const; input_manager &manager() const;
running_machine &machine() const; running_machine &machine() const;
const char *name() const { return m_name.c_str(); } const std::string &name() const { return m_name; }
void *internal() const { return m_internal; } void *internal() const { return m_internal; }
input_item_id itemid() const { return m_itemid; } input_item_id itemid() const { return m_itemid; }
input_item_class itemclass() const { return m_itemclass; } input_item_class itemclass() const { return m_itemclass; }
input_code code() const; input_code code() const;
const char *token() const { return m_token.c_str(); } const std::string &token() const { return m_token; }
s32 current() const { return m_current; } s32 current() const { return m_current; }
// helpers // helpers
@ -117,6 +113,9 @@ public:
virtual bool item_check_axis(input_item_modifier modifier, s32 memory) = 0; virtual bool item_check_axis(input_item_modifier modifier, s32 memory) = 0;
protected: protected:
// construction/destruction
input_device_item(input_device &device, std::string_view name, void *internal, input_item_id itemid, item_get_state_func getstate, input_item_class itemclass);
// internal state // internal state
input_device & m_device; // reference to our owning device input_device & m_device; // reference to our owning device
std::string m_name; // string name of item std::string m_name; // string name of item
@ -140,15 +139,15 @@ class input_device
public: public:
// construction/destruction // construction/destruction
input_device(input_manager &manager, const char *_name, const char *_id, void *_internal); input_device(input_manager &manager, std::string_view _name, std::string_view _id, void *_internal);
virtual ~input_device(); virtual ~input_device();
// getters // getters
input_manager &manager() const { return m_manager; } input_manager &manager() const { return m_manager; }
running_machine &machine() const { return m_manager.machine(); } running_machine &machine() const { return m_manager.machine(); }
input_device_class devclass() const { return device_class(); } input_device_class devclass() const { return device_class(); }
const char *name() const { return m_name.c_str(); } const std::string &name() const { return m_name; }
const char *id() const { return m_id.c_str(); } const std::string &id() const { return m_id; }
int devindex() const { return m_devindex; } int devindex() const { return m_devindex; }
input_device_item *item(input_item_id index) const { return m_item[index].get(); } input_device_item *item(input_item_id index) const { return m_item[index].get(); }
input_item_id maxitem() const { return m_maxitem; } input_item_id maxitem() const { return m_maxitem; }
@ -160,7 +159,7 @@ public:
void set_devindex(int devindex) { m_devindex = devindex; } void set_devindex(int devindex) { m_devindex = devindex; }
// item management // item management
input_item_id add_item(const char *name, input_item_id itemid, item_get_state_func getstate, void *internal = nullptr); input_item_id add_item(std::string_view name, input_item_id itemid, item_get_state_func getstate, void *internal = nullptr);
// helpers // helpers
s32 adjust_absolute(s32 value) const { return adjust_absolute_value(value); } s32 adjust_absolute(s32 value) const { return adjust_absolute_value(value); }
@ -192,7 +191,7 @@ class input_device_keyboard : public input_device
{ {
public: public:
// construction/destruction // construction/destruction
input_device_keyboard(input_manager &manager, const char *_name, const char *_id, void *_internal); input_device_keyboard(input_manager &manager, std::string_view _name, std::string_view _id, void *_internal);
// helpers // helpers
void apply_steadykey() const; void apply_steadykey() const;
@ -209,7 +208,7 @@ class input_device_mouse : public input_device
{ {
public: public:
// construction/destruction // construction/destruction
input_device_mouse(input_manager &manager, const char *_name, const char *_id, void *_internal); input_device_mouse(input_manager &manager, std::string_view _name, std::string_view _id, void *_internal);
protected: protected:
// specific overrides // specific overrides
@ -223,7 +222,7 @@ class input_device_lightgun : public input_device
{ {
public: public:
// construction/destruction // construction/destruction
input_device_lightgun(input_manager &manager, const char *_name, const char *_id, void *_internal); input_device_lightgun(input_manager &manager, std::string_view _name, std::string_view _id, void *_internal);
protected: protected:
// specific overrides // specific overrides
@ -238,7 +237,7 @@ class input_device_joystick : public input_device
{ {
public: public:
// construction/destruction // construction/destruction
input_device_joystick(input_manager &manager, const char *_name, const char *_id, void *_internal); input_device_joystick(input_manager &manager, std::string_view _name, std::string_view _id, void *_internal);
// getters // getters
joystick_map &joymap() { return m_joymap; } joystick_map &joymap() { return m_joymap; }
@ -284,8 +283,7 @@ public:
void set_multi(bool multi = true) { m_multi = multi; } void set_multi(bool multi = true) { m_multi = multi; }
// device management // device management
input_device *add_device(const char *name, const char *id, void *internal = nullptr); input_device &add_device(std::string_view name, std::string_view id, void *internal = nullptr);
input_device *add_device(std::unique_ptr<input_device> &&new_device);
// misc helpers // misc helpers
input_item_class standard_item_class(input_item_id itemid) const; input_item_class standard_item_class(input_item_id itemid) const;
@ -293,10 +291,11 @@ public:
protected: protected:
// specific overrides // specific overrides
virtual std::unique_ptr<input_device> make_device(const char *name, const char *id, void *internal) = 0; virtual std::unique_ptr<input_device> make_device(std::string_view name, std::string_view id, void *internal) = 0;
private: private:
// indexing helpers // internal helpers
input_device &add_device(std::unique_ptr<input_device> &&new_device);
int newindex(input_device &device); int newindex(input_device &device);
// internal state // internal state
@ -321,7 +320,7 @@ public:
protected: protected:
// specific overrides // specific overrides
virtual std::unique_ptr<input_device> make_device(const char *name, const char *id, void *internal) override virtual std::unique_ptr<input_device> make_device(std::string_view name, std::string_view id, void *internal) override
{ {
return std::make_unique<input_device_keyboard>(manager(), name, id, internal); return std::make_unique<input_device_keyboard>(manager(), name, id, internal);
} }
@ -343,7 +342,7 @@ public:
protected: protected:
// specific overrides // specific overrides
virtual std::unique_ptr<input_device> make_device(const char *name, const char *id, void *internal) override virtual std::unique_ptr<input_device> make_device(std::string_view name, std::string_view id, void *internal) override
{ {
return std::make_unique<input_device_mouse>(manager(), name, id, internal); return std::make_unique<input_device_mouse>(manager(), name, id, internal);
} }
@ -361,7 +360,7 @@ public:
protected: protected:
// specific overrides // specific overrides
virtual std::unique_ptr<input_device> make_device(const char *name, const char *id, void *internal) override virtual std::unique_ptr<input_device> make_device(std::string_view name, std::string_view id, void *internal) override
{ {
return std::make_unique<input_device_lightgun>(manager(), name, id, internal); return std::make_unique<input_device_lightgun>(manager(), name, id, internal);
} }
@ -386,7 +385,7 @@ public:
protected: protected:
// specific overrides // specific overrides
virtual std::unique_ptr<input_device> make_device(const char *name, const char *id, void *internal) override virtual std::unique_ptr<input_device> make_device(std::string_view name, std::string_view id, void *internal) override
{ {
return std::make_unique<input_device_joystick>(manager(), name, id, internal); return std::make_unique<input_device_joystick>(manager(), name, id, internal);
} }

View File

@ -2067,18 +2067,18 @@ void ioport_manager::load_config(config_type cfg_type, config_level cfg_level, u
// iterate over all the remap nodes // iterate over all the remap nodes
load_remap_table(*parentnode); load_remap_table(*parentnode);
devicemap_table_type devicemap_table; input_manager::devicemap_table devicemap;
for (util::xml::data_node const *mapdevice_node = parentnode->get_child("mapdevice"); mapdevice_node != nullptr; mapdevice_node = mapdevice_node->get_next_sibling("mapdevice")) for (util::xml::data_node const *mapdevice_node = parentnode->get_child("mapdevice"); mapdevice_node != nullptr; mapdevice_node = mapdevice_node->get_next_sibling("mapdevice"))
{ {
char const *const devicename = mapdevice_node->get_attribute_string("device", nullptr); char const *const devicename = mapdevice_node->get_attribute_string("device", nullptr);
char const *const controllername = mapdevice_node->get_attribute_string("controller", nullptr); char const *const controllername = mapdevice_node->get_attribute_string("controller", nullptr);
if (devicename && controllername) if (devicename && controllername)
devicemap_table.emplace(devicename, controllername); devicemap.emplace(devicename, controllername);
} }
// map device to controller if we have a device map // map device to controller if we have a device map
if (!devicemap_table.empty()) if (!devicemap.empty())
machine().input().map_device_to_controller(devicemap_table); machine().input().map_device_to_controller(devicemap);
} }
// iterate over all the port nodes // iterate over all the port nodes

View File

@ -8,21 +8,17 @@
// //
//============================================================ //============================================================
#include "input_module.h"
#include "modules/lib/osdobj_common.h" #include "modules/lib/osdobj_common.h"
#include <memory>
// MAME headers // MAME headers
#include "emu.h" #include "emu.h"
#include "input_common.h"
// winnt.h defines this // winnt.h defines this
#ifdef DELETE #ifdef DELETE
#undef DELETE #undef DELETE
#endif #endif
#include "input_common.h"
//============================================================ //============================================================
// Keyboard translation table // Keyboard translation table
//============================================================ //============================================================

View File

@ -7,20 +7,21 @@
// SDLMAME by Olivier Galibert and R. Belmont // SDLMAME by Olivier Galibert and R. Belmont
// //
//============================================================ //============================================================
#ifndef MAME_OSD_INPUT_INPUT_COMMON_H
#define MAME_OSD_INPUT_INPUT_COMMON_H
#ifndef INPUT_COMMON_H_ #pragma once
#define INPUT_COMMON_H_
#include "input_module.h" #include "input_module.h"
#include "inputdev.h" #include "inputdev.h"
#include <algorithm>
#include <chrono> #include <chrono>
#include <functional>
#include <memory> #include <memory>
#include <mutex> #include <mutex>
#include <queue> #include <queue>
#include <algorithm>
#include <functional>
//============================================================ //============================================================
@ -201,8 +202,8 @@ class device_info
friend input_device_list; friend input_device_list;
private: private:
std::string m_name; const std::string m_name;
std::string m_id; const std::string m_id;
input_device * m_device; input_device * m_device;
running_machine & m_machine; running_machine & m_machine;
input_module & m_module; input_module & m_module;
@ -210,9 +211,9 @@ private:
public: public:
// Constructor // Constructor
device_info(running_machine &machine, const char *name, const char *id, input_device_class deviceclass, input_module &module) device_info(running_machine &machine, std::string &&name, std::string &&id, input_device_class deviceclass, input_module &module) :
: m_name(name), m_name(std::move(name)),
m_id(id), m_id(std::move(id)),
m_device(nullptr), m_device(nullptr),
m_machine(machine), m_machine(machine),
m_module(module), m_module(module),
@ -221,18 +222,18 @@ public:
} }
// Destructor // Destructor
virtual ~device_info() {} virtual ~device_info() { }
// Getters // Getters
running_machine & machine() const { return m_machine; } running_machine & machine() const { return m_machine; }
const char * name() const { return m_name.c_str(); } const std::string & name() const { return m_name; }
const char * id() const { return m_id.c_str(); } const std::string & id() const { return m_id; }
input_device * device() const { return m_device; } input_device * device() const { return m_device; }
input_module & module() const { return m_module; } input_module & module() const { return m_module; }
input_device_class deviceclass() const { return m_deviceclass; } input_device_class deviceclass() const { return m_deviceclass; }
// Poll and reset methods // Poll and reset methods
virtual void poll() {}; virtual void poll() { }
virtual void reset() = 0; virtual void reset() = 0;
}; };
@ -254,8 +255,8 @@ protected:
virtual void process_event(TEvent &ev) = 0; virtual void process_event(TEvent &ev) = 0;
public: public:
event_based_device(running_machine &machine, const char *name, const char *id, input_device_class deviceclass, input_module &module) event_based_device(running_machine &machine, std::string &&name, std::string &&id, input_device_class deviceclass, input_module &module)
: device_info(machine, name, id, deviceclass, module) : device_info(machine, std::move(name), std::move(id), deviceclass, module)
{ {
} }
@ -310,10 +311,10 @@ public:
device->reset(); device->reset();
} }
void free_device(device_info* devinfo) void free_device(device_info &devinfo)
{ {
// find the device to remove // find the device to remove
auto device_matches = [devinfo](std::unique_ptr<device_info> &device) { return devinfo == device.get(); }; const auto device_matches = [&devinfo] (std::unique_ptr<device_info> &device) { return &devinfo == device.get(); };
m_list.erase(std::remove_if(std::begin(m_list), std::end(m_list), device_matches), m_list.end()); m_list.erase(std::remove_if(std::begin(m_list), std::end(m_list), device_matches), m_list.end());
} }
@ -330,24 +331,22 @@ public:
} }
template <typename TActual, typename... TArgs> template <typename TActual, typename... TArgs>
TActual* create_device(running_machine &machine, const char *name, const char *id, input_module &module, TArgs&&... args) TActual &create_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module, TArgs&&... args)
{ {
// allocate the device object // allocate the device object
auto devinfo = std::make_unique<TActual>(machine, name, id, module, std::forward<TArgs>(args)...); auto devinfo = std::make_unique<TActual>(machine, std::move(name), std::move(id), module, std::forward<TArgs>(args)...);
return add_device(machine, std::move(devinfo)); return add_device(machine, std::move(devinfo));
} }
template <typename TActual> template <typename TActual>
TActual* add_device(running_machine &machine, std::unique_ptr<TActual> devinfo) TActual &add_device(running_machine &machine, std::unique_ptr<TActual> devinfo)
{ {
// Add the device to the machine // Add the device to the machine
devinfo->m_device = machine.input().device_class(devinfo->deviceclass()).add_device(devinfo->name(), devinfo->id(), devinfo.get()); devinfo->m_device = &machine.input().device_class(devinfo->deviceclass()).add_device(devinfo->name(), devinfo->id(), devinfo.get());
// append us to the list // append us to the list
m_list.push_back(std::move(devinfo)); return *static_cast<TActual *>(m_list.emplace_back(std::move(devinfo)).get());
return static_cast<TActual*>(m_list.back().get());
} }
}; };
@ -426,8 +425,8 @@ typedef std::chrono::time_point<std::chrono::high_resolution_clock> timepoint_ty
class input_module_base : public input_module class input_module_base : public input_module
{ {
public: public:
input_module_base(const char *type, const char* name) input_module_base(const char *type, const char* name) :
: input_module(type, name), input_module(type, name),
m_input_enabled(false), m_input_enabled(false),
m_mouse_enabled(false), m_mouse_enabled(false),
m_lightgun_enabled(false), m_lightgun_enabled(false),
@ -544,7 +543,7 @@ int generic_axis_get_state(void *device_internal, void *item_internal)
// default_button_name // default_button_name
//============================================================ //============================================================
inline static const char *default_button_name(int which) inline const char *default_button_name(int which)
{ {
static char buffer[20]; static char buffer[20];
snprintf(buffer, std::size(buffer), "B%d", which); snprintf(buffer, std::size(buffer), "B%d", which);
@ -555,7 +554,7 @@ inline static const char *default_button_name(int which)
// default_pov_name // default_pov_name
//============================================================ //============================================================
inline static const char *default_pov_name(int which) inline const char *default_pov_name(int which)
{ {
static char buffer[20]; static char buffer[20];
snprintf(buffer, std::size(buffer), "POV%d", which); snprintf(buffer, std::size(buffer), "POV%d", which);
@ -569,7 +568,7 @@ const char *const default_axis_name[] =
"RY", "RZ", "SL1", "SL2" "RY", "RZ", "SL1", "SL2"
}; };
inline static int32_t normalize_absolute_axis(double raw, double rawmin, double rawmax) inline int32_t normalize_absolute_axis(double raw, double rawmin, double rawmax)
{ {
double center = (rawmax + rawmin) / 2.0; double center = (rawmax + rawmin) / 2.0;
@ -577,19 +576,18 @@ inline static int32_t normalize_absolute_axis(double raw, double rawmin, double
if (rawmin >= rawmax) if (rawmin >= rawmax)
return int32_t(raw); return int32_t(raw);
// above center
if (raw >= center) if (raw >= center)
{ {
// above center
double result = (raw - center) * INPUT_ABSOLUTE_MAX / (rawmax - center); double result = (raw - center) * INPUT_ABSOLUTE_MAX / (rawmax - center);
return std::min(result, (double)INPUT_ABSOLUTE_MAX); return std::min(result, (double)INPUT_ABSOLUTE_MAX);
} }
// below center
else else
{ {
// below center
double result = -((center - raw) * (double)-INPUT_ABSOLUTE_MIN / (center - rawmin)); double result = -((center - raw) * (double)-INPUT_ABSOLUTE_MIN / (center - rawmin));
return std::max(result, (double)INPUT_ABSOLUTE_MIN); return std::max(result, (double)INPUT_ABSOLUTE_MIN);
} }
} }
#endif // INPUT_COMMON_H_ #endif // MAME_OSD_INPUT_INPUT_COMMON_H

View File

@ -38,17 +38,44 @@
using namespace Microsoft::WRL; using namespace Microsoft::WRL;
static int32_t dinput_joystick_pov_get_state(void *device_internal, void *item_internal); namespace {
//============================================================
// dinput_joystick_pov_get_state
//============================================================
int32_t dinput_joystick_pov_get_state(void *device_internal, void *item_internal)
{
auto *devinfo = static_cast<dinput_joystick_device *>(device_internal);
int povnum = reinterpret_cast<uintptr_t>(item_internal) / 4;
int povdir = reinterpret_cast<uintptr_t>(item_internal) % 4;
int32_t result = 0;
// get the current state
devinfo->module().poll_if_necessary(devinfo->machine());
const DWORD pov = devinfo->joystick.state.rgdwPOV[povnum];
// if invalid, return 0
if ((pov & 0xffff) == 0xffff)
return result;
// return the current state
switch (povdir)
{
case POVDIR_LEFT: result = (pov >= 22500 && pov <= 31500); break;
case POVDIR_RIGHT: result = (pov >= 4500 && pov <= 13500); break;
case POVDIR_UP: result = (pov >= 31500 || pov <= 4500); break;
case POVDIR_DOWN: result = (pov >= 13500 && pov <= 22500); break;
}
return result;
}
//============================================================ //============================================================
// dinput_set_dword_property // dinput_set_dword_property
//============================================================ //============================================================
#if DIRECTINPUT_VERSION >= 0x0800 HRESULT dinput_set_dword_property(ComPtr<IDirectInputDevice8> device, REFGUID property_guid, DWORD object, DWORD how, DWORD value)
static HRESULT dinput_set_dword_property(ComPtr<IDirectInputDevice8> device, REFGUID property_guid, DWORD object, DWORD how, DWORD value)
#else
static HRESULT dinput_set_dword_property(ComPtr<IDirectInputDevice> device, REFGUID property_guid, DWORD object, DWORD how, DWORD value)
#endif
{ {
DIPROPDWORD dipdw; DIPROPDWORD dipdw;
@ -61,144 +88,6 @@ static HRESULT dinput_set_dword_property(ComPtr<IDirectInputDevice> device, REFG
return device->SetProperty(property_guid, &dipdw.diph); return device->SetProperty(property_guid, &dipdw.diph);
} }
//============================================================
// dinput_device - base directinput device
//============================================================
dinput_device::dinput_device(running_machine &machine, const char *name, const char *id, input_device_class deviceclass, input_module &module)
: device_info(machine, name, id, deviceclass, module),
dinput({nullptr})
{
}
dinput_device::~dinput_device()
{
if (dinput.device != nullptr)
dinput.device.Reset();
}
HRESULT dinput_device::poll_dinput(LPVOID pState) const
{
HRESULT result;
// first poll the device, then get the state
#if DIRECTINPUT_VERSION >= 0x0800
dinput.device->Poll();
#else
if (dinput.device2 != nullptr)
dinput.device2->Poll();
#endif
// GetDeviceState returns the immediate state
result = dinput.device->GetDeviceState(dinput.format->dwDataSize, pState);
// handle lost inputs here
if (result == DIERR_INPUTLOST || result == DIERR_NOTACQUIRED)
{
result = dinput.device->Acquire();
if (result == DI_OK)
result = dinput.device->GetDeviceState(dinput.format->dwDataSize, pState);
}
return result;
}
//============================================================
// dinput_keyboard_device - directinput keyboard device
//============================================================
dinput_keyboard_device::dinput_keyboard_device(running_machine &machine, const char *name, const char *id, input_module &module)
: dinput_device(machine, name, id, DEVICE_CLASS_KEYBOARD, module),
keyboard({{0}})
{
}
// Polls the direct input immediate state
void dinput_keyboard_device::poll()
{
std::lock_guard<std::mutex> scope_lock(m_device_lock);
// Poll the state
dinput_device::poll_dinput(&keyboard.state);
}
void dinput_keyboard_device::reset()
{
memset(&keyboard.state, 0, sizeof(keyboard.state));
}
//============================================================
// dinput_api_helper - DirectInput API helper
//============================================================
dinput_api_helper::dinput_api_helper(int version)
: m_dinput(nullptr),
m_dinput_version(version),
m_dinput_create_prt(nullptr)
{
}
dinput_api_helper::~dinput_api_helper()
{
m_dinput.Reset();
}
int dinput_api_helper::initialize()
{
HRESULT result;
#if DIRECTINPUT_VERSION >= 0x0800
if (m_dinput_version >= 0x0800)
{
result = DirectInput8Create(GetModuleHandleUni(), m_dinput_version, IID_IDirectInput8, reinterpret_cast<void **>(m_dinput.GetAddressOf()), nullptr);
if (result != DI_OK)
{
m_dinput_version = 0;
return result;
}
}
else
#endif
{
m_dinput_dll = osd::dynamic_module::open({ "dinput.dll" });
m_dinput_create_prt = m_dinput_dll->bind<dinput_create_fn>("DirectInputCreateW");
if (m_dinput_create_prt == nullptr)
{
osd_printf_verbose("Legacy DirectInput library dinput.dll is not available\n");
return ERROR_DLL_NOT_FOUND;
}
// first attempt to initialize DirectInput at v7
m_dinput_version = 0x0700;
result = (*m_dinput_create_prt)(GetModuleHandleUni(), m_dinput_version, m_dinput.GetAddressOf(), nullptr);
if (result != DI_OK)
{
// if that fails, try version 5
m_dinput_version = 0x0500;
result = (*m_dinput_create_prt)(GetModuleHandleUni(), m_dinput_version, m_dinput.GetAddressOf(), nullptr);
if (result != DI_OK)
{
m_dinput_version = 0;
return result;
}
}
}
osd_printf_verbose("DirectInput: Using DirectInput %d\n", m_dinput_version >> 8);
return 0;
}
HRESULT dinput_api_helper::enum_attached_devices(int devclass, device_enum_interface *enumerate_interface, void *state) const
{
device_enum_interface::dinput_callback_context ctx;
ctx.self = enumerate_interface;
ctx.state = state;
return m_dinput->EnumDevices(devclass, device_enum_interface::enum_callback, &ctx, DIEDFL_ATTACHEDONLY);
}
//============================================================ //============================================================
// dinput_module - base directinput module // dinput_module - base directinput module
@ -218,7 +107,7 @@ public:
int init_internal() override int init_internal() override
{ {
m_dinput_helper = std::make_unique<dinput_api_helper>(DIRECTINPUT_VERSION); m_dinput_helper = std::make_unique<dinput_api_helper>();
int result = m_dinput_helper->initialize(); int result = m_dinput_helper->initialize();
if (result != 0) if (result != 0)
return result; return result;
@ -236,7 +125,7 @@ public:
{ {
HRESULT result = m_dinput_helper->enum_attached_devices(dinput_devclass(), this, &machine); HRESULT result = m_dinput_helper->enum_attached_devices(dinput_devclass(), this, &machine);
if (result != DI_OK) if (result != DI_OK)
fatalerror("DirectInput: Unable to enumerate keyboards (result=%08X)\n", static_cast<uint32_t>(result)); fatalerror("DirectInput: Unable to enumerate devices (result=%08X)\n", uint32_t(result));
} }
static std::string device_item_name(dinput_device * devinfo, int offset, const char * defstring, const TCHAR * suffix) static std::string device_item_name(dinput_device * devinfo, int offset, const char * defstring, const TCHAR * suffix)
@ -286,11 +175,7 @@ public:
int dinput_devclass() override int dinput_devclass() override
{ {
#if DIRECTINPUT_VERSION >= 0x0800
return DI8DEVCLASS_KEYBOARD; return DI8DEVCLASS_KEYBOARD;
#else
return DIDEVTYPE_KEYBOARD;
#endif
} }
BOOL device_enum_callback(LPCDIDEVICEINSTANCE instance, LPVOID ref) override BOOL device_enum_callback(LPCDIDEVICEINSTANCE instance, LPVOID ref) override
@ -316,7 +201,7 @@ public:
name = device_item_name(devinfo, keynum, defname, nullptr); name = device_item_name(devinfo, keynum, defname, nullptr);
// add the item to the device // add the item to the device
devinfo->device()->add_item(name.c_str(), itemid, generic_button_get_state<std::uint8_t>, &devinfo->keyboard.state[keynum]); devinfo->device()->add_item(name, itemid, generic_button_get_state<std::uint8_t>, &devinfo->keyboard.state[keynum]);
} }
exit: exit:
@ -324,29 +209,6 @@ public:
} }
}; };
dinput_mouse_device::dinput_mouse_device(running_machine &machine, const char *name, const char *id, input_module &module)
: dinput_device(machine, name, id, DEVICE_CLASS_MOUSE, module),
mouse({0})
{
}
void dinput_mouse_device::poll()
{
// poll
dinput_device::poll_dinput(&mouse);
// scale the axis data
mouse.lX *= INPUT_RELATIVE_PER_PIXEL;
mouse.lY *= INPUT_RELATIVE_PER_PIXEL;
mouse.lZ *= INPUT_RELATIVE_PER_PIXEL;
}
void dinput_mouse_device::reset()
{
memset(&mouse, 0, sizeof(mouse));
}
class mouse_input_dinput : public dinput_module class mouse_input_dinput : public dinput_module
{ {
public: public:
@ -357,11 +219,7 @@ public:
int dinput_devclass() override int dinput_devclass() override
{ {
#if DIRECTINPUT_VERSION >= 0x0800
return DI8DEVCLASS_POINTER; return DI8DEVCLASS_POINTER;
#else
return DIDEVTYPE_MOUSE;
#endif
} }
BOOL device_enum_callback(LPCDIDEVICEINSTANCE instance, LPVOID ref) override BOOL device_enum_callback(LPCDIDEVICEINSTANCE instance, LPVOID ref) override
@ -373,7 +231,7 @@ public:
// allocate and link in a new device // allocate and link in a new device
devinfo = m_dinput_helper->create_device<dinput_mouse_device>(machine, *this, instance, &c_dfDIMouse2, &c_dfDIMouse, dinput_cooperative_level::FOREGROUND); devinfo = m_dinput_helper->create_device<dinput_mouse_device>(machine, *this, instance, &c_dfDIMouse2, &c_dfDIMouse, dinput_cooperative_level::FOREGROUND);
if (devinfo == nullptr) if (!devinfo)
goto exit; goto exit;
// set relative mode on the mouse device // set relative mode on the mouse device
@ -394,7 +252,7 @@ public:
// add to the mouse device and optionally to the gun device as well // add to the mouse device and optionally to the gun device as well
std::string name = device_item_name(devinfo, offsetof(DIMOUSESTATE, lX) + axisnum * sizeof(LONG), default_axis_name[axisnum], nullptr); std::string name = device_item_name(devinfo, offsetof(DIMOUSESTATE, lX) + axisnum * sizeof(LONG), default_axis_name[axisnum], nullptr);
devinfo->device()->add_item( devinfo->device()->add_item(
name.c_str(), name,
static_cast<input_item_id>(ITEM_ID_XAXIS + axisnum), static_cast<input_item_id>(ITEM_ID_XAXIS + axisnum),
generic_axis_get_state<LONG>, generic_axis_get_state<LONG>,
&devinfo->mouse.lX + axisnum); &devinfo->mouse.lX + axisnum);
@ -408,7 +266,7 @@ public:
// add to the mouse device // add to the mouse device
std::string name = device_item_name(devinfo, offset, default_button_name(butnum), nullptr); std::string name = device_item_name(devinfo, offset, default_button_name(butnum), nullptr);
devinfo->device()->add_item( devinfo->device()->add_item(
name.c_str(), name,
static_cast<input_item_id>(ITEM_ID_BUTTON1 + butnum), static_cast<input_item_id>(ITEM_ID_BUTTON1 + butnum),
generic_button_get_state<BYTE>, generic_button_get_state<BYTE>,
&devinfo->mouse.rgbButtons[butnum]); &devinfo->mouse.rgbButtons[butnum]);
@ -418,140 +276,12 @@ public:
return DIENUM_CONTINUE; return DIENUM_CONTINUE;
error: error:
if (devinfo != nullptr) if (devinfo)
devicelist()->free_device(devinfo); devicelist()->free_device(*devinfo);
goto exit; goto exit;
} }
}; };
dinput_joystick_device::dinput_joystick_device(running_machine &machine, const char *name, const char *id, input_module &module)
: dinput_device(machine, name, id, DEVICE_CLASS_JOYSTICK, module),
joystick({{0}})
{
}
void dinput_joystick_device::reset()
{
memset(&joystick.state, 0, sizeof(joystick.state));
}
void dinput_joystick_device::poll()
{
int axisnum;
// poll the device first
if (dinput_device::poll_dinput(&joystick.state) != ERROR_SUCCESS)
return;
// normalize axis values
for (axisnum = 0; axisnum < 8; axisnum++)
{
LONG *axis = (&joystick.state.lX) + axisnum;
*axis = normalize_absolute_axis(*axis, joystick.rangemin[axisnum], joystick.rangemax[axisnum]);
}
}
int dinput_joystick_device::configure()
{
HRESULT result;
uint32_t axisnum, axiscount;
auto devicelist = static_cast<input_module_base&>(module()).devicelist();
// temporary approximation of index
int devindex = devicelist->size();
// set absolute mode
result = dinput_set_dword_property(dinput.device, DIPROP_AXISMODE, 0, DIPH_DEVICE, DIPROPAXISMODE_ABS);
if (result != DI_OK && result != DI_PROPNOEFFECT)
osd_printf_warning("DirectInput: Unable to set absolute mode for joystick %d (%s)\n", devindex, name());
// turn off deadzone; we do our own calculations
result = dinput_set_dword_property(dinput.device, DIPROP_DEADZONE, 0, DIPH_DEVICE, 0);
if (result != DI_OK && result != DI_PROPNOEFFECT)
osd_printf_warning("DirectInput: Unable to reset deadzone for joystick %d (%s)\n", devindex, name());
// turn off saturation; we do our own calculations
result = dinput_set_dword_property(dinput.device, DIPROP_SATURATION, 0, DIPH_DEVICE, 10000);
if (result != DI_OK && result != DI_PROPNOEFFECT)
osd_printf_warning("DirectInput: Unable to reset saturation for joystick %d (%s)\n", devindex, name());
// cap the number of axes, POVs, and buttons based on the format
dinput.caps.dwAxes = std::min(dinput.caps.dwAxes, DWORD(8));
dinput.caps.dwPOVs = std::min(dinput.caps.dwPOVs, DWORD(4));
dinput.caps.dwButtons = std::min(dinput.caps.dwButtons, DWORD(128));
// populate the axes
for (axisnum = axiscount = 0; axiscount < dinput.caps.dwAxes && axisnum < 8; axisnum++)
{
DIPROPRANGE dipr;
std::string name;
// fetch the range of this axis
dipr.diph.dwSize = sizeof(dipr);
dipr.diph.dwHeaderSize = sizeof(dipr.diph);
dipr.diph.dwObj = offsetof(DIJOYSTATE2, lX) + axisnum * sizeof(LONG);
dipr.diph.dwHow = DIPH_BYOFFSET;
result = dinput.device->GetProperty(DIPROP_RANGE, &dipr.diph);
if (result != DI_OK)
continue;
joystick.rangemin[axisnum] = dipr.lMin;
joystick.rangemax[axisnum] = dipr.lMax;
// populate the item description as well
name = dinput_module::device_item_name(this, offsetof(DIJOYSTATE2, lX) + axisnum * sizeof(LONG), default_axis_name[axisnum], nullptr);
device()->add_item(
name.c_str(),
static_cast<input_item_id>(ITEM_ID_XAXIS + axisnum),
generic_axis_get_state<LONG>,
&joystick.state.lX + axisnum);
axiscount++;
}
// populate the POVs
for (uint32_t povnum = 0; povnum < dinput.caps.dwPOVs; povnum++)
{
std::string name;
// left
name = dinput_module::device_item_name(this, offsetof(DIJOYSTATE2, rgdwPOV) + povnum * sizeof(DWORD), default_pov_name(povnum), TEXT("L"));
device()->add_item(name.c_str(), ITEM_ID_OTHER_SWITCH, dinput_joystick_pov_get_state, reinterpret_cast<void *>(static_cast<uintptr_t>(povnum * 4 + POVDIR_LEFT)));
// right
name = dinput_module::device_item_name(this, offsetof(DIJOYSTATE2, rgdwPOV) + povnum * sizeof(DWORD), default_pov_name(povnum), TEXT("R"));
device()->add_item(name.c_str(), ITEM_ID_OTHER_SWITCH, dinput_joystick_pov_get_state, reinterpret_cast<void *>(static_cast<uintptr_t>(povnum * 4 + POVDIR_RIGHT)));
// up
name = dinput_module::device_item_name(this, offsetof(DIJOYSTATE2, rgdwPOV) + povnum * sizeof(DWORD), default_pov_name(povnum), TEXT("U"));
device()->add_item(name.c_str(), ITEM_ID_OTHER_SWITCH, dinput_joystick_pov_get_state, reinterpret_cast<void *>(static_cast<uintptr_t>(povnum * 4 + POVDIR_UP)));
// down
name = dinput_module::device_item_name(this, offsetof(DIJOYSTATE2, rgdwPOV) + povnum * sizeof(DWORD), default_pov_name(povnum), TEXT("D"));
device()->add_item(name.c_str(), ITEM_ID_OTHER_SWITCH, dinput_joystick_pov_get_state, reinterpret_cast<void *>(static_cast<uintptr_t>(povnum * 4 + POVDIR_DOWN)));
}
// populate the buttons
for (uint32_t butnum = 0; butnum < dinput.caps.dwButtons; butnum++)
{
auto offset = reinterpret_cast<uintptr_t>(&static_cast<DIJOYSTATE2 *>(nullptr)->rgbButtons[butnum]);
std::string name = dinput_module::device_item_name(this, offset, default_button_name(butnum), nullptr);
input_item_id itemid;
if (butnum < INPUT_MAX_BUTTONS)
itemid = static_cast<input_item_id>(ITEM_ID_BUTTON1 + butnum);
else if (butnum < INPUT_MAX_BUTTONS + INPUT_MAX_ADD_SWITCH)
itemid = static_cast<input_item_id>(ITEM_ID_ADD_SWITCH1 - INPUT_MAX_BUTTONS + butnum);
else
itemid = ITEM_ID_OTHER_SWITCH;
device()->add_item(name.c_str(), itemid, generic_button_get_state<BYTE>, &joystick.state.rgbButtons[butnum]);
}
return 0;
}
class joystick_input_dinput : public dinput_module class joystick_input_dinput : public dinput_module
{ {
@ -563,11 +293,7 @@ public:
int dinput_devclass() override int dinput_devclass() override
{ {
#if DIRECTINPUT_VERSION >= 0x0800
return DI8DEVCLASS_GAMECTRL; return DI8DEVCLASS_GAMECTRL;
#else
return DIDEVTYPE_JOYSTICK;
#endif
} }
BOOL device_enum_callback(LPCDIDEVICEINSTANCE instance, LPVOID ref) override BOOL device_enum_callback(LPCDIDEVICEINSTANCE instance, LPVOID ref) override
@ -596,42 +322,273 @@ public:
} }
}; };
} // anonymous namespace
//============================================================ //============================================================
// dinput_joystick_pov_get_state // dinput_device - base directinput device
//============================================================ //============================================================
static int32_t dinput_joystick_pov_get_state(void *device_internal, void *item_internal) dinput_device::dinput_device(running_machine &machine, std::string &&name, std::string &&id, input_device_class deviceclass, input_module &module)
: device_info(machine, std::move(name), std::move(id), deviceclass, module),
dinput({nullptr})
{ {
auto *devinfo = static_cast<dinput_joystick_device *>(device_internal); }
int povnum = reinterpret_cast<uintptr_t>(item_internal) / 4;
int povdir = reinterpret_cast<uintptr_t>(item_internal) % 4;
int32_t result = 0;
DWORD pov;
// get the current state dinput_device::~dinput_device()
devinfo->module().poll_if_necessary(devinfo->machine()); {
pov = devinfo->joystick.state.rgdwPOV[povnum]; if (dinput.device)
dinput.device.Reset();
}
// if invalid, return 0 HRESULT dinput_device::poll_dinput(LPVOID pState) const
if ((pov & 0xffff) == 0xffff) {
return result; HRESULT result;
// return the current state // first poll the device, then get the state
switch (povdir) dinput.device->Poll();
// GetDeviceState returns the immediate state
result = dinput.device->GetDeviceState(dinput.format->dwDataSize, pState);
// handle lost inputs here
if (result == DIERR_INPUTLOST || result == DIERR_NOTACQUIRED)
{ {
case POVDIR_LEFT: result = (pov >= 22500 && pov <= 31500); break; result = dinput.device->Acquire();
case POVDIR_RIGHT: result = (pov >= 4500 && pov <= 13500); break; if (result == DI_OK)
case POVDIR_UP: result = (pov >= 31500 || pov <= 4500); break; result = dinput.device->GetDeviceState(dinput.format->dwDataSize, pState);
case POVDIR_DOWN: result = (pov >= 13500 && pov <= 22500); break;
} }
return result; return result;
} }
#else
//============================================================
// dinput_keyboard_device - directinput keyboard device
//============================================================
dinput_keyboard_device::dinput_keyboard_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module)
: dinput_device(machine, std::move(name), std::move(id), DEVICE_CLASS_KEYBOARD, module),
keyboard({{0}})
{
}
// Polls the direct input immediate state
void dinput_keyboard_device::poll()
{
std::lock_guard<std::mutex> scope_lock(m_device_lock);
// Poll the state
dinput_device::poll_dinput(&keyboard.state);
}
void dinput_keyboard_device::reset()
{
memset(&keyboard.state, 0, sizeof(keyboard.state));
}
//============================================================
// dinput_mouse_device - directinput mouse device
//============================================================
dinput_mouse_device::dinput_mouse_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module)
: dinput_device(machine, std::move(name), std::move(id), DEVICE_CLASS_MOUSE, module),
mouse({0})
{
}
void dinput_mouse_device::poll()
{
// poll
dinput_device::poll_dinput(&mouse);
// scale the axis data
mouse.lX *= INPUT_RELATIVE_PER_PIXEL;
mouse.lY *= INPUT_RELATIVE_PER_PIXEL;
mouse.lZ *= INPUT_RELATIVE_PER_PIXEL;
}
void dinput_mouse_device::reset()
{
memset(&mouse, 0, sizeof(mouse));
}
//============================================================
// dinput_joystick_device - directinput joystick device
//============================================================
dinput_joystick_device::dinput_joystick_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module)
: dinput_device(machine, std::move(name), std::move(id), DEVICE_CLASS_JOYSTICK, module),
joystick({{0}})
{
}
void dinput_joystick_device::reset()
{
memset(&joystick.state, 0, sizeof(joystick.state));
}
void dinput_joystick_device::poll()
{
int axisnum;
// poll the device first
if (dinput_device::poll_dinput(&joystick.state) != ERROR_SUCCESS)
return;
// normalize axis values
for (axisnum = 0; axisnum < 8; axisnum++)
{
LONG *axis = (&joystick.state.lX) + axisnum;
*axis = normalize_absolute_axis(*axis, joystick.rangemin[axisnum], joystick.rangemax[axisnum]);
}
}
int dinput_joystick_device::configure()
{
HRESULT result;
auto devicelist = static_cast<input_module_base&>(module()).devicelist();
// temporary approximation of index
int devindex = devicelist->size();
// set absolute mode
result = dinput_set_dword_property(dinput.device, DIPROP_AXISMODE, 0, DIPH_DEVICE, DIPROPAXISMODE_ABS);
if (result != DI_OK && result != DI_PROPNOEFFECT)
osd_printf_warning("DirectInput: Unable to set absolute mode for joystick %d (%s)\n", devindex, name());
// turn off deadzone; we do our own calculations
result = dinput_set_dword_property(dinput.device, DIPROP_DEADZONE, 0, DIPH_DEVICE, 0);
if (result != DI_OK && result != DI_PROPNOEFFECT)
osd_printf_warning("DirectInput: Unable to reset deadzone for joystick %d (%s)\n", devindex, name());
// turn off saturation; we do our own calculations
result = dinput_set_dword_property(dinput.device, DIPROP_SATURATION, 0, DIPH_DEVICE, 10000);
if (result != DI_OK && result != DI_PROPNOEFFECT)
osd_printf_warning("DirectInput: Unable to reset saturation for joystick %d (%s)\n", devindex, name());
// cap the number of axes, POVs, and buttons based on the format
dinput.caps.dwAxes = std::min(dinput.caps.dwAxes, DWORD(8));
dinput.caps.dwPOVs = std::min(dinput.caps.dwPOVs, DWORD(4));
dinput.caps.dwButtons = std::min(dinput.caps.dwButtons, DWORD(128));
// populate the axes
for (uint32_t axisnum = 0, axiscount = 0; axiscount < dinput.caps.dwAxes && axisnum < 8; axisnum++)
{
// fetch the range of this axis
DIPROPRANGE dipr;
dipr.diph.dwSize = sizeof(dipr);
dipr.diph.dwHeaderSize = sizeof(dipr.diph);
dipr.diph.dwObj = offsetof(DIJOYSTATE2, lX) + axisnum * sizeof(LONG);
dipr.diph.dwHow = DIPH_BYOFFSET;
result = dinput.device->GetProperty(DIPROP_RANGE, &dipr.diph);
if (result != DI_OK)
continue;
joystick.rangemin[axisnum] = dipr.lMin;
joystick.rangemax[axisnum] = dipr.lMax;
// populate the item description as well
std::string name = dinput_module::device_item_name(this, offsetof(DIJOYSTATE2, lX) + axisnum * sizeof(LONG), default_axis_name[axisnum], nullptr);
device()->add_item(
name,
static_cast<input_item_id>(ITEM_ID_XAXIS + axisnum),
generic_axis_get_state<LONG>,
&joystick.state.lX + axisnum);
axiscount++;
}
// populate the POVs
for (uint32_t povnum = 0; povnum < dinput.caps.dwPOVs; povnum++)
{
std::string name;
// left
name = dinput_module::device_item_name(this, offsetof(DIJOYSTATE2, rgdwPOV) + povnum * sizeof(DWORD), default_pov_name(povnum), TEXT("L"));
device()->add_item(name, ITEM_ID_OTHER_SWITCH, dinput_joystick_pov_get_state, reinterpret_cast<void *>(static_cast<uintptr_t>(povnum * 4 + POVDIR_LEFT)));
// right
name = dinput_module::device_item_name(this, offsetof(DIJOYSTATE2, rgdwPOV) + povnum * sizeof(DWORD), default_pov_name(povnum), TEXT("R"));
device()->add_item(name, ITEM_ID_OTHER_SWITCH, dinput_joystick_pov_get_state, reinterpret_cast<void *>(static_cast<uintptr_t>(povnum * 4 + POVDIR_RIGHT)));
// up
name = dinput_module::device_item_name(this, offsetof(DIJOYSTATE2, rgdwPOV) + povnum * sizeof(DWORD), default_pov_name(povnum), TEXT("U"));
device()->add_item(name, ITEM_ID_OTHER_SWITCH, dinput_joystick_pov_get_state, reinterpret_cast<void *>(static_cast<uintptr_t>(povnum * 4 + POVDIR_UP)));
// down
name = dinput_module::device_item_name(this, offsetof(DIJOYSTATE2, rgdwPOV) + povnum * sizeof(DWORD), default_pov_name(povnum), TEXT("D"));
device()->add_item(name, ITEM_ID_OTHER_SWITCH, dinput_joystick_pov_get_state, reinterpret_cast<void *>(static_cast<uintptr_t>(povnum * 4 + POVDIR_DOWN)));
}
// populate the buttons
for (uint32_t butnum = 0; butnum < dinput.caps.dwButtons; butnum++)
{
auto offset = reinterpret_cast<uintptr_t>(&static_cast<DIJOYSTATE2 *>(nullptr)->rgbButtons[butnum]);
std::string name = dinput_module::device_item_name(this, offset, default_button_name(butnum), nullptr);
input_item_id itemid;
if (butnum < INPUT_MAX_BUTTONS)
itemid = static_cast<input_item_id>(ITEM_ID_BUTTON1 + butnum);
else if (butnum < INPUT_MAX_BUTTONS + INPUT_MAX_ADD_SWITCH)
itemid = static_cast<input_item_id>(ITEM_ID_ADD_SWITCH1 - INPUT_MAX_BUTTONS + butnum);
else
itemid = ITEM_ID_OTHER_SWITCH;
device()->add_item(name, itemid, generic_button_get_state<BYTE>, &joystick.state.rgbButtons[butnum]);
}
return 0;
}
//============================================================
// dinput_api_helper - DirectInput API helper
//============================================================
dinput_api_helper::dinput_api_helper()
: m_dinput(nullptr),
m_dinput_create_prt(nullptr)
{
}
dinput_api_helper::~dinput_api_helper()
{
m_dinput.Reset();
}
int dinput_api_helper::initialize()
{
HRESULT result = DirectInput8Create(GetModuleHandleUni(), DIRECTINPUT_VERSION, IID_IDirectInput8, reinterpret_cast<void **>(m_dinput.GetAddressOf()), nullptr);
if (result != DI_OK)
{
return result;
}
osd_printf_verbose("DirectInput: Using DirectInput %d\n", DIRECTINPUT_VERSION >> 8);
return 0;
}
HRESULT dinput_api_helper::enum_attached_devices(int devclass, device_enum_interface *enumerate_interface, void *state) const
{
device_enum_interface::dinput_callback_context ctx;
ctx.self = enumerate_interface;
ctx.state = state;
return m_dinput->EnumDevices(devclass, device_enum_interface::enum_callback, &ctx, DIEDFL_ATTACHEDONLY);
}
#else // defined(OSD_WINDOWS)
MODULE_NOT_SUPPORTED(keyboard_input_dinput, OSD_KEYBOARDINPUT_PROVIDER, "dinput") MODULE_NOT_SUPPORTED(keyboard_input_dinput, OSD_KEYBOARDINPUT_PROVIDER, "dinput")
MODULE_NOT_SUPPORTED(mouse_input_dinput, OSD_MOUSEINPUT_PROVIDER, "dinput") MODULE_NOT_SUPPORTED(mouse_input_dinput, OSD_MOUSEINPUT_PROVIDER, "dinput")
MODULE_NOT_SUPPORTED(joystick_input_dinput, OSD_JOYSTICKINPUT_PROVIDER, "dinput") MODULE_NOT_SUPPORTED(joystick_input_dinput, OSD_JOYSTICKINPUT_PROVIDER, "dinput")
#endif
#endif // defined(OSD_WINDOWS)
MODULE_DEFINITION(KEYBOARDINPUT_DINPUT, keyboard_input_dinput) MODULE_DEFINITION(KEYBOARDINPUT_DINPUT, keyboard_input_dinput)
MODULE_DEFINITION(MOUSEINPUT_DINPUT, mouse_input_dinput) MODULE_DEFINITION(MOUSEINPUT_DINPUT, mouse_input_dinput)

View File

@ -1,5 +1,7 @@
#ifndef INPUT_DINPUT_H_ #ifndef MAME_OSD_INPUT_INPUT_DINPUT_H
#define INPUT_DINPUT_H_ #define MAME_OSD_INPUT_INPUT_DINPUT_H
#pragma once
#include "input_common.h" #include "input_common.h"
#include "modules/lib/osdlib.h" #include "modules/lib/osdlib.h"
@ -8,19 +10,6 @@
// dinput_device - base directinput device // dinput_device - base directinput device
//============================================================ //============================================================
// DirectInput-specific information about a device
struct dinput_api_state
{
#if DIRECTINPUT_VERSION >= 0x0800
Microsoft::WRL::ComPtr<IDirectInputDevice8> device;
#else
Microsoft::WRL::ComPtr<IDirectInputDevice> device;
Microsoft::WRL::ComPtr<IDirectInputDevice2> device2;
#endif
DIDEVCAPS caps;
LPCDIDATAFORMAT format;
};
class device_enum_interface class device_enum_interface
{ {
public: public:
@ -44,11 +33,7 @@ public:
}; };
// Typedef for dynamically loaded function // Typedef for dynamically loaded function
#if DIRECTINPUT_VERSION >= 0x0800
typedef HRESULT (WINAPI *dinput_create_fn)(HINSTANCE, DWORD, LPDIRECTINPUT8 *, LPUNKNOWN); typedef HRESULT (WINAPI *dinput_create_fn)(HINSTANCE, DWORD, LPDIRECTINPUT8 *, LPUNKNOWN);
#else
typedef HRESULT (WINAPI *dinput_create_fn)(HINSTANCE, DWORD, LPDIRECTINPUT *, LPUNKNOWN);
#endif
enum class dinput_cooperative_level enum class dinput_cooperative_level
{ {
@ -59,17 +44,12 @@ enum class dinput_cooperative_level
class dinput_api_helper class dinput_api_helper
{ {
private: private:
#if DIRECTINPUT_VERSION >= 0x0800
Microsoft::WRL::ComPtr<IDirectInput8> m_dinput; Microsoft::WRL::ComPtr<IDirectInput8> m_dinput;
#else
Microsoft::WRL::ComPtr<IDirectInput> m_dinput;
#endif
int m_dinput_version;
osd::dynamic_module::ptr m_dinput_dll; osd::dynamic_module::ptr m_dinput_dll;
dinput_create_fn m_dinput_create_prt; dinput_create_fn m_dinput_create_prt;
public: public:
dinput_api_helper(int version); dinput_api_helper();
virtual ~dinput_api_helper(); virtual ~dinput_api_helper();
int initialize(); int initialize();
@ -93,36 +73,29 @@ public:
std::string utf8_instance_id = utf8_instance_name + " product_" + guid_to_string(instance->guidProduct) + " instance_" + guid_to_string(instance->guidInstance); std::string utf8_instance_id = utf8_instance_name + " product_" + guid_to_string(instance->guidProduct) + " instance_" + guid_to_string(instance->guidInstance);
// allocate memory for the device object // allocate memory for the device object
TDevice* devinfo = module.devicelist()->create_device<TDevice>(machine, utf8_instance_name.c_str(), utf8_instance_id.c_str(), module); TDevice &devinfo = module.devicelist()->create_device<TDevice>(machine, std::move(utf8_instance_name), std::move(utf8_instance_id), module);
// attempt to create a device // attempt to create a device
result = m_dinput->CreateDevice(instance->guidInstance, devinfo->dinput.device.GetAddressOf(), nullptr); result = m_dinput->CreateDevice(instance->guidInstance, devinfo.dinput.device.GetAddressOf(), nullptr);
if (result != DI_OK) if (result != DI_OK)
goto error; goto error;
#if DIRECTINPUT_VERSION < 0x0800
// try to get a version 2 device for it so we can use the poll method
result = devinfo->dinput.device.CopyTo(IID_IDirectInputDevice2, reinterpret_cast<void**>(devinfo->dinput.device2.GetAddressOf()));
if (result != DI_OK)
devinfo->dinput.device2 = nullptr;
#endif
// get the caps // get the caps
devinfo->dinput.caps.dwSize = sizeof(devinfo->dinput.caps); devinfo.dinput.caps.dwSize = sizeof(devinfo.dinput.caps);
result = devinfo->dinput.device->GetCapabilities(&devinfo->dinput.caps); result = devinfo.dinput.device->GetCapabilities(&devinfo.dinput.caps);
if (result != DI_OK) if (result != DI_OK)
goto error; goto error;
// attempt to set the data format // attempt to set the data format
devinfo->dinput.format = format1; devinfo.dinput.format = format1;
result = devinfo->dinput.device->SetDataFormat(devinfo->dinput.format); result = devinfo.dinput.device->SetDataFormat(devinfo.dinput.format);
if (result != DI_OK) if (result != DI_OK)
{ {
// use the secondary format if available // use the secondary format if available
if (format2 != nullptr) if (format2)
{ {
devinfo->dinput.format = format2; devinfo.dinput.format = format2;
result = devinfo->dinput.device->SetDataFormat(devinfo->dinput.format); result = devinfo.dinput.device->SetDataFormat(devinfo.dinput.format);
} }
if (result != DI_OK) if (result != DI_OK)
goto error; goto error;
@ -154,11 +127,11 @@ public:
} }
// set the cooperative level // set the cooperative level
result = devinfo->dinput.device->SetCooperativeLevel(hwnd, di_cooperative_level); result = devinfo.dinput.device->SetCooperativeLevel(hwnd, di_cooperative_level);
if (result != DI_OK) if (result != DI_OK)
goto error; goto error;
return devinfo; return &devinfo;
error: error:
module.devicelist()->free_device(devinfo); module.devicelist()->free_device(devinfo);
@ -187,9 +160,17 @@ public:
class dinput_device : public device_info class dinput_device : public device_info
{ {
public: public:
// DirectInput-specific information about a device
struct dinput_api_state
{
Microsoft::WRL::ComPtr<IDirectInputDevice8> device;
DIDEVCAPS caps;
LPCDIDATAFORMAT format;
};
dinput_api_state dinput; dinput_api_state dinput;
dinput_device(running_machine &machine, const char *name, const char *id, input_device_class deviceclass, input_module &module); dinput_device(running_machine &machine, std::string &&name, std::string &&id, input_device_class deviceclass, input_module &module);
virtual ~dinput_device(); virtual ~dinput_device();
protected: protected:
@ -204,7 +185,7 @@ private:
public: public:
keyboard_state keyboard; keyboard_state keyboard;
dinput_keyboard_device(running_machine &machine, const char *name, const char *id, input_module &module); dinput_keyboard_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module);
void poll() override; void poll() override;
void reset() override; void reset() override;
@ -216,7 +197,7 @@ public:
mouse_state mouse; mouse_state mouse;
public: public:
dinput_mouse_device(running_machine &machine, const char *name, const char *id, input_module &module); dinput_mouse_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module);
void poll() override; void poll() override;
void reset() override; void reset() override;
}; };
@ -234,11 +215,10 @@ class dinput_joystick_device : public dinput_device
public: public:
dinput_joystick_state joystick; dinput_joystick_state joystick;
public: public:
dinput_joystick_device(running_machine &machine, const char *name, const char *id, input_module &module); dinput_joystick_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module);
void reset() override; void reset() override;
void poll() override; void poll() override;
int configure(); int configure();
}; };
#endif // MAME_OSD_INPUT_INPUT_DINPUT_H
#endif

View File

@ -5,9 +5,10 @@
// input_module.h - OSD input module contracts // input_module.h - OSD input module contracts
// //
//============================================================ //============================================================
#ifndef MAME_OSD_INPUT_INPUT_MODULE_H
#define MAME_OSD_INPUT_INPUT_MODULE_H
#ifndef INPUT_MODULE_H_ #pragma once
#define INPUT_MODULE_H_
#include "osdepend.h" #include "osdepend.h"
@ -39,4 +40,4 @@ public:
#define OSD_LIGHTGUNINPUT_PROVIDER "lightgunprovider" #define OSD_LIGHTGUNINPUT_PROVIDER "lightgunprovider"
#define OSD_JOYSTICKINPUT_PROVIDER "joystickprovider" #define OSD_JOYSTICKINPUT_PROVIDER "joystickprovider"
#endif /* INPUT_MODULE_H_ */ #endif // MAME_OSD_INPUT_INPUT_MODULE_H

View File

@ -12,13 +12,12 @@
class keyboard_input_none : public input_module class keyboard_input_none : public input_module
{ {
public: public:
keyboard_input_none() keyboard_input_none() : input_module(OSD_KEYBOARDINPUT_PROVIDER, "none") { }
: input_module(OSD_KEYBOARDINPUT_PROVIDER, "none") {}
int init(const osd_options &options) override { return 0; } int init(const osd_options &options) override { return 0; }
void poll_if_necessary(running_machine &machine) override {}; void poll_if_necessary(running_machine &machine) override { }
void input_init(running_machine &machine) override {}; void input_init(running_machine &machine) override { }
void pause() override {}; void pause() override { }
void resume() override {}; void resume() override { }
}; };
MODULE_DEFINITION(KEYBOARD_NONE, keyboard_input_none) MODULE_DEFINITION(KEYBOARD_NONE, keyboard_input_none)
@ -26,13 +25,12 @@ MODULE_DEFINITION(KEYBOARD_NONE, keyboard_input_none)
class mouse_input_none : public input_module class mouse_input_none : public input_module
{ {
public: public:
mouse_input_none() mouse_input_none() : input_module(OSD_MOUSEINPUT_PROVIDER, "none") { }
: input_module(OSD_MOUSEINPUT_PROVIDER, "none") {}
int init(const osd_options &options) override { return 0; } int init(const osd_options &options) override { return 0; }
void input_init(running_machine &machine) override {}; void input_init(running_machine &machine) override { }
void poll_if_necessary(running_machine &machine) override {}; void poll_if_necessary(running_machine &machine) override { }
void pause() override {}; void pause() override { }
void resume() override {}; void resume() override { }
}; };
MODULE_DEFINITION(MOUSE_NONE, mouse_input_none) MODULE_DEFINITION(MOUSE_NONE, mouse_input_none)
@ -40,13 +38,12 @@ MODULE_DEFINITION(MOUSE_NONE, mouse_input_none)
class lightgun_input_none : public input_module class lightgun_input_none : public input_module
{ {
public: public:
lightgun_input_none() lightgun_input_none() : input_module(OSD_LIGHTGUNINPUT_PROVIDER, "none") { }
: input_module(OSD_LIGHTGUNINPUT_PROVIDER, "none") {}
int init(const osd_options &options) override { return 0; } int init(const osd_options &options) override { return 0; }
void input_init(running_machine &machine) override {}; void input_init(running_machine &machine) override { }
void poll_if_necessary(running_machine &machine) override {}; void poll_if_necessary(running_machine &machine) override { }
void pause() override {}; void pause() override { }
void resume() override {}; void resume() override { }
}; };
MODULE_DEFINITION(LIGHTGUN_NONE, lightgun_input_none) MODULE_DEFINITION(LIGHTGUN_NONE, lightgun_input_none)
@ -54,13 +51,12 @@ MODULE_DEFINITION(LIGHTGUN_NONE, lightgun_input_none)
class joystick_input_none : public input_module class joystick_input_none : public input_module
{ {
public: public:
joystick_input_none() joystick_input_none() : input_module(OSD_JOYSTICKINPUT_PROVIDER, "none") { }
: input_module(OSD_JOYSTICKINPUT_PROVIDER, "none") {}
int init(const osd_options &options) override { return 0; } int init(const osd_options &options) override { return 0; }
void input_init(running_machine &machine) override {}; void input_init(running_machine &machine) override { }
void poll_if_necessary(running_machine &machine) override {}; void poll_if_necessary(running_machine &machine) override { }
void pause() override {}; void pause() override { }
void resume() override {}; void resume() override { }
}; };
MODULE_DEFINITION(JOYSTICK_NONE, joystick_input_none) MODULE_DEFINITION(JOYSTICK_NONE, joystick_input_none)

View File

@ -16,9 +16,9 @@
#include <tchar.h> #include <tchar.h>
#undef interface #undef interface
#include <mutex>
#include <functional>
#include <algorithm> #include <algorithm>
#include <functional>
#include <mutex>
// MAME headers // MAME headers
#include "emu.h" #include "emu.h"
@ -274,8 +274,8 @@ private:
HANDLE m_handle = nullptr; HANDLE m_handle = nullptr;
public: public:
rawinput_device(running_machine &machine, const char *name, const char *id, input_device_class deviceclass, input_module &module) : rawinput_device(running_machine &machine, std::string &&name, std::string &&id, input_device_class deviceclass, input_module &module) :
event_based_device(machine, name, id, deviceclass, module) event_based_device(machine, std::move(name), std::move(id), deviceclass, module)
{ {
} }
@ -292,8 +292,8 @@ class rawinput_keyboard_device : public rawinput_device
public: public:
keyboard_state keyboard; keyboard_state keyboard;
rawinput_keyboard_device(running_machine &machine, const char *name, const char *id, input_module &module) : rawinput_keyboard_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module) :
rawinput_device(machine, name, id, DEVICE_CLASS_KEYBOARD, module), rawinput_device(machine, std::move(name), std::move(id), DEVICE_CLASS_KEYBOARD, module),
keyboard({{0}}) keyboard({{0}})
{ {
} }
@ -328,8 +328,8 @@ private:
public: public:
mouse_state mouse; mouse_state mouse;
rawinput_mouse_device(running_machine &machine, const char *name, const char *id, input_module &module) : rawinput_mouse_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module) :
rawinput_device(machine, name, id, DEVICE_CLASS_MOUSE, module), rawinput_device(machine, std::move(name), std::move(id), DEVICE_CLASS_MOUSE, module),
mouse({0}) mouse({0})
{ {
} }
@ -388,8 +388,8 @@ private:
public: public:
mouse_state lightgun; mouse_state lightgun;
rawinput_lightgun_device(running_machine &machine, const char *name, const char *id, input_module &module) : rawinput_lightgun_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module) :
rawinput_device(machine, name, id, DEVICE_CLASS_LIGHTGUN, module), rawinput_device(machine, std::move(name), std::move(id), DEVICE_CLASS_LIGHTGUN, module),
lightgun({0}) lightgun({0})
{ {
} }
@ -545,17 +545,17 @@ protected:
std::wstring name = rawinput_device_improve_name(tname.get()); std::wstring name = rawinput_device_improve_name(tname.get());
// convert name to utf8 // convert name to utf8
std::string utf8_name = osd::text::from_wstring(name.c_str()); std::string utf8_name = osd::text::from_wstring(name);
// set device id to raw input name // set device id to raw input name
std::string utf8_id = osd::text::from_wstring(tname.get()); std::string utf8_id = osd::text::from_wstring(tname.get());
TDevice *devinfo = devicelist()->create_device<TDevice>(machine, utf8_name.c_str(), utf8_id.c_str(), *this); TDevice &devinfo = devicelist()->create_device<TDevice>(machine, std::move(utf8_name), std::move(utf8_id), *this);
// Add the handle // Add the handle
devinfo->set_handle(rawinputdevice->hDevice); devinfo.set_handle(rawinputdevice->hDevice);
return devinfo; return &devinfo;
} }
bool handle_input_event(input_event eventid, void *eventdata) override bool handle_input_event(input_event eventid, void *eventdata) override
@ -658,7 +658,7 @@ protected:
std::string name = osd::text::from_wstring(keyname); std::string name = osd::text::from_wstring(keyname);
// add the item to the device // add the item to the device
devinfo->device()->add_item(name.c_str(), itemid, generic_button_get_state<std::uint8_t>, &devinfo->keyboard.state[keynum]); devinfo->device()->add_item(name, itemid, generic_button_get_state<std::uint8_t>, &devinfo->keyboard.state[keynum]);
} }
} }
}; };
@ -764,11 +764,13 @@ protected:
} // anonymous namespace } // anonymous namespace
#else #else // defined(OSD_WINDOWS)
MODULE_NOT_SUPPORTED(keyboard_input_rawinput, OSD_KEYBOARDINPUT_PROVIDER, "rawinput") MODULE_NOT_SUPPORTED(keyboard_input_rawinput, OSD_KEYBOARDINPUT_PROVIDER, "rawinput")
MODULE_NOT_SUPPORTED(mouse_input_rawinput, OSD_MOUSEINPUT_PROVIDER, "rawinput") MODULE_NOT_SUPPORTED(mouse_input_rawinput, OSD_MOUSEINPUT_PROVIDER, "rawinput")
MODULE_NOT_SUPPORTED(lightgun_input_rawinput, OSD_LIGHTGUNINPUT_PROVIDER, "rawinput") MODULE_NOT_SUPPORTED(lightgun_input_rawinput, OSD_LIGHTGUNINPUT_PROVIDER, "rawinput")
#endif
#endif // defined(OSD_WINDOWS)
MODULE_DEFINITION(KEYBOARDINPUT_RAWINPUT, keyboard_input_rawinput) MODULE_DEFINITION(KEYBOARDINPUT_RAWINPUT, keyboard_input_rawinput)
MODULE_DEFINITION(MOUSEINPUT_RAWINPUT, mouse_input_rawinput) MODULE_DEFINITION(MOUSEINPUT_RAWINPUT, mouse_input_rawinput)

View File

@ -46,6 +46,8 @@
#endif #endif
namespace {
// FIXME: sdl does not properly report the window for certain OS. // FIXME: sdl does not properly report the window for certain OS.
#define GET_FOCUS_WINDOW(ev) focus_window() #define GET_FOCUS_WINDOW(ev) focus_window()
//#define GET_FOCUS_WINDOW(ev) window_from_id((ev)->windowID) //#define GET_FOCUS_WINDOW(ev) window_from_id((ev)->windowID)
@ -62,7 +64,7 @@ struct key_lookup_table
#define KE5(A, B, C, D, E) KE(A) KE(B) KE(C) KE(D) KE(E) #define KE5(A, B, C, D, E) KE(A) KE(B) KE(C) KE(D) KE(E)
#define KE3(A, B, C) KE(A) KE(B) KE(C) #define KE3(A, B, C) KE(A) KE(B) KE(C)
static key_lookup_table sdl_lookup_table[] = key_lookup_table sdl_lookup_table[] =
{ {
KE(UNKNOWN) KE(UNKNOWN)
@ -332,7 +334,7 @@ static key_lookup_table sdl_lookup_table[] =
// lookup_sdl_code // lookup_sdl_code
//============================================================ //============================================================
static int lookup_sdl_code(const char *scode) int lookup_sdl_code(const char *scode)
{ {
int i = 0; int i = 0;
@ -352,8 +354,8 @@ static int lookup_sdl_code(const char *scode)
class sdl_device : public event_based_device<SDL_Event> class sdl_device : public event_based_device<SDL_Event>
{ {
public: public:
sdl_device(running_machine &machine, const char *name, const char *id, input_device_class devclass, input_module &module) sdl_device(running_machine &machine, std::string &&name, std::string &&id, input_device_class devclass, input_module &module) :
: event_based_device(machine, name, id, devclass, module) event_based_device(machine, std::move(name), std::move(id), devclass, module)
{ {
} }
@ -373,8 +375,8 @@ class sdl_keyboard_device : public sdl_device
public: public:
keyboard_state keyboard; keyboard_state keyboard;
sdl_keyboard_device(running_machine &machine, const char *name, const char *id, input_module &module) sdl_keyboard_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module) :
: sdl_device(machine, name, id, DEVICE_CLASS_KEYBOARD, module), sdl_device(machine, std::move(name), std::move(id), DEVICE_CLASS_KEYBOARD, module),
keyboard({{0}}) keyboard({{0}})
{ {
#ifdef __APPLE__ #ifdef __APPLE__
@ -483,8 +485,8 @@ private:
public: public:
mouse_state mouse; mouse_state mouse;
sdl_mouse_device(running_machine &machine, const char *name, const char *id, input_module &module) sdl_mouse_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module) :
: sdl_device(machine, name, id, DEVICE_CLASS_MOUSE, module), sdl_device(machine, std::move(name), std::move(id), DEVICE_CLASS_MOUSE, module),
last_x(0), last_x(0),
last_y(0), last_y(0),
mouse({0}) mouse({0})
@ -622,8 +624,8 @@ public:
sdl_joystick_state joystick; sdl_joystick_state joystick;
sdl_api_state sdl_state; sdl_api_state sdl_state;
sdl_joystick_device(running_machine &machine, const char *name, const char *id, input_module &module) sdl_joystick_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module) :
: sdl_device(machine, name, id, DEVICE_CLASS_JOYSTICK, module), sdl_device(machine, std::move(name), std::move(id), DEVICE_CLASS_JOYSTICK, module),
joystick({{0}}), joystick({{0}}),
sdl_state({ nullptr }) sdl_state({ nullptr })
{ {
@ -709,8 +711,8 @@ public:
class sdl_sixaxis_joystick_device : public sdl_joystick_device class sdl_sixaxis_joystick_device : public sdl_joystick_device
{ {
public: public:
sdl_sixaxis_joystick_device(running_machine &machine, const char *name, const char *id, input_module &module) sdl_sixaxis_joystick_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module) :
: sdl_joystick_device(machine, name, id, module) sdl_joystick_device(machine, std::move(name), std::move(id), module)
{ {
} }
@ -749,8 +751,7 @@ public:
class sdl_input_module : public input_module_base, public sdl_event_subscriber class sdl_input_module : public input_module_base, public sdl_event_subscriber
{ {
public: public:
sdl_input_module(const char *type) sdl_input_module(const char *type) : input_module_base(type, "sdl")
: input_module_base(type, "sdl")
{ {
} }
@ -799,8 +800,9 @@ class sdl_keyboard_module : public sdl_input_module
{ {
keyboard_trans_table * m_key_trans_table; keyboard_trans_table * m_key_trans_table;
public: public:
sdl_keyboard_module() sdl_keyboard_module() :
: sdl_input_module(OSD_KEYBOARDINPUT_PROVIDER), m_key_trans_table(nullptr) sdl_input_module(OSD_KEYBOARDINPUT_PROVIDER),
m_key_trans_table(nullptr)
{ {
} }
@ -816,8 +818,6 @@ public:
sdl_event_manager::instance().subscribe(event_types, std::size(event_types), this); sdl_event_manager::instance().subscribe(event_types, std::size(event_types), this);
sdl_keyboard_device *devinfo;
// Read our keymap and store a pointer to our table // Read our keymap and store a pointer to our table
m_key_trans_table = sdlinput_read_keymap(machine); m_key_trans_table = sdlinput_read_keymap(machine);
@ -826,7 +826,7 @@ public:
osd_printf_verbose("Keyboard: Start initialization\n"); osd_printf_verbose("Keyboard: Start initialization\n");
// SDL only has 1 keyboard add it now // SDL only has 1 keyboard add it now
devinfo = devicelist()->create_device<sdl_keyboard_device>(machine, "System keyboard", "System keyboard", *this); auto &devinfo = devicelist()->create_device<sdl_keyboard_device>(machine, "System keyboard", "System keyboard", *this);
// populate it // populate it
for (int keynum = 0; local_table[keynum].mame_key != ITEM_ID_INVALID; keynum++) for (int keynum = 0; local_table[keynum].mame_key != ITEM_ID_INVALID; keynum++)
@ -837,31 +837,26 @@ public:
char defname[20]; char defname[20];
snprintf(defname, sizeof(defname) - 1, "%s", local_table[keynum].ui_name); snprintf(defname, sizeof(defname) - 1, "%s", local_table[keynum].ui_name);
devinfo->device()->add_item(defname, itemid, generic_button_get_state<std::int32_t>, &devinfo->keyboard.state[local_table[keynum].sdl_scancode]); devinfo.device()->add_item(defname, itemid, generic_button_get_state<std::int32_t>, &devinfo.keyboard.state[local_table[keynum].sdl_scancode]);
} }
osd_printf_verbose("Keyboard: Registered %s\n", devinfo->name()); osd_printf_verbose("Keyboard: Registered %s\n", devinfo.name());
osd_printf_verbose("Keyboard: End initialization\n"); osd_printf_verbose("Keyboard: End initialization\n");
} }
private: private:
keyboard_trans_table* sdlinput_read_keymap(running_machine &machine) keyboard_trans_table *sdlinput_read_keymap(running_machine &machine)
{ {
char *keymap_filename;
FILE *keymap_file;
int line = 1;
int sdl2section = 0;
keyboard_trans_table &default_table = keyboard_trans_table::instance(); keyboard_trans_table &default_table = keyboard_trans_table::instance();
if (!machine.options().bool_value(SDLOPTION_KEYMAP)) if (!machine.options().bool_value(SDLOPTION_KEYMAP))
return &default_table; return &default_table;
keymap_filename = (char *)downcast<sdl_options &>(machine.options()).keymap_file(); const char *const keymap_filename = downcast<sdl_options &>(machine.options()).keymap_file();
osd_printf_verbose("Keymap: Start reading keymap_file %s\n", keymap_filename); osd_printf_verbose("Keymap: Start reading keymap_file %s\n", keymap_filename);
keymap_file = fopen(keymap_filename, "r"); FILE *const keymap_file = fopen(keymap_filename, "r");
if (keymap_file == nullptr) if (!keymap_file)
{ {
osd_printf_warning("Keymap: Unable to open keymap %s, using default\n", keymap_filename); osd_printf_warning("Keymap: Unable to open keymap %s, using default\n", keymap_filename);
return &default_table; return &default_table;
@ -877,6 +872,8 @@ private:
// Allocate the trans table to be associated with the machine so we don't have to free it // Allocate the trans table to be associated with the machine so we don't have to free it
m_custom_table = std::make_unique<keyboard_trans_table>(std::move(key_trans_entries), default_table.size()); m_custom_table = std::make_unique<keyboard_trans_table>(std::move(key_trans_entries), default_table.size());
int line = 1;
int sdl2section = 0;
while (!feof(keymap_file)) while (!feof(keymap_file))
{ {
char buf[256]; char buf[256];
@ -913,9 +910,11 @@ private:
osd_printf_verbose("Keymap: Mapped <%s> to <%s> with ui-text <%s>\n", sks, mks, kns); osd_printf_verbose("Keymap: Mapped <%s> to <%s> with ui-text <%s>\n", sks, mks, kns);
} }
else else
{
osd_printf_error("Keymap: Error on line %d - %s key not found: %s\n", line, (sk<0) ? "sdl" : "mame", buf); osd_printf_error("Keymap: Error on line %d - %s key not found: %s\n", line, (sk<0) ? "sdl" : "mame", buf);
} }
} }
}
line++; line++;
} }
fclose(keymap_file); fclose(keymap_file);
@ -935,8 +934,7 @@ private:
class sdl_mouse_module : public sdl_input_module class sdl_mouse_module : public sdl_input_module
{ {
public: public:
sdl_mouse_module() sdl_mouse_module() : sdl_input_module(OSD_MOUSEINPUT_PROVIDER)
: sdl_input_module(OSD_MOUSEINPUT_PROVIDER)
{ {
} }
@ -953,45 +951,42 @@ public:
sdl_event_manager::instance().subscribe(event_types, std::size(event_types), this); sdl_event_manager::instance().subscribe(event_types, std::size(event_types), this);
sdl_mouse_device *devinfo;
char defname[20];
int button;
osd_printf_verbose("Mouse: Start initialization\n"); osd_printf_verbose("Mouse: Start initialization\n");
// SDL currently only supports one mouse // SDL currently only supports one mouse
devinfo = devicelist()->create_device<sdl_mouse_device>(machine, "System mouse", "System mouse", *this); auto &devinfo = devicelist()->create_device<sdl_mouse_device>(machine, "System mouse", "System mouse", *this);
// add the axes // add the axes
devinfo->device()->add_item("X", ITEM_ID_XAXIS, generic_axis_get_state<std::int32_t>, &devinfo->mouse.lX); devinfo.device()->add_item("X", ITEM_ID_XAXIS, generic_axis_get_state<std::int32_t>, &devinfo.mouse.lX);
devinfo->device()->add_item("Y", ITEM_ID_YAXIS, generic_axis_get_state<std::int32_t>, &devinfo->mouse.lY); devinfo.device()->add_item("Y", ITEM_ID_YAXIS, generic_axis_get_state<std::int32_t>, &devinfo.mouse.lY);
for (button = 0; button < 4; button++) for (int button = 0; button < 4; button++)
{ {
input_item_id itemid = (input_item_id)(ITEM_ID_BUTTON1 + button); input_item_id itemid = (input_item_id)(ITEM_ID_BUTTON1 + button);
char defname[20];
snprintf(defname, sizeof(defname), "B%d", button + 1); snprintf(defname, sizeof(defname), "B%d", button + 1);
devinfo->device()->add_item(defname, itemid, generic_button_get_state<std::int32_t>, &devinfo->mouse.buttons[button]); devinfo.device()->add_item(defname, itemid, generic_button_get_state<std::int32_t>, &devinfo.mouse.buttons[button]);
} }
osd_printf_verbose("Mouse: Registered %s\n", devinfo->name()); osd_printf_verbose("Mouse: Registered %s\n", devinfo.name());
osd_printf_verbose("Mouse: End initialization\n"); osd_printf_verbose("Mouse: End initialization\n");
} }
}; };
static void devmap_register(device_map_t &devmap, int physical_idx, const std::string &name) void devmap_register(device_map_t &devmap, int physical_idx, const std::string &name)
{ {
// Attempt to find the entry by name // Attempt to find the entry by name
auto entry = std::find_if(std::begin(devmap.map), std::end(devmap.map), [&name](auto &item) auto entry = std::find_if(
{ std::begin(devmap.map),
return item.name == name && item.physical < 0; std::end(devmap.map),
}); [&name] (auto &item) { return (item.name == name) && (item.physical < 0); });
// If we didn't find it by name, find the first free slot // If we didn't find it by name, find the first free slot
if (entry == std::end(devmap.map)) if (entry == std::end(devmap.map))
{ {
entry = std::find_if(std::begin(devmap.map), std::end(devmap.map), [](auto &item) { return item.name.empty(); }); entry = std::find_if(std::begin(devmap.map), std::end(devmap.map), [] (auto &item) { return item.name.empty(); });
} }
if (entry != std::end(devmap.map)) if (entry != std::end(devmap.map))
@ -1015,8 +1010,11 @@ private:
bool m_initialized_haptic; bool m_initialized_haptic;
bool m_sixaxis_mode; bool m_sixaxis_mode;
public: public:
sdl_joystick_module() sdl_joystick_module() :
: sdl_input_module(OSD_JOYSTICKINPUT_PROVIDER), m_initialized_joystick(false), m_initialized_haptic(false), m_sixaxis_mode(false) sdl_input_module(OSD_JOYSTICKINPUT_PROVIDER),
m_initialized_joystick(false),
m_initialized_haptic(false),
m_sixaxis_mode(false)
{ {
} }
@ -1070,9 +1068,9 @@ public:
for (int stick = 0; stick < MAX_DEVMAP_ENTRIES; stick++) for (int stick = 0; stick < MAX_DEVMAP_ENTRIES; stick++)
{ {
sdl_joystick_device *devinfo = create_joystick_device(machine, &m_joy_map, stick, DEVICE_CLASS_JOYSTICK); sdl_joystick_device *const devinfo = create_joystick_device(machine, &m_joy_map, stick, DEVICE_CLASS_JOYSTICK);
if (devinfo == nullptr) if (!devinfo)
continue; continue;
physical_stick = m_joy_map.map[stick].physical; physical_stick = m_joy_map.map[stick].physical;
@ -1110,7 +1108,7 @@ public:
else else
itemid = ITEM_ID_OTHER_AXIS_ABSOLUTE; itemid = ITEM_ID_OTHER_AXIS_ABSOLUTE;
snprintf(tempname, sizeof(tempname), "A%d %s", axis, devinfo->name()); snprintf(tempname, sizeof(tempname), "A%d %s", axis, devinfo->name().c_str());
devinfo->device()->add_item(tempname, itemid, generic_axis_get_state<std::int32_t>, &devinfo->joystick.axes[axis]); devinfo->device()->add_item(tempname, itemid, generic_axis_get_state<std::int32_t>, &devinfo->joystick.axes[axis]);
} }
@ -1163,9 +1161,9 @@ public:
else else
itemid = ITEM_ID_OTHER_AXIS_RELATIVE; itemid = ITEM_ID_OTHER_AXIS_RELATIVE;
snprintf(tempname, sizeof(tempname), "R%d %s", ball * 2, devinfo->name()); snprintf(tempname, sizeof(tempname), "R%d %s", ball * 2, devinfo->name().c_str());
devinfo->device()->add_item(tempname, (input_item_id)itemid, generic_axis_get_state<std::int32_t>, &devinfo->joystick.balls[ball * 2]); devinfo->device()->add_item(tempname, (input_item_id)itemid, generic_axis_get_state<std::int32_t>, &devinfo->joystick.balls[ball * 2]);
snprintf(tempname, sizeof(tempname), "R%d %s", ball * 2 + 1, devinfo->name()); snprintf(tempname, sizeof(tempname), "R%d %s", ball * 2 + 1, devinfo->name().c_str());
devinfo->device()->add_item(tempname, (input_item_id)(itemid + 1), generic_axis_get_state<std::int32_t>, &devinfo->joystick.balls[ball * 2 + 1]); devinfo->device()->add_item(tempname, (input_item_id)(itemid + 1), generic_axis_get_state<std::int32_t>, &devinfo->joystick.balls[ball * 2 + 1]);
} }
} }
@ -1186,7 +1184,10 @@ public:
virtual void handle_event(SDL_Event &sdlevent) override virtual void handle_event(SDL_Event &sdlevent) override
{ {
// Figure out which joystick this event id destined for // Figure out which joystick this event id destined for
auto target_device = std::find_if(devicelist()->begin(), devicelist()->end(), [&sdlevent](auto &device) auto target_device = std::find_if(
devicelist()->begin(),
devicelist()->end(),
[&sdlevent] (auto &device)
{ {
std::unique_ptr<device_info> &ptr = device; std::unique_ptr<device_info> &ptr = device;
return downcast<sdl_joystick_device*>(ptr.get())->sdl_state.joystick_id == sdlevent.jdevice.which; return downcast<sdl_joystick_device*>(ptr.get())->sdl_state.joystick_id == sdlevent.jdevice.which;
@ -1200,12 +1201,12 @@ public:
} }
private: private:
sdl_joystick_device* create_joystick_device(running_machine &machine, device_map_t *devmap, int index, input_device_class devclass) sdl_joystick_device *create_joystick_device(running_machine &machine, device_map_t *devmap, int index, input_device_class devclass)
{ {
char tempname[20]; char tempname[20];
char guid_str[256]; char guid_str[256];
SDL_JoystickGUID guid = SDL_JoystickGetDeviceGUID(m_joy_map.map[index].physical); SDL_JoystickGUID guid = SDL_JoystickGetDeviceGUID(m_joy_map.map[index].physical);
SDL_JoystickGetGUIDString(guid, guid_str, sizeof(guid_str)-1); SDL_JoystickGetGUIDString(guid, guid_str, sizeof(guid_str) - 1);
if (devmap->map[index].name.empty()) if (devmap->map[index].name.empty())
{ {
@ -1222,16 +1223,20 @@ private:
} }
return m_sixaxis_mode return m_sixaxis_mode
? devicelist()->create_device<sdl_sixaxis_joystick_device>(machine, devmap->map[index].name.c_str(), guid_str, *this) ? &devicelist()->create_device<sdl_sixaxis_joystick_device>(machine, std::string(devmap->map[index].name), guid_str, *this)
: devicelist()->create_device<sdl_joystick_device>(machine, devmap->map[index].name.c_str(), guid_str, *this); : &devicelist()->create_device<sdl_joystick_device>(machine, std::string(devmap->map[index].name), guid_str, *this);
} }
}; };
#else } // anonymous namespace
#else // defined(SDLMAME_SDL2)
MODULE_NOT_SUPPORTED(sdl_keyboard_module, OSD_KEYBOARDINPUT_PROVIDER, "sdl") MODULE_NOT_SUPPORTED(sdl_keyboard_module, OSD_KEYBOARDINPUT_PROVIDER, "sdl")
MODULE_NOT_SUPPORTED(sdl_mouse_module, OSD_MOUSEINPUT_PROVIDER, "sdl") MODULE_NOT_SUPPORTED(sdl_mouse_module, OSD_MOUSEINPUT_PROVIDER, "sdl")
MODULE_NOT_SUPPORTED(sdl_joystick_module, OSD_JOYSTICKINPUT_PROVIDER, "sdl") MODULE_NOT_SUPPORTED(sdl_joystick_module, OSD_JOYSTICKINPUT_PROVIDER, "sdl")
#endif
#endif // defined(SDLMAME_SDL2)
MODULE_DEFINITION(KEYBOARDINPUT_SDL, sdl_keyboard_module) MODULE_DEFINITION(KEYBOARDINPUT_SDL, sdl_keyboard_module)
MODULE_DEFINITION(MOUSEINPUT_SDL, sdl_mouse_module) MODULE_DEFINITION(MOUSEINPUT_SDL, sdl_mouse_module)

View File

@ -26,6 +26,9 @@
#include "input_common.h" #include "input_common.h"
#include "input_windows.h" #include "input_windows.h"
namespace {
#define UWP_BUTTON_COUNT 32 #define UWP_BUTTON_COUNT 32
using namespace concurrency; using namespace concurrency;
@ -54,10 +57,10 @@ private:
input_device *m_inputdevice; input_device *m_inputdevice;
internal: internal:
UwpInputDevice(running_machine &machine, const char *name, const char *id, input_device_class deviceclass, input_module &module) UwpInputDevice(running_machine &machine, std::string &&name, std::string &&id, input_device_class deviceclass, input_module &module) :
: m_machine(machine), m_machine(machine),
m_name(name), m_name(std::move(name)),
m_id(id), m_id(std::move(id)),
m_devclass(deviceclass), m_devclass(deviceclass),
m_module(module), m_module(module),
m_inputdevice(nullptr) m_inputdevice(nullptr)
@ -115,8 +118,8 @@ private:
UwpInputDevice ^m_wrapped_device; UwpInputDevice ^m_wrapped_device;
public: public:
uwp_input_device(UwpInputDevice ^device) uwp_input_device(UwpInputDevice ^device) :
: device_info(device->Machine, device->Name.c_str(), device->Id.c_str(), device->DeviceClass, device->Module), device_info(device->Machine, std::string(device->Name), std::string(device->Id), device->DeviceClass, device->Module),
m_wrapped_device(device) m_wrapped_device(device)
{ {
} }
@ -148,9 +151,9 @@ private:
uwp_input_module *m_module; uwp_input_module *m_module;
internal: internal:
UwpInputModule(const char *type, const char *name) UwpInputModule(std::string &&type, std::string &&name) :
: m_type(type), m_type(std::move(type)),
m_name(name), m_name(std::move(name)),
m_module(nullptr) m_module(nullptr)
{ {
} }
@ -187,8 +190,8 @@ private:
UwpInputModule^ m_refmodule; UwpInputModule^ m_refmodule;
public: public:
uwp_input_module(UwpInputModule^ refmodule) uwp_input_module(UwpInputModule^ refmodule) :
: wininput_module(refmodule->Type.c_str(), refmodule->Name.c_str()), wininput_module(refmodule->Type.c_str(), refmodule->Name.c_str()),
m_refmodule(refmodule) m_refmodule(refmodule)
{ {
refmodule->NativeModule = this; refmodule->NativeModule = this;
@ -216,8 +219,8 @@ private:
std::mutex m_state_lock; std::mutex m_state_lock;
internal: internal:
UwpKeyboardDevice(Platform::Agile<CoreWindow> coreWindow, running_machine& machine, char *name, const char *id, input_module &module) UwpKeyboardDevice(Platform::Agile<CoreWindow> coreWindow, running_machine& machine, std::string &&name, std::string &&id, input_module &module) :
: UwpInputDevice(machine, name, id, DEVICE_CLASS_KEYBOARD, module), UwpInputDevice(machine, std::move(name), std::move(id), DEVICE_CLASS_KEYBOARD, module),
keyboard({{0}}), keyboard({{0}}),
m_coreWindow(coreWindow) m_coreWindow(coreWindow)
{ {
@ -244,7 +247,7 @@ internal:
const char *keyname = table.ui_label_for_mame_key(itemid); const char *keyname = table.ui_label_for_mame_key(itemid);
char temp[256]; char temp[256];
if (keyname == nullptr) if (!keyname)
{ {
snprintf(temp, std::size(temp), "Scan%03d", keynum); snprintf(temp, std::size(temp), "Scan%03d", keynum);
keyname = temp; keyname = temp;
@ -301,8 +304,7 @@ private:
running_machine *m_machine; running_machine *m_machine;
internal: internal:
UwpKeyboardModule() UwpKeyboardModule() : UwpInputModule(OSD_KEYBOARDINPUT_PROVIDER, "uwp")
: UwpInputModule(OSD_KEYBOARDINPUT_PROVIDER, "uwp")
{ {
} }
@ -316,10 +318,10 @@ internal:
// Allocate the wrapper and add it to the list // Allocate the wrapper and add it to the list
auto created_devinfo = std::make_unique<uwp_input_device>(refdevice); auto created_devinfo = std::make_unique<uwp_input_device>(refdevice);
uwp_input_device *devinfo = NativeModule->devicelist()->add_device<uwp_input_device>(machine, std::move(created_devinfo)); uwp_input_device &devinfo = NativeModule->devicelist()->add_device<uwp_input_device>(machine, std::move(created_devinfo));
// Give the UWP implementation a handle to the input_device // Give the UWP implementation a handle to the input_device
refdevice->InputDevice = devinfo->device(); refdevice->InputDevice = devinfo.device();
// Configure the device // Configure the device
refdevice->Configure(); refdevice->Configure();
@ -577,8 +579,6 @@ internal:
int padindex = 0; int padindex = 0;
std::for_each(begin(pads), end(pads), [&](Gamepad^ pad) std::for_each(begin(pads), end(pads), [&](Gamepad^ pad)
{ {
uwp_input_device *devinfo;
std::ostringstream namestream; std::ostringstream namestream;
namestream << "UWP Gamepad " << (padindex + 1); namestream << "UWP Gamepad " << (padindex + 1);
@ -589,7 +589,7 @@ internal:
// Allocate the wrapper and add it to the list // Allocate the wrapper and add it to the list
auto created_devinfo = std::make_unique<uwp_input_device>(refdevice); auto created_devinfo = std::make_unique<uwp_input_device>(refdevice);
devinfo = NativeModule->devicelist()->add_device<uwp_input_device>(machine, std::move(created_devinfo)); auto &devinfo = NativeModule->devicelist()->add_device<uwp_input_device>(machine, std::move(created_devinfo));
// Give the UWP implementation a handle to the input_device // Give the UWP implementation a handle to the input_device
refdevice->InputDevice = devinfo->device(); refdevice->InputDevice = devinfo->device();
@ -634,16 +634,19 @@ private:
class uwp_joystick_module : public uwp_input_module class uwp_joystick_module : public uwp_input_module
{ {
public: public:
uwp_joystick_module() uwp_joystick_module() : uwp_input_module(ref new UwpJoystickModule())
: uwp_input_module(ref new UwpJoystickModule())
{ {
} }
}; };
#else } // anonymous namespace
#else // defined(OSD_UWP)
MODULE_NOT_SUPPORTED(uwp_keyboard_module, OSD_KEYBOARDINPUT_PROVIDER, "uwp") MODULE_NOT_SUPPORTED(uwp_keyboard_module, OSD_KEYBOARDINPUT_PROVIDER, "uwp")
MODULE_NOT_SUPPORTED(uwp_joystick_module, OSD_JOYSTICKINPUT_PROVIDER, "uwp") MODULE_NOT_SUPPORTED(uwp_joystick_module, OSD_JOYSTICKINPUT_PROVIDER, "uwp")
#endif
#endif // defined(OSD_UWP)
MODULE_DEFINITION(KEYBOARDINPUT_UWP, uwp_keyboard_module) MODULE_DEFINITION(KEYBOARDINPUT_UWP, uwp_keyboard_module)
MODULE_DEFINITION(JOYSTICKINPUT_UWP, uwp_joystick_module) MODULE_DEFINITION(JOYSTICKINPUT_UWP, uwp_joystick_module)

View File

@ -27,6 +27,8 @@
#include "input_common.h" #include "input_common.h"
#include "input_windows.h" #include "input_windows.h"
namespace {
//============================================================ //============================================================
// win32_keyboard_device // win32_keyboard_device
//============================================================ //============================================================
@ -37,8 +39,8 @@ class win32_keyboard_device : public event_based_device<KeyPressEventArgs>
public: public:
keyboard_state keyboard; keyboard_state keyboard;
win32_keyboard_device(running_machine& machine, const char *name, const char *id, input_module &module) win32_keyboard_device(running_machine& machine, std::string &&name, std::string &&id, input_module &module)
: event_based_device(machine, name, id, DEVICE_CLASS_KEYBOARD, module), : event_based_device(machine, std::move(name), std::move(id), DEVICE_CLASS_KEYBOARD, module),
keyboard({{0}}) keyboard({{0}})
{ {
} }
@ -72,7 +74,7 @@ public:
virtual void input_init(running_machine &machine) override virtual void input_init(running_machine &machine) override
{ {
// Add a single win32 keyboard device that we'll monitor using Win32 // Add a single win32 keyboard device that we'll monitor using Win32
auto *devinfo = devicelist()->create_device<win32_keyboard_device>(machine, "Win32 Keyboard 1", "Win32 Keyboard 1", *this); auto &devinfo = devicelist()->create_device<win32_keyboard_device>(machine, "Win32 Keyboard 1", "Win32 Keyboard 1", *this);
keyboard_trans_table &table = keyboard_trans_table::instance(); keyboard_trans_table &table = keyboard_trans_table::instance();
@ -88,7 +90,7 @@ public:
std::string name = osd::text::from_tstring(keyname); std::string name = osd::text::from_tstring(keyname);
// add the item to the device // add the item to the device
devinfo->device()->add_item(name.c_str(), itemid, generic_button_get_state<std::uint8_t>, &devinfo->keyboard.state[keynum]); devinfo.device()->add_item(name, itemid, generic_button_get_state<std::uint8_t>, &devinfo.keyboard.state[keynum]);
} }
} }
@ -134,8 +136,8 @@ public:
mouse_state mouse; mouse_state mouse;
win32_mouse_state win32_mouse; win32_mouse_state win32_mouse;
win32_mouse_device(running_machine& machine, const char *name, const char *id, input_module &module) win32_mouse_device(running_machine& machine, std::string &&name, std::string &&id, input_module &module)
: event_based_device(machine, name, id, DEVICE_CLASS_MOUSE, module), : event_based_device(machine, std::move(name), std::move(id), DEVICE_CLASS_MOUSE, module),
mouse({0}), mouse({0}),
win32_mouse({{0}}) win32_mouse({{0}})
{ {
@ -200,35 +202,30 @@ public:
virtual void input_init(running_machine &machine) override virtual void input_init(running_machine &machine) override
{ {
win32_mouse_device *devinfo;
int axisnum, butnum;
if (!input_enabled() || !mouse_enabled()) if (!input_enabled() || !mouse_enabled())
return; return;
// allocate a device // allocate a device
devinfo = devicelist()->create_device<win32_mouse_device>(machine, "Win32 Mouse 1", "Win32 Mouse 1", *this); auto &devinfo = devicelist()->create_device<win32_mouse_device>(machine, "Win32 Mouse 1", "Win32 Mouse 1", *this);
if (devinfo == nullptr)
return;
// populate the axes // populate the axes
for (axisnum = 0; axisnum < 2; axisnum++) for (int axisnum = 0; axisnum < 2; axisnum++)
{ {
devinfo->device()->add_item( devinfo.device()->add_item(
default_axis_name[axisnum], default_axis_name[axisnum],
static_cast<input_item_id>(ITEM_ID_XAXIS + axisnum), static_cast<input_item_id>(ITEM_ID_XAXIS + axisnum),
generic_axis_get_state<LONG>, generic_axis_get_state<LONG>,
&devinfo->mouse.lX + axisnum); &devinfo.mouse.lX + axisnum);
} }
// populate the buttons // populate the buttons
for (butnum = 0; butnum < 2; butnum++) for (int butnum = 0; butnum < 2; butnum++)
{ {
devinfo->device()->add_item( devinfo.device()->add_item(
default_button_name(butnum), default_button_name(butnum),
static_cast<input_item_id>(ITEM_ID_BUTTON1 + butnum), static_cast<input_item_id>(ITEM_ID_BUTTON1 + butnum),
generic_button_get_state<BYTE>, generic_button_get_state<BYTE>,
&devinfo->mouse.rgbButtons[butnum]); &devinfo.mouse.rgbButtons[butnum]);
} }
} }
@ -262,8 +259,8 @@ private:
public: public:
mouse_state mouse; mouse_state mouse;
win32_lightgun_device(running_machine& machine, const char *name, const char *id, input_module &module) win32_lightgun_device(running_machine& machine, std::string &&name, std::string &&id, input_module &module)
: event_based_device(machine, name, id, DEVICE_CLASS_LIGHTGUN, module), : event_based_device(machine, std::move(name), std::move(id), DEVICE_CLASS_LIGHTGUN, module),
m_lightgun_shared_axis_mode(FALSE), m_lightgun_shared_axis_mode(FALSE),
m_gun_index(0), m_gun_index(0),
mouse({0}) mouse({0})
@ -392,32 +389,28 @@ public:
for (int gunnum = 0; gunnum < max_guns; gunnum++) for (int gunnum = 0; gunnum < max_guns; gunnum++)
{ {
static const char *const gun_names[] = { "Win32 Gun 1", "Win32 Gun 2" }; static const char *const gun_names[] = { "Win32 Gun 1", "Win32 Gun 2" };
win32_lightgun_device *devinfo;
int axisnum, butnum;
// allocate a device // allocate a device
devinfo = devicelist()->create_device<win32_lightgun_device>(machine, gun_names[gunnum], gun_names[gunnum], *this); auto &devinfo = devicelist()->create_device<win32_lightgun_device>(machine, gun_names[gunnum], gun_names[gunnum], *this);
if (devinfo == nullptr)
break;
// populate the axes // populate the axes
for (axisnum = 0; axisnum < 2; axisnum++) for (int axisnum = 0; axisnum < 2; axisnum++)
{ {
devinfo->device()->add_item( devinfo.device()->add_item(
default_axis_name[axisnum], default_axis_name[axisnum],
static_cast<input_item_id>(ITEM_ID_XAXIS + axisnum), static_cast<input_item_id>(ITEM_ID_XAXIS + axisnum),
generic_axis_get_state<LONG>, generic_axis_get_state<LONG>,
&devinfo->mouse.lX + axisnum); &devinfo.mouse.lX + axisnum);
} }
// populate the buttons // populate the buttons
for (butnum = 0; butnum < 2; butnum++) for (int butnum = 0; butnum < 2; butnum++)
{ {
devinfo->device()->add_item( devinfo.device()->add_item(
default_button_name(butnum), default_button_name(butnum),
static_cast<input_item_id>(ITEM_ID_BUTTON1 + butnum), static_cast<input_item_id>(ITEM_ID_BUTTON1 + butnum),
generic_button_get_state<BYTE>, generic_button_get_state<BYTE>,
&devinfo->mouse.rgbButtons[butnum]); &devinfo.mouse.rgbButtons[butnum]);
} }
} }
} }
@ -439,11 +432,15 @@ public:
} }
}; };
#else } // anonymous namespace
#else // defined(OSD_WINDOWS)
MODULE_NOT_SUPPORTED(keyboard_input_win32, OSD_KEYBOARDINPUT_PROVIDER, "win32") MODULE_NOT_SUPPORTED(keyboard_input_win32, OSD_KEYBOARDINPUT_PROVIDER, "win32")
MODULE_NOT_SUPPORTED(mouse_input_win32, OSD_MOUSEINPUT_PROVIDER, "win32") MODULE_NOT_SUPPORTED(mouse_input_win32, OSD_MOUSEINPUT_PROVIDER, "win32")
MODULE_NOT_SUPPORTED(lightgun_input_win32, OSD_LIGHTGUNINPUT_PROVIDER, "win32") MODULE_NOT_SUPPORTED(lightgun_input_win32, OSD_LIGHTGUNINPUT_PROVIDER, "win32")
#endif
#endif // defined(OSD_WINDOWS)
MODULE_DEFINITION(KEYBOARDINPUT_WIN32, keyboard_input_win32) MODULE_DEFINITION(KEYBOARDINPUT_WIN32, keyboard_input_win32)
MODULE_DEFINITION(MOUSEINPUT_WIN32, mouse_input_win32) MODULE_DEFINITION(MOUSEINPUT_WIN32, mouse_input_win32)

View File

@ -167,4 +167,4 @@ void windows_osd_interface::customize_input_type_list(std::vector<input_type_ent
} }
} }
#endif #endif // defined(OSD_WINDOWS) || defined(OSD_UWP)

View File

@ -5,9 +5,10 @@
// input_windows.h - Common code used by Windows input modules // input_windows.h - Common code used by Windows input modules
// //
//============================================================ //============================================================
#ifndef MAME_OSD_INPUT_INPUT_WINDOWS_H
#define MAME_OSD_INPUT_INPUT_WINDOWS_H
#ifndef INPUT_WIN_H_ #pragma once
#define INPUT_WIN_H_
// standard windows headers // standard windows headers
#include <windows.h> #include <windows.h>
@ -80,4 +81,4 @@ protected:
} }
}; };
#endif #endif // MAME_OSD_INPUT_INPUT_WINDOWS_H

View File

@ -37,6 +37,8 @@
#include "input_xinput.h" #include "input_xinput.h"
#include "input_dinput.h" #include "input_dinput.h"
namespace {
using namespace Microsoft::WRL; using namespace Microsoft::WRL;
template<class TCom> template<class TCom>
@ -46,8 +48,7 @@ private:
std::vector<TCom*> m_entries; std::vector<TCom*> m_entries;
public: public:
ComArray(size_t capacity) ComArray(size_t capacity) : m_entries(capacity, nullptr)
: m_entries(capacity, nullptr)
{ {
} }
@ -76,12 +77,12 @@ public:
void Release() void Release()
{ {
for (int i = 0; i < m_entries.size(); i++) for (auto &entry : m_entries)
{ {
if (m_entries[i] != nullptr) if (entry != nullptr)
{ {
m_entries[i]->Release(); entry->Release();
m_entries[i] = nullptr; entry = nullptr;
} }
} }
} }
@ -91,7 +92,7 @@ struct bstr_deleter
{ {
void operator () (BSTR bstr) const void operator () (BSTR bstr) const
{ {
if (bstr != nullptr) if (bstr)
SysFreeString(bstr); SysFreeString(bstr);
} }
}; };
@ -146,8 +147,8 @@ private:
bool m_xinput_detect_failed; bool m_xinput_detect_failed;
public: public:
winhybrid_joystick_module() winhybrid_joystick_module() :
: wininput_module(OSD_JOYSTICKINPUT_PROVIDER, "winhybrid"), wininput_module(OSD_JOYSTICKINPUT_PROVIDER, "winhybrid"),
m_xinput_helper(nullptr), m_xinput_helper(nullptr),
m_dinput_helper(nullptr), m_dinput_helper(nullptr),
m_xinput_detect_failed(false) m_xinput_detect_failed(false)
@ -232,13 +233,13 @@ protected:
if (result != 0) if (result != 0)
{ {
m_xinput_detect_failed = true; m_xinput_detect_failed = true;
osd_printf_warning("XInput device detection failed. XInput won't be used. Error: 0x%X\n", static_cast<unsigned int>(result)); osd_printf_warning("XInput device detection failed. XInput won't be used. Error: 0x%X\n", uint32_t(result));
} }
// Enumerate all the directinput joysticks and add them if they aren't xinput compatible // Enumerate all the directinput joysticks and add them if they aren't xinput compatible
result = m_dinput_helper->enum_attached_devices(DI8DEVCLASS_GAMECTRL, this, &machine); result = m_dinput_helper->enum_attached_devices(DI8DEVCLASS_GAMECTRL, this, &machine);
if (result != DI_OK) if (result != DI_OK)
fatalerror("DirectInput: Unable to enumerate keyboards (result=%08X)\n", static_cast<uint32_t>(result)); fatalerror("DirectInput: Unable to enumerate game controllers (result=%08X)\n", uint32_t(result));
xinput_joystick_device *devinfo; xinput_joystick_device *devinfo;
@ -254,7 +255,7 @@ protected:
{ {
// allocate and link in a new device // allocate and link in a new device
devinfo = m_xinput_helper->create_xinput_device(machine, i, *this); devinfo = m_xinput_helper->create_xinput_device(machine, i, *this);
if (devinfo == nullptr) if (!devinfo)
continue; continue;
// Configure each gamepad to add buttons and Axes, etc. // Configure each gamepad to add buttons and Axes, etc.
@ -269,7 +270,7 @@ private:
{ {
int status = 0; int status = 0;
if (m_xinput_helper == nullptr) if (!m_xinput_helper)
{ {
m_xinput_helper = std::make_shared<xinput_api_helper>(); m_xinput_helper = std::make_shared<xinput_api_helper>();
status = m_xinput_helper->initialize(); status = m_xinput_helper->initialize();
@ -280,9 +281,9 @@ private:
} }
} }
if (m_dinput_helper == nullptr) if (!m_dinput_helper)
{ {
m_dinput_helper = std::make_unique<dinput_api_helper>(DIRECTINPUT_VERSION); m_dinput_helper = std::make_unique<dinput_api_helper>();
status = m_dinput_helper->initialize(); status = m_dinput_helper->initialize();
if (status != DI_OK) if (status != DI_OK)
{ {
@ -441,8 +442,12 @@ private:
} }
}; };
#else } // anonymous namespace
#else // defined(OSD_WINDOWS)
MODULE_NOT_SUPPORTED(winhybrid_joystick_module, OSD_JOYSTICKINPUT_PROVIDER, "winhybrid") MODULE_NOT_SUPPORTED(winhybrid_joystick_module, OSD_JOYSTICKINPUT_PROVIDER, "winhybrid")
#endif
#endif // defined(OSD_WINDOWS)
MODULE_DEFINITION(JOYSTICKINPUT_WINHYBRID, winhybrid_joystick_module) MODULE_DEFINITION(JOYSTICKINPUT_WINHYBRID, winhybrid_joystick_module)

View File

@ -38,6 +38,9 @@
#include "../../sdl/osdsdl.h" #include "../../sdl/osdsdl.h"
#include "input_sdlcommon.h" #include "input_sdlcommon.h"
namespace {
#define MAX_DEVMAP_ENTRIES 16 #define MAX_DEVMAP_ENTRIES 16
#define INVALID_EVENT_TYPE -1 #define INVALID_EVENT_TYPE -1
@ -71,7 +74,7 @@ struct x11_api_state
#define XI_DBG(format, ...) osd_printf_verbose(format, __VA_ARGS__) #define XI_DBG(format, ...) osd_printf_verbose(format, __VA_ARGS__)
#define print_motion_event(motion) print_motion_event_impl(motion) #define print_motion_event(motion) print_motion_event_impl(motion)
static inline void print_motion_event_impl(XDeviceMotionEvent *motion) inline void print_motion_event_impl(XDeviceMotionEvent *motion)
{ {
/* /*
* print a lot of debug informations of the motion event(s). * print a lot of debug informations of the motion event(s).
@ -185,7 +188,7 @@ find_device_info(Display *display,
} }
//Copypasted from xinfo //Copypasted from xinfo
static int int
register_events( register_events(
Display *dpy, Display *dpy,
XDeviceInfo *info, XDeviceInfo *info,
@ -356,8 +359,8 @@ class x11_input_device : public event_based_device<XEvent>
public: public:
x11_api_state x11_state; x11_api_state x11_state;
x11_input_device(running_machine &machine, const char *name, const char *id, input_device_class devclass, input_module &module) x11_input_device(running_machine &machine, std::string &&name, std::string &&id, input_device_class devclass, input_module &module) :
: event_based_device(machine, name, id, devclass, module), event_based_device(machine, std::move(name), std::move(id), devclass, module),
x11_state({0}) x11_state({0})
{ {
} }
@ -372,8 +375,8 @@ class x11_lightgun_device : public x11_input_device
public: public:
lightgun_state lightgun; lightgun_state lightgun;
x11_lightgun_device(running_machine &machine, const char *name, const char *id, input_module &module) x11_lightgun_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module) :
: x11_input_device(machine, name, id, DEVICE_CLASS_LIGHTGUN, module), x11_input_device(machine, std::move(name), std::move(id), DEVICE_CLASS_LIGHTGUN, module),
lightgun({0}) lightgun({0})
{ {
} }
@ -455,8 +458,8 @@ private:
device_map_t m_lightgun_map; device_map_t m_lightgun_map;
Display * m_display; Display * m_display;
public: public:
x11_lightgun_module() x11_lightgun_module() :
: input_module_base(OSD_LIGHTGUNINPUT_PROVIDER, "x11"), input_module_base(OSD_LIGHTGUNINPUT_PROVIDER, "x11"),
m_display(nullptr) m_display(nullptr)
{ {
} }
@ -464,7 +467,7 @@ public:
virtual bool probe() override virtual bool probe() override
{ {
// If there is no X server, X11 lightguns cannot be supported // If there is no X server, X11 lightguns cannot be supported
if (XOpenDisplay(nullptr) == nullptr) if (!XOpenDisplay(nullptr))
{ {
return false; return false;
} }
@ -474,8 +477,6 @@ public:
void input_init(running_machine &machine) override void input_init(running_machine &machine) override
{ {
int index;
osd_printf_verbose("Lightgun: Begin initialization\n"); osd_printf_verbose("Lightgun: Begin initialization\n");
devmap_init(machine, &m_lightgun_map, SDLOPTION_LIGHTGUNINDEX, 8, "Lightgun mapping"); devmap_init(machine, &m_lightgun_map, SDLOPTION_LIGHTGUNINDEX, 8, "Lightgun mapping");
@ -487,7 +488,7 @@ public:
assert(m_display != nullptr); assert(m_display != nullptr);
// Loop through all 8 possible devices // Loop through all 8 possible devices
for (index = 0; index < 8; index++) for (int index = 0; index < 8; index++)
{ {
XDeviceInfo *info; XDeviceInfo *info;
@ -495,19 +496,18 @@ public:
if (m_lightgun_map.map[index].name.length() == 0) if (m_lightgun_map.map[index].name.length() == 0)
continue; continue;
x11_lightgun_device *devinfo;
std::string const &name = m_lightgun_map.map[index].name; std::string const &name = m_lightgun_map.map[index].name;
char defname[512]; char defname[512];
// Register and add the device // Register and add the device
devinfo = create_lightgun_device(machine, index); auto *devinfo = create_lightgun_device(machine, index);
osd_printf_verbose("%i: %s\n", index, name); osd_printf_verbose("%i: %s\n", index, name);
// Find the device info associated with the name // Find the device info associated with the name
info = find_device_info(m_display, name.c_str(), 0); info = find_device_info(m_display, name.c_str(), 0);
// If we couldn't find the device, skip // If we couldn't find the device, skip
if (info == nullptr) if (!info)
{ {
osd_printf_verbose("Can't find device %s!\n", name); osd_printf_verbose("Can't find device %s!\n", name);
continue; continue;
@ -517,17 +517,17 @@ public:
if (info->num_classes > 0) if (info->num_classes > 0)
{ {
// Add the lightgun buttons based on what we read // Add the lightgun buttons based on what we read
add_lightgun_buttons(static_cast<XAnyClassPtr>(info->inputclassinfo), info->num_classes, devinfo); add_lightgun_buttons(static_cast<XAnyClassPtr>(info->inputclassinfo), info->num_classes, *devinfo);
// Also, set the axix min/max ranges if we got them // Also, set the axix min/max ranges if we got them
set_lightgun_axis_props(static_cast<XAnyClassPtr>(info->inputclassinfo), info->num_classes, devinfo); set_lightgun_axis_props(static_cast<XAnyClassPtr>(info->inputclassinfo), info->num_classes, *devinfo);
} }
// Add X and Y axis // Add X and Y axis
sprintf(defname, "X %s", devinfo->name()); sprintf(defname, "X %s", devinfo->name().c_str());
devinfo->device()->add_item(defname, ITEM_ID_XAXIS, generic_axis_get_state<std::int32_t>, &devinfo->lightgun.lX); devinfo->device()->add_item(defname, ITEM_ID_XAXIS, generic_axis_get_state<std::int32_t>, &devinfo->lightgun.lX);
sprintf(defname, "Y %s", devinfo->name()); sprintf(defname, "Y %s", devinfo->name().c_str());
devinfo->device()->add_item(defname, ITEM_ID_YAXIS, generic_axis_get_state<std::int32_t>, &devinfo->lightgun.lY); devinfo->device()->add_item(defname, ITEM_ID_YAXIS, generic_axis_get_state<std::int32_t>, &devinfo->lightgun.lY);
// Save the device id // Save the device id
@ -596,24 +596,26 @@ public:
} }
private: private:
x11_lightgun_device* create_lightgun_device(running_machine &machine, int index) x11_lightgun_device *create_lightgun_device(running_machine &machine, int index)
{ {
char tempname[20];
if (m_lightgun_map.map[index].name.length() == 0) if (m_lightgun_map.map[index].name.length() == 0)
{ {
if (m_lightgun_map.initialized) if (m_lightgun_map.initialized)
{ {
char tempname[20];
snprintf(tempname, std::size(tempname), "NC%d", index); snprintf(tempname, std::size(tempname), "NC%d", index);
return devicelist()->create_device<x11_lightgun_device>(machine, tempname, tempname, *this); return &devicelist()->create_device<x11_lightgun_device>(machine, tempname, tempname, *this);
} else }
else
{
return nullptr; return nullptr;
} }
return devicelist()->create_device<x11_lightgun_device>(machine, m_lightgun_map.map[index].name.c_str(), m_lightgun_map.map[index].name.c_str(), *this);
} }
void add_lightgun_buttons(XAnyClassPtr first_info_class, int num_classes, x11_lightgun_device *devinfo) const return &devicelist()->create_device<x11_lightgun_device>(machine, std::string(m_lightgun_map.map[index].name), std::string(m_lightgun_map.map[index].name), *this);
}
void add_lightgun_buttons(XAnyClassPtr first_info_class, int num_classes, x11_lightgun_device &devinfo) const
{ {
XAnyClassPtr any = first_info_class; XAnyClassPtr any = first_info_class;
@ -626,7 +628,7 @@ private:
for (int button = 0; button < b->num_buttons; button++) for (int button = 0; button < b->num_buttons; button++)
{ {
input_item_id itemid = static_cast<input_item_id>(ITEM_ID_BUTTON1 + button); input_item_id itemid = static_cast<input_item_id>(ITEM_ID_BUTTON1 + button);
devinfo->device()->add_item(default_button_name(button), itemid, generic_button_get_state<std::int32_t>, &devinfo->lightgun.buttons[button]); devinfo.device()->add_item(default_button_name(button), itemid, generic_button_get_state<std::int32_t>, &devinfo.lightgun.buttons[button]);
} }
break; break;
} }
@ -635,7 +637,7 @@ private:
} }
} }
void set_lightgun_axis_props(XAnyClassPtr first_info_class, int num_classes, x11_lightgun_device *devinfo) const void set_lightgun_axis_props(XAnyClassPtr first_info_class, int num_classes, x11_lightgun_device &devinfo) const
{ {
XAnyClassPtr any = first_info_class; XAnyClassPtr any = first_info_class;
@ -651,15 +653,15 @@ private:
if (j == 0) if (j == 0)
{ {
XI_DBG("Set minx=%d, maxx=%d\n", axis_info->min_value, axis_info->max_value); XI_DBG("Set minx=%d, maxx=%d\n", axis_info->min_value, axis_info->max_value);
devinfo->x11_state.maxx = axis_info->max_value; devinfo.x11_state.maxx = axis_info->max_value;
devinfo->x11_state.minx = axis_info->min_value; devinfo.x11_state.minx = axis_info->min_value;
} }
if (j == 1) if (j == 1)
{ {
XI_DBG("Set miny=%d, maxy=%d\n", axis_info->min_value, axis_info->max_value); XI_DBG("Set miny=%d, maxy=%d\n", axis_info->min_value, axis_info->max_value);
devinfo->x11_state.maxy = axis_info->max_value; devinfo.x11_state.maxy = axis_info->max_value;
devinfo->x11_state.miny = axis_info->min_value; devinfo.x11_state.miny = axis_info->min_value;
} }
} }
break; break;
@ -670,8 +672,12 @@ private:
} }
}; };
#else } // anonymous namespace
#else // defined(SDLMAME_SDL2) && !defined(SDLMAME_WIN32) && defined(USE_XINPUT) && USE_XINPUT
MODULE_NOT_SUPPORTED(x11_lightgun_module, OSD_LIGHTGUNINPUT_PROVIDER, "x11") MODULE_NOT_SUPPORTED(x11_lightgun_module, OSD_LIGHTGUNINPUT_PROVIDER, "x11")
#endif
#endif // defined(SDLMAME_SDL2) && !defined(SDLMAME_WIN32) && defined(USE_XINPUT) && USE_XINPUT
MODULE_DEFINITION(LIGHTGUN_X11, x11_lightgun_module) MODULE_DEFINITION(LIGHTGUN_X11, x11_lightgun_module)

View File

@ -36,6 +36,127 @@
#define XINPUT_LIBRARIES { "xinput1_4.dll" } #define XINPUT_LIBRARIES { "xinput1_4.dll" }
#endif #endif
#define XINPUT_AXIS_MINVALUE -32767
#define XINPUT_AXIS_MAXVALUE 32767
namespace {
// default axis names
const char *const xinput_axis_name[] =
{
"LSX",
"LSY",
"RSX",
"RSY"
};
const input_item_id xinput_axis_ids[] =
{
ITEM_ID_XAXIS,
ITEM_ID_YAXIS,
ITEM_ID_RXAXIS,
ITEM_ID_RYAXIS
};
const USHORT xinput_pov_dir[] = {
XINPUT_GAMEPAD_DPAD_UP,
XINPUT_GAMEPAD_DPAD_DOWN,
XINPUT_GAMEPAD_DPAD_LEFT,
XINPUT_GAMEPAD_DPAD_RIGHT
};
const char *const xinput_pov_names[] = {
"DPAD Up",
"DPAD Down",
"DPAD Left",
"DPAD Right"
};
const USHORT xinput_buttons[] = {
XINPUT_GAMEPAD_A,
XINPUT_GAMEPAD_B,
XINPUT_GAMEPAD_X,
XINPUT_GAMEPAD_Y,
XINPUT_GAMEPAD_LEFT_SHOULDER,
XINPUT_GAMEPAD_RIGHT_SHOULDER,
XINPUT_GAMEPAD_START,
XINPUT_GAMEPAD_BACK,
XINPUT_GAMEPAD_LEFT_THUMB,
XINPUT_GAMEPAD_RIGHT_THUMB,
};
const char *const xinput_button_names[] = {
"A",
"B",
"X",
"Y",
"LB",
"RB",
"Start",
"Back",
"LS",
"RS"
};
//============================================================
// xinput_joystick_module
//============================================================
class xinput_joystick_module : public wininput_module
{
public:
xinput_joystick_module() : wininput_module(OSD_JOYSTICKINPUT_PROVIDER, "xinput")
{
}
int init(const osd_options &options) override
{
// Call the base
int status = wininput_module::init(options);
if (status != 0)
return status;
// Create and initialize our helper
m_xinput_helper = std::make_shared<xinput_api_helper>();
status = m_xinput_helper->initialize();
if (status != 0)
{
osd_printf_error("xinput_joystick_module failed to get XInput interface! Error: %u\n", static_cast<unsigned int>(status));
return -1;
}
return 0;
}
protected:
virtual void input_init(running_machine &machine) override
{
// Loop through each gamepad to determine if they are connected
for (UINT i = 0; i < XUSER_MAX_COUNT; i++)
{
XINPUT_STATE state = {0};
if (m_xinput_helper->xinput_get_state(i, &state) == ERROR_SUCCESS)
{
// allocate and link in a new device
auto *devinfo = m_xinput_helper->create_xinput_device(machine, i, *this);
if (!devinfo)
continue;
// Configure each gamepad to add buttons and Axes, etc.
devinfo->configure();
}
}
}
private:
std::shared_ptr<xinput_api_helper> m_xinput_helper;
};
} // anonymous namespace
int xinput_api_helper::initialize() int xinput_api_helper::initialize()
{ {
m_xinput_dll = osd::dynamic_module::open(XINPUT_LIBRARIES); m_xinput_dll = osd::dynamic_module::open(XINPUT_LIBRARIES);
@ -58,8 +179,6 @@ int xinput_api_helper::initialize()
xinput_joystick_device * xinput_api_helper::create_xinput_device(running_machine &machine, UINT index, wininput_module &module) xinput_joystick_device * xinput_api_helper::create_xinput_device(running_machine &machine, UINT index, wininput_module &module)
{ {
xinput_joystick_device *devinfo;
XINPUT_CAPABILITIES caps = { 0 }; XINPUT_CAPABILITIES caps = { 0 };
if (FAILED(xinput_get_capabilities(index, 0, &caps))) if (FAILED(xinput_get_capabilities(index, 0, &caps)))
{ {
@ -71,23 +190,23 @@ xinput_joystick_device * xinput_api_helper::create_xinput_device(running_machine
snprintf(device_name, sizeof(device_name), "XInput Player %u", index + 1); snprintf(device_name, sizeof(device_name), "XInput Player %u", index + 1);
// allocate the device object // allocate the device object
devinfo = module.devicelist()->create_device<xinput_joystick_device>(machine, device_name, device_name, module, shared_from_this()); auto &devinfo = module.devicelist()->create_device<xinput_joystick_device>(machine, device_name, device_name, module, shared_from_this());
// Set the player ID // Set the player ID
devinfo->xinput_state.player_index = index; devinfo.xinput_state.player_index = index;
// Assign the caps we captured earlier // Assign the caps we captured earlier
devinfo->xinput_state.caps = caps; devinfo.xinput_state.caps = caps;
return devinfo; return &devinfo;
} }
//============================================================ //============================================================
// xinput_joystick_device // xinput_joystick_device
//============================================================ //============================================================
xinput_joystick_device::xinput_joystick_device(running_machine &machine, const char *name, char const *id, input_module &module, std::shared_ptr<xinput_api_helper> helper) xinput_joystick_device::xinput_joystick_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module, std::shared_ptr<xinput_api_helper> helper)
: device_info(machine, name, id, DEVICE_CLASS_JOYSTICK, module), : device_info(machine, std::string(name), std::string(id), DEVICE_CLASS_JOYSTICK, module),
gamepad({{0}}), gamepad({{0}}),
xinput_state({0}), xinput_state({0}),
m_xinput_helper(helper), m_xinput_helper(helper),
@ -193,67 +312,10 @@ void xinput_joystick_device::configure()
m_configured = true; m_configured = true;
} }
//============================================================ #else // defined(OSD_WINDOWS)
// xinput_joystick_module
//============================================================
class xinput_joystick_module : public wininput_module
{
private:
std::shared_ptr<xinput_api_helper> m_xinput_helper;
public:
xinput_joystick_module()
: wininput_module(OSD_JOYSTICKINPUT_PROVIDER, "xinput"),
m_xinput_helper(nullptr)
{
}
int init(const osd_options &options) override
{
// Call the base
int status = wininput_module::init(options);
if (status != 0)
return status;
// Create and initialize our helper
m_xinput_helper = std::make_shared<xinput_api_helper>();
status = m_xinput_helper->initialize();
if (status != 0)
{
osd_printf_error("xinput_joystick_module failed to get XInput interface! Error: %u\n", static_cast<unsigned int>(status));
return -1;
}
return 0;
}
protected:
virtual void input_init(running_machine &machine) override
{
xinput_joystick_device *devinfo;
// Loop through each gamepad to determine if they are connected
for (UINT i = 0; i < XUSER_MAX_COUNT; i++)
{
XINPUT_STATE state = {0};
if (m_xinput_helper->xinput_get_state(i, &state) == ERROR_SUCCESS)
{
// allocate and link in a new device
devinfo = m_xinput_helper->create_xinput_device(machine, i, *this);
if (devinfo == nullptr)
continue;
// Configure each gamepad to add buttons and Axes, etc.
devinfo->configure();
}
}
}
};
#else
MODULE_NOT_SUPPORTED(xinput_joystick_module, OSD_JOYSTICKINPUT_PROVIDER, "xinput") MODULE_NOT_SUPPORTED(xinput_joystick_module, OSD_JOYSTICKINPUT_PROVIDER, "xinput")
#endif
#endif // defined(OSD_WINDOWS)
MODULE_DEFINITION(JOYSTICKINPUT_XINPUT, xinput_joystick_module) MODULE_DEFINITION(JOYSTICKINPUT_XINPUT, xinput_joystick_module)

View File

@ -1,111 +1,24 @@
#ifndef INPUT_XINPUT_H_ #ifndef MAME_OSD_INPUT_INPUT_XINPUT_H
#define INPUT_XINPUT_H_ #define MAME_OSD_INPUT_INPUT_XINPUT_H
#include <mutex> #pragma once
#include "modules/lib/osdlib.h" #include "modules/lib/osdlib.h"
#define XINPUT_MAX_POV 4 #include <cstdint>
#define XINPUT_MAX_BUTTONS 10 #include <memory>
#define XINPUT_MAX_AXIS 4 #include <mutex>
#include <string_view>
#define XINPUT_AXIS_MINVALUE -32767
#define XINPUT_AXIS_MAXVALUE 32767
class xinput_joystick_device; class xinput_joystick_device;
// default axis names
static const char *const xinput_axis_name[] =
{
"LSX",
"LSY",
"RSX",
"RSY"
};
static const input_item_id xinput_axis_ids[] =
{
ITEM_ID_XAXIS,
ITEM_ID_YAXIS,
ITEM_ID_RXAXIS,
ITEM_ID_RYAXIS
};
static const USHORT xinput_pov_dir[] = {
XINPUT_GAMEPAD_DPAD_UP,
XINPUT_GAMEPAD_DPAD_DOWN,
XINPUT_GAMEPAD_DPAD_LEFT,
XINPUT_GAMEPAD_DPAD_RIGHT
};
static const char *const xinput_pov_names[] = {
"DPAD Up",
"DPAD Down",
"DPAD Left",
"DPAD Right"
};
static const USHORT xinput_buttons[] = {
XINPUT_GAMEPAD_A,
XINPUT_GAMEPAD_B,
XINPUT_GAMEPAD_X,
XINPUT_GAMEPAD_Y,
XINPUT_GAMEPAD_LEFT_SHOULDER,
XINPUT_GAMEPAD_RIGHT_SHOULDER,
XINPUT_GAMEPAD_START,
XINPUT_GAMEPAD_BACK,
XINPUT_GAMEPAD_LEFT_THUMB,
XINPUT_GAMEPAD_RIGHT_THUMB,
};
static const char *const xinput_button_names[] = {
"A",
"B",
"X",
"Y",
"LB",
"RB",
"Start",
"Back",
"LS",
"RS"
};
struct gamepad_state
{
BYTE buttons[XINPUT_MAX_BUTTONS];
BYTE povs[XINPUT_MAX_POV];
LONG left_trigger;
LONG right_trigger;
LONG left_thumb_x;
LONG left_thumb_y;
LONG right_thumb_x;
LONG right_thumb_y;
};
// state information for a gamepad; state must be first element
struct xinput_api_state
{
uint32_t player_index;
XINPUT_STATE xstate;
XINPUT_CAPABILITIES caps;
};
// Typedefs for dynamically loaded functions
typedef DWORD (WINAPI *xinput_get_state_fn)(DWORD, XINPUT_STATE *);
typedef DWORD (WINAPI *xinput_get_caps_fn)(DWORD, DWORD, XINPUT_CAPABILITIES *);
class xinput_api_helper : public std::enable_shared_from_this<xinput_api_helper> class xinput_api_helper : public std::enable_shared_from_this<xinput_api_helper>
{ {
public: public:
xinput_api_helper() xinput_api_helper() { }
: m_xinput_dll(nullptr),
XInputGetState(nullptr),
XInputGetCapabilities(nullptr)
{
}
int initialize(); int initialize();
xinput_joystick_device * create_xinput_device(running_machine &machine, UINT index, wininput_module &module); xinput_joystick_device *create_xinput_device(running_machine &machine, UINT index, wininput_module &module);
DWORD xinput_get_state(DWORD dwUserindex, XINPUT_STATE *pState) const DWORD xinput_get_state(DWORD dwUserindex, XINPUT_STATE *pState) const
{ {
@ -118,14 +31,42 @@ public:
} }
private: private:
osd::dynamic_module::ptr m_xinput_dll; // Typedefs for dynamically loaded functions
xinput_get_state_fn XInputGetState; typedef DWORD (WINAPI *xinput_get_state_fn)(DWORD, XINPUT_STATE *);
xinput_get_caps_fn XInputGetCapabilities; typedef DWORD (WINAPI *xinput_get_caps_fn)(DWORD, DWORD, XINPUT_CAPABILITIES *);
osd::dynamic_module::ptr m_xinput_dll = nullptr;
xinput_get_state_fn XInputGetState = nullptr;
xinput_get_caps_fn XInputGetCapabilities = nullptr;
}; };
class xinput_joystick_device : public device_info class xinput_joystick_device : public device_info
{ {
public: public:
static inline constexpr int XINPUT_MAX_POV = 4;
static inline constexpr int XINPUT_MAX_BUTTONS = 10;
static inline constexpr int XINPUT_MAX_AXIS = 4;
struct gamepad_state
{
BYTE buttons[XINPUT_MAX_BUTTONS];
BYTE povs[XINPUT_MAX_POV];
LONG left_trigger;
LONG right_trigger;
LONG left_thumb_x;
LONG left_thumb_y;
LONG right_thumb_x;
LONG right_thumb_y;
};
// state information for a gamepad; state must be first element
struct xinput_api_state
{
uint32_t player_index;
XINPUT_STATE xstate;
XINPUT_CAPABILITIES caps;
};
gamepad_state gamepad; gamepad_state gamepad;
xinput_api_state xinput_state; xinput_api_state xinput_state;
@ -135,11 +76,11 @@ private:
bool m_configured; bool m_configured;
public: public:
xinput_joystick_device(running_machine &machine, const char *name, const char *id, input_module &module, std::shared_ptr<xinput_api_helper> helper); xinput_joystick_device(running_machine &machine, std::string &&name, std::string &&id, input_module &module, std::shared_ptr<xinput_api_helper> helper);
void poll() override; void poll() override;
void reset() override; void reset() override;
void configure(); void configure();
}; };
#endif #endif // MAME_OSD_INPUT_INPUT_XINPUT_H