summaryrefslogtreecommitdiffstatshomepage
path: root/src/osd/modules/input/input_x11.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/osd/modules/input/input_x11.cpp')
-rw-r--r--src/osd/modules/input/input_x11.cpp678
1 files changed, 380 insertions, 298 deletions
diff --git a/src/osd/modules/input/input_x11.cpp b/src/osd/modules/input/input_x11.cpp
index 40df3d528b6..5230dfd7164 100644
--- a/src/osd/modules/input/input_x11.cpp
+++ b/src/osd/modules/input/input_x11.cpp
@@ -9,34 +9,41 @@
//============================================================
#include "input_module.h"
+
#include "modules/osdmodule.h"
#if defined(SDLMAME_SDL2) && !defined(SDLMAME_WIN32) && defined(USE_XINPUT) && USE_XINPUT
+#include "input_common.h"
+
+#include "sdl/osdsdl.h"
+
+// MAME headers
+#include "inpttype.h"
+
+// standard SDL header
+#include <SDL2/SDL.h>
+
// for X11 xinput
#include <X11/Xlib.h>
#include <X11/extensions/XInput.h>
#include <X11/Xutil.h>
-// standard sdl header
-#include <SDL2/SDL.h>
-#include <ctype.h>
-#include <stddef.h>
-#include <mutex>
+#include <algorithm>
+#include <cctype>
+#include <cstddef>
+#include <cstdio>
+#include <cstring>
#include <memory>
+#include <mutex>
#include <queue>
#include <string>
-#include <algorithm>
+#include <unordered_map>
-// MAME headers
-#include "emu.h"
-#include "osdepend.h"
-// MAMEOS headers
-#include "../lib/osdobj_common.h"
-#include "input_common.h"
-#include "../../sdl/osdsdl.h"
-#include "input_sdlcommon.h"
+namespace osd {
+
+namespace {
#define MAX_DEVMAP_ENTRIES 16
@@ -49,20 +56,6 @@ static int key_release_type = INVALID_EVENT_TYPE;
static int proximity_in_type = INVALID_EVENT_TYPE;
static int proximity_out_type = INVALID_EVENT_TYPE;
-// state information for a lightgun
-struct lightgun_state
-{
- int32_t lX, lY;
- int32_t buttons[MAX_BUTTONS];
-};
-
-struct x11_api_state
-{
- XID deviceid; // X11 device id
- int32_t maxx, maxy;
- int32_t minx, miny;
-};
-
//============================================================
// DEBUG MACROS
//============================================================
@@ -71,56 +64,64 @@ struct x11_api_state
#define XI_DBG(format, ...) osd_printf_verbose(format, __VA_ARGS__)
#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 const *motion)
{
/*
* print a lot of debug informations of the motion event(s).
*/
osd_printf_verbose(
- "XDeviceMotionEvent:\n"
- " type: %d\n"
- " serial: %lu\n"
- " send_event: %d\n"
- " display: %p\n"
- " window: --\n"
- " deviceid: %lu\n"
- " root: --\n"
- " subwindow: --\n"
- " time: --\n"
- " x: %d, y: %d\n"
- " x_root: %d, y_root: %d\n"
- " state: %u\n"
- " is_hint: %2.2X\n"
- " same_screen: %d\n"
- " device_state: %u\n"
- " axes_count: %2.2X\n"
- " first_axis: %2.2X\n"
- " axis_data[6]: {%d,%d,%d,%d,%d,%d}\n",
- motion->type,
- motion->serial,
- motion->send_event,
- motion->display,
- /* motion->window, */
- motion->deviceid,
- /* motion->root */
- /* motion->subwindow */
- /* motion->time, */
- motion->x, motion->y,
- motion->x_root, motion->y_root,
- motion->state,
- motion->is_hint,
- motion->same_screen,
- motion->device_state,
- motion->axes_count,
- motion->first_axis,
- motion->axis_data[0], motion->axis_data[1], motion->axis_data[2], motion->axis_data[3], motion->axis_data[4], motion->axis_data[5]
- );
+ "XDeviceMotionEvent:\n"
+ " type: %d\n"
+ " serial: %lu\n"
+ " send_event: %d\n"
+ " display: %p\n"
+ " window: --\n"
+ " deviceid: %lu\n"
+ " root: --\n"
+ " subwindow: --\n"
+ " time: --\n"
+ " x: %d, y: %d\n"
+ " x_root: %d, y_root: %d\n"
+ " state: %u\n"
+ " is_hint: %2.2X\n"
+ " same_screen: %d\n"
+ " device_state: %u\n"
+ " axes_count: %2.2X\n"
+ " first_axis: %2.2X\n"
+ " axis_data[6]: {%d,%d,%d,%d,%d,%d}\n",
+ motion->type,
+ motion->serial,
+ motion->send_event,
+ motion->display,
+ /* motion->window, */
+ motion->deviceid,
+ /* motion->root */
+ /* motion->subwindow */
+ /* motion->time, */
+ motion->x, motion->y,
+ motion->x_root, motion->y_root,
+ motion->state,
+ motion->is_hint,
+ motion->same_screen,
+ motion->device_state,
+ motion->axes_count,
+ motion->first_axis,
+ motion->axis_data[0], motion->axis_data[1], motion->axis_data[2], motion->axis_data[3], motion->axis_data[4], motion->axis_data[5]);
}
#else
-#define XI_DBG(format, ...) while(0) {}
-#define print_motion_event(motion) while(0) {}
+#define XI_DBG(format, ...) do { } while (false)
+#define print_motion_event(motion) do { } while (false)
#endif
+
+inline std::string remove_spaces(const char *s)
+{
+ std::string output(s);
+ output.erase(std::remove_if(output.begin(), output.end(), isspace), output.end());
+ return output;
+}
+
+
//============================================================
// lightgun helpers: copy-past from xinfo
//============================================================
@@ -138,7 +139,7 @@ find_device_info(Display *display,
bool is_id = true;
XID id = static_cast<XID>(-1);
- for(loop = 0; loop < len; loop++)
+ for (loop = 0; loop < len; loop++)
{
if (!isdigit(name[loop]))
{
@@ -154,7 +155,7 @@ find_device_info(Display *display,
devices = XListInputDevices(display, &num_devices);
- for(loop = 0; loop < num_devices; loop++)
+ for (loop = 0; loop < num_devices; loop++)
{
osd_printf_verbose("Evaluating device with name: %s\n", devices[loop].name);
@@ -185,7 +186,7 @@ find_device_info(Display *display,
}
//Copypasted from xinfo
-static int
+int
register_events(
Display *dpy,
XDeviceInfo *info,
@@ -252,32 +253,90 @@ register_events(
return number;
}
-//============================================================
-// x11_event_manager
-//============================================================
-class x11_event_handler
+struct device_map
{
-public:
- virtual ~x11_event_handler() {}
+ static inline constexpr unsigned MAX_ENTRIES = 16;
+
+ struct {
+ std::string name;
+ int physical;
+ } map[MAX_ENTRIES];
+ int logical[MAX_ENTRIES];
+ int initialized;
+
+ void init(osd_options const &options, const char *opt, int max_devices, const char *label)
+ {
+ // initialize based on an input option prefix and max number of devices
+ char defname[20];
+
+ // The max devices the user specified, better not be bigger than the max the arrays can old
+ assert(max_devices <= MAX_ENTRIES);
- virtual void handle_event(XEvent &xevent) = 0;
+ // Initialize the map to default uninitialized values
+ for (int dev = 0; dev < MAX_ENTRIES; dev++)
+ {
+ map[dev].name.clear();
+ map[dev].physical = -1;
+ logical[dev] = -1;
+ }
+ initialized = 0;
+
+ // populate the device map up to the max number of devices
+ for (int dev = 0; dev < max_devices; dev++)
+ {
+ const char *dev_name;
+
+ // derive the parameter name from the option name and index. For instance: lightgun_index1 to lightgun_index8
+ sprintf(defname, "%s%d", opt, dev + 1);
+
+ // Get the user-specified name that matches the parameter
+ dev_name = options.value(defname);
+
+ // If they've specified a name and it's not "auto", treat it as a custom mapping
+ if (dev_name && *dev_name && strcmp(dev_name, OSDOPTVAL_AUTO))
+ {
+ // remove the spaces from the name store it in the index
+ map[dev].name = remove_spaces(dev_name);
+ osd_printf_verbose("%s: Logical id %d: %s\n", label, dev + 1, map[dev].name);
+ initialized = 1;
+ }
+ }
+ }
};
-class x11_event_manager : public event_manager_t<x11_event_handler>
+
+//============================================================
+// x11_event_manager
+//============================================================
+
+class x11_event_manager : public event_subscription_manager<XEvent, int>
{
private:
- Display * m_display;
-
- x11_event_manager()
- : event_manager_t(),
- m_display(nullptr)
+ struct x_cleanup
{
- }
+ void operator()(Display *ptr) const
+ {
+ if (ptr)
+ XCloseDisplay(ptr);
+ }
+ void operator()(XExtensionVersion *ptr) const
+ {
+ if (ptr)
+ XFree(ptr);
+ }
+ };
+
+ template <typename T> using x_ptr = std::unique_ptr<T, x_cleanup>;
+
+ x_ptr<Display> m_display;
+
+ x11_event_manager() = default;
+
public:
- Display * display() const { return m_display; }
+ Display *display() const { return m_display.get(); }
- static x11_event_manager& instance()
+ static x11_event_manager &instance()
{
static x11_event_manager s_instance;
return s_instance;
@@ -285,20 +344,20 @@ public:
int initialize()
{
- std::lock_guard<std::mutex> scope_lock(m_lock);
+ std::lock_guard<std::mutex> scope_lock(subscription_mutex());
- if (m_display != nullptr)
+ if (m_display)
return 0;
- m_display = XOpenDisplay(nullptr);
- if (m_display == nullptr)
+ m_display.reset(XOpenDisplay(nullptr));
+ if (!m_display)
{
osd_printf_verbose("Unable to connect to X server\n");
return -1;
}
- XExtensionVersion *version = XGetExtensionVersion(m_display, INAME);
- if (!version || (version == reinterpret_cast<XExtensionVersion*>(NoSuchExtension)))
+ x_ptr<XExtensionVersion> version(XGetExtensionVersion(m_display.get(), INAME));
+ if (!version || (version.get() == reinterpret_cast<XExtensionVersion *>(NoSuchExtension)))
{
osd_printf_verbose("xinput extension not available!\n");
return -1;
@@ -307,28 +366,24 @@ public:
return 0;
}
- void process_events(running_machine &machine) override
+ void process_events()
{
- std::lock_guard<std::mutex> scope_lock(m_lock);
- XEvent xevent;
+ std::lock_guard<std::mutex> scope_lock(subscription_mutex());
- //Get XInput events
- while (XPending(m_display) != 0)
- {
- XNextEvent(m_display, &xevent);
-
- // Find all subscribers for the event type
- auto subscribers = m_subscription_index.equal_range(xevent.type);
+ // If X11 has become invalid for some reason, XPending will crash. Assert instead.
+ assert(m_display);
- // Dispatch the events
- std::for_each(subscribers.first, subscribers.second, [&xevent](auto &pair)
- {
- pair.second->handle_event(xevent);
- });
+ // Get XInput events
+ while (XPending(m_display.get()) != 0)
+ {
+ XEvent event;
+ XNextEvent(m_display.get(), &event);
+ dispatch_event(event.type, event);
}
}
};
+
//============================================================
// x11_input_device
//============================================================
@@ -336,15 +391,23 @@ public:
class x11_input_device : public event_based_device<XEvent>
{
public:
- x11_api_state x11_state;
-
- x11_input_device(running_machine &machine, const char *name, const char *id, input_device_class devclass, input_module &module)
- : event_based_device(machine, name, id, devclass, module),
- x11_state({0})
+ x11_input_device(
+ std::string &&name,
+ std::string &&id,
+ input_module &module,
+ XDeviceInfo const *info) :
+ event_based_device(std::move(name), std::move(id), module),
+ m_device_id(info ? info->id : 0)
{
}
+
+ XID const &device_id() const { return m_device_id; }
+
+protected:
+ XID const m_device_id; // X11 device ID
};
+
//============================================================
// x11_lightgun_device
//============================================================
@@ -352,55 +415,124 @@ public:
class x11_lightgun_device : public x11_input_device
{
public:
- lightgun_state lightgun;
+ x11_lightgun_device(
+ std::string &&name,
+ std::string &&id,
+ input_module
+ &module,
+ XDeviceInfo *info) :
+ x11_input_device(std::move(name), std::move(id), module, info),
+ m_axis_count(0),
+ m_button_count(0),
+ m_maxx(0),
+ m_maxy(0),
+ m_minx(0),
+ m_miny(0),
+ m_lightgun({ 0 })
+ {
+ if (info && (info->num_classes > 0))
+ {
+ // Grab device info and translate to stuff MAME can use
+ XAnyClassPtr any = static_cast<XAnyClassPtr>(info->inputclassinfo);
+ for (int i = 0; i < info->num_classes; i++)
+ {
+ switch (any->c_class)
+ {
+ // Set the axis min/max ranges if we got them
+ case ValuatorClass:
+ {
+ auto const valuator_info = reinterpret_cast<XValuatorInfoPtr>(any);
+ auto axis_info = reinterpret_cast<XAxisInfoPtr>(reinterpret_cast<char *>(valuator_info) + sizeof(XValuatorInfo));
+ for (int j = 0; (j < valuator_info->num_axes) && (j < 2); j++, axis_info++)
+ {
+ if (j == 0)
+ {
+ XI_DBG("Set minx=%d, maxx=%d\n", axis_info->min_value, axis_info->max_value);
+ m_axis_count = 1;
+ m_maxx = axis_info->max_value;
+ m_minx = axis_info->min_value;
+ }
+
+ if (j == 1)
+ {
+ XI_DBG("Set miny=%d, maxy=%d\n", axis_info->min_value, axis_info->max_value);
+ m_axis_count = 2;
+ m_maxy = axis_info->max_value;
+ m_miny = axis_info->min_value;
+ }
+ }
+ }
+ break;
+
+ // Count the lightgun buttons based on what we read
+ case ButtonClass:
+ {
+ XButtonInfoPtr b = reinterpret_cast<XButtonInfoPtr>(any);
+ if (b->num_buttons < 0)
+ m_button_count = 0;
+ else if (b->num_buttons <= MAX_BUTTONS)
+ m_button_count = b->num_buttons;
+ else
+ m_button_count = MAX_BUTTONS;
+ }
+ break;
+ }
- x11_lightgun_device(running_machine &machine, const char *name, const char *id, input_module &module)
- : x11_input_device(machine, name, id, DEVICE_CLASS_LIGHTGUN, module),
- lightgun({0})
+ any = reinterpret_cast<XAnyClassPtr>(reinterpret_cast<char *>(any) + any->length);
+ }
+ }
+ }
+
+ virtual void reset() override
{
+ memset(&m_lightgun, 0, sizeof(m_lightgun));
}
- void process_event(XEvent &xevent) override
+ virtual void configure(input_device &device) override
+ {
+ // Add buttons
+ for (int button = 0; button < m_button_count; button++)
+ {
+ input_item_id const itemid = input_item_id(ITEM_ID_BUTTON1 + button);
+ device.add_item(default_button_name(button), std::string_view(), itemid, generic_button_get_state<std::int32_t>, &m_lightgun.buttons[button]);
+ }
+
+ // Add X and Y axis
+ if (1 <= m_axis_count)
+ device.add_item("X", std::string_view(), ITEM_ID_XAXIS, generic_axis_get_state<std::int32_t>, &m_lightgun.lX);
+ if (2 <= m_axis_count)
+ device.add_item("Y", std::string_view(), ITEM_ID_YAXIS, generic_axis_get_state<std::int32_t>, &m_lightgun.lY);
+ }
+
+ virtual void process_event(XEvent const &xevent) override
{
if (xevent.type == motion_type)
{
- XDeviceMotionEvent *motion = reinterpret_cast<XDeviceMotionEvent *>(&xevent);
+ auto const motion = reinterpret_cast<XDeviceMotionEvent const *>(&xevent);
print_motion_event(motion);
- /*
- * We have to check with axis will start on array index 0.
- * We have also to check the number of axes that are stored in the array.
- */
+ // We have to check with axis will start on array index 0.
+ // We also have to check the number of axes that are stored in the array.
switch (motion->first_axis)
{
- /*
- * Starting with x, check number of axis, if there is also the y axis stored.
- */
+ // Starting with x, check number of axes, if there is also the y axis stored.
case 0:
if (motion->axes_count >= 1)
- {
- lightgun.lX = normalize_absolute_axis(motion->axis_data[0], x11_state.minx, x11_state.maxx);
- if (motion->axes_count >= 2)
- {
- lightgun.lY = normalize_absolute_axis(motion->axis_data[1], x11_state.miny, x11_state.maxy);
- }
- }
+ m_lightgun.lX = normalize_absolute_axis(motion->axis_data[0], m_minx, m_maxx);
+ if (motion->axes_count >= 2)
+ m_lightgun.lY = normalize_absolute_axis(motion->axis_data[1], m_miny, m_maxy);
break;
- /*
- * Starting with y, ...
- */
+ // Starting with y, ...
case 1:
if (motion->axes_count >= 1)
- {
- lightgun.lY = normalize_absolute_axis(motion->axis_data[0], x11_state.miny, x11_state.maxy);
- }
+ m_lightgun.lY = normalize_absolute_axis(motion->axis_data[0], m_miny, m_maxy);
break;
}
}
else if (xevent.type == button_press_type || xevent.type == button_release_type)
{
- XDeviceButtonEvent *button = reinterpret_cast<XDeviceButtonEvent *>(&xevent);
+ auto const button = reinterpret_cast<XDeviceButtonEvent const *>(&xevent);
/*
* SDL/X11 Number the buttons 1,2,3, while windows and other parts of MAME
@@ -408,140 +540,160 @@ public:
* -1 the button number to align the numbering schemes.
*/
int button_number = button->button;
- switch (button_number)
+ if (button_number <= MAX_BUTTONS)
{
+ switch (button_number)
+ {
case 2:
- button_number = 3;
- break;
case 3:
- button_number = 2;
+ button_number ^= 1;
break;
+ }
+ m_lightgun.buttons[button_number - 1] = (xevent.type == button_press_type) ? 0x80 : 0;
}
- lightgun.buttons[button_number - 1] = (xevent.type == button_press_type) ? 0x80 : 0;
}
}
- void reset() override
+private:
+ struct lightgun_state
{
- memset(&lightgun, 0, sizeof(lightgun));
- }
+ int32_t lX, lY;
+ int32_t buttons[MAX_BUTTONS];
+ };
+
+ int m_axis_count;
+ int m_button_count;
+ int32_t m_maxx;
+ int32_t m_maxy;
+ int32_t m_minx;
+ int32_t m_miny;
+ lightgun_state m_lightgun;
};
+
//============================================================
// x11_lightgun_module
//============================================================
-class x11_lightgun_module : public input_module_base, public x11_event_handler
+class x11_lightgun_module : public input_module_impl<x11_input_device, osd_common_t>, public x11_event_manager::subscriber
{
private:
- device_map_t m_lightgun_map;
- Display * m_display;
+ device_map m_lightgun_map;
+ Display *m_display;
+
public:
- x11_lightgun_module()
- : input_module_base(OSD_LIGHTGUNINPUT_PROVIDER, "x11"),
- m_display(nullptr)
+ x11_lightgun_module() :
+ input_module_impl<x11_input_device, osd_common_t>(OSD_LIGHTGUNINPUT_PROVIDER, "x11"),
+ m_display(nullptr)
{
}
- void input_init(running_machine &machine) override
+ virtual bool probe() override
{
- int index;
+ // If there is no X server, X11 lightguns cannot be supported
+ Display *const display = XOpenDisplay(nullptr);
+ if (!display)
+ return false;
+ XCloseDisplay(display);
- osd_printf_verbose("Lightgun: Begin initialization\n");
-
- devmap_init(machine, &m_lightgun_map, SDLOPTION_LIGHTGUNINDEX, 8, "Lightgun mapping");
+ return true;
+ }
+ virtual int init(osd_interface &osd, osd_options const &options) override
+ {
+ // If the X server has become invalid, a crash can occur
x11_event_manager::instance().initialize();
m_display = x11_event_manager::instance().display();
+ if (!m_display)
+ return -1;
+
+ return input_module_impl<x11_input_device, osd_common_t>::init(osd, options);
+ }
+
+ virtual void input_init(running_machine &machine) override
+ {
+ assert(m_display);
+
+ input_module_impl<x11_input_device, osd_common_t>::input_init(machine);
+
+ osd_printf_verbose("Lightgun: Begin initialization\n");
+
+ m_lightgun_map.init(*options(), SDLOPTION_LIGHTGUNINDEX, 8, "Lightgun mapping");
// Loop through all 8 possible devices
- for (index = 0; index < 8; index++)
+ for (int index = 0; index < 8; index++)
{
- XDeviceInfo *info;
-
// Skip if the name is empty
- if (m_lightgun_map.map[index].name.length() == 0)
+ if (m_lightgun_map.map[index].name.empty())
continue;
- x11_lightgun_device *devinfo;
+ // Find the device info associated with the name
std::string const &name = m_lightgun_map.map[index].name;
- char defname[512];
+ osd_printf_verbose("%i: %s\n", index, name);
+ XDeviceInfo *const info = find_device_info(m_display, name.c_str(), 0);
+ if (!info)
+ osd_printf_verbose("Lightgun: Can't find device %s!\n", name);
- // Register and add the device
- devinfo = create_lightgun_device(machine, index);
- osd_printf_verbose("%i: %s\n", index, name.c_str());
-
- // Find the device info associated with the name
- info = find_device_info(m_display, name.c_str(), 0);
+ // previously had code to use "NC%d" format if name was empty
+ // but that couldn't happen because device creation would be skipped
- // If we couldn't find the device, skip
- if (info == nullptr)
- {
- osd_printf_verbose("Can't find device %s!\n", name.c_str());
- continue;
- }
+ // Register and add the device
+ create_device<x11_lightgun_device>(
+ DEVICE_CLASS_LIGHTGUN,
+ std::string(name),
+ std::string(name),
+ info);
- //Grab device info and translate to stuff mame can use
- if (info->num_classes > 0)
+ // Register this device to receive event notifications
+ if (info)
{
- // Add the lightgun buttons based on what we read
- add_lightgun_buttons(static_cast<XAnyClassPtr>(info->inputclassinfo), info->num_classes, devinfo);
-
- // Also, set the axix min/max ranges if we got them
- set_lightgun_axis_props(static_cast<XAnyClassPtr>(info->inputclassinfo), info->num_classes, devinfo);
+ int const events_registered = register_events(m_display, info, name.c_str(), 0);
+ osd_printf_verbose("Device %i: Registered %i events.\n", int(info->id), events_registered);
}
+ }
- // Add X and Y axis
- sprintf(defname, "X %s", devinfo->name());
- devinfo->device()->add_item(defname, ITEM_ID_XAXIS, generic_axis_get_state<std::int32_t>, &devinfo->lightgun.lX);
-
- sprintf(defname, "Y %s", devinfo->name());
- devinfo->device()->add_item(defname, ITEM_ID_YAXIS, generic_axis_get_state<std::int32_t>, &devinfo->lightgun.lY);
-
- // Save the device id
- devinfo->x11_state.deviceid = info->id;
+ // register ourself to handle events from event manager
+ int const event_types[] = { motion_type, button_press_type, button_release_type };
+ osd_printf_verbose("Events types to register: motion:%d, press:%d, release:%d\n", motion_type, button_press_type, button_release_type);
+ subscribe(x11_event_manager::instance(), event_types);
- // Register this device to receive event notifications
- int events_registered = register_events(m_display, info, m_lightgun_map.map[index].name.c_str(), 0);
- osd_printf_verbose("Device %i: Registered %i events.\n", static_cast<int>(info->id), events_registered);
+ osd_printf_verbose("Lightgun: End initialization\n");
+ }
- // register ourself to handle events from event manager
- int event_types[] = { motion_type, button_press_type, button_release_type };
- osd_printf_verbose("Events types to register: motion:%d, press:%d, release:%d\n", motion_type, button_press_type, button_release_type);
- x11_event_manager::instance().subscribe(event_types, ARRAY_LENGTH(event_types), this);
- }
+ virtual void exit() override
+ {
+ // unsubscribe from events
+ unsubscribe();
- osd_printf_verbose("Lightgun: End initialization\n");
+ input_module_impl<x11_input_device, osd_common_t>::exit();
}
- bool should_poll_devices(running_machine &machine) override
+ virtual bool should_poll_devices() override
{
- return sdl_event_manager::instance().has_focus();
+ return osd().has_focus();
}
- void before_poll(running_machine &machine) override
+ virtual void before_poll() override
{
- if (!should_poll_devices(machine))
- return;
+ // trigger the SDL event manager so it can process window events
+ input_module_impl<x11_input_device, osd_common_t>::before_poll();
// Tell the event manager to process events and push them to the devices
- x11_event_manager::instance().process_events(machine);
-
- // Also trigger the SDL event manager so it can process window events
- sdl_event_manager::instance().process_events(machine);
+ if (should_poll_devices())
+ x11_event_manager::instance().process_events();
}
- void handle_event(XEvent &xevent) override
+ virtual void handle_event(XEvent const &xevent) override
{
XID deviceid;
if (xevent.type == motion_type)
{
- XDeviceMotionEvent *motion = reinterpret_cast<XDeviceMotionEvent *>(&xevent);
+ auto const motion = reinterpret_cast<XDeviceMotionEvent const *>(&xevent);
deviceid = motion->deviceid;
}
else if (xevent.type == button_press_type || xevent.type == button_release_type)
{
- XDeviceButtonEvent *button = reinterpret_cast<XDeviceButtonEvent *>(&xevent);
+ auto const button = reinterpret_cast<XDeviceButtonEvent const *>(&xevent);
deviceid = button->deviceid;
}
else
@@ -550,97 +702,27 @@ public:
}
// Figure out which lightgun this event id destined for
- auto target_device = std::find_if(devicelist()->begin(), devicelist()->end(), [deviceid](auto &device)
- {
- std::unique_ptr<device_info> &ptr = device;
- return downcast<x11_input_device*>(ptr.get())->x11_state.deviceid == deviceid;
- });
+ auto target_device = std::find_if(
+ devicelist().begin(),
+ devicelist().end(),
+ [&deviceid] (auto &device) { return device->device_id() == deviceid; });
// If we find a matching lightgun, dispatch the event to the lightgun
- if (target_device != devicelist()->end())
- {
- downcast<x11_input_device*>((*target_device).get())->queue_events(&xevent, 1);
- }
+ if (target_device != devicelist().end())
+ (*target_device)->queue_events(&xevent, 1);
}
+};
-private:
- 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.initialized)
- {
- snprintf(tempname, ARRAY_LENGTH(tempname), "NC%d", index);
- devicelist()->create_device<x11_lightgun_device>(machine, tempname, tempname, *this);
- }
-
- 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
- {
- XAnyClassPtr any = first_info_class;
-
- for (int i = 0; i < num_classes; i++)
- {
- switch (any->c_class)
- {
- case ButtonClass:
- XButtonInfoPtr b = reinterpret_cast<XButtonInfoPtr>(any);
- for (int button = 0; button < b->num_buttons; 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]);
- }
- break;
- }
+} // anonymous namespace
- any = reinterpret_cast<XAnyClassPtr>(reinterpret_cast<char *>(any) + any->length);
- }
- }
+} // namespace osd
- void set_lightgun_axis_props(XAnyClassPtr first_info_class, int num_classes, x11_lightgun_device *devinfo) const
- {
- XAnyClassPtr any = first_info_class;
- for (int i = 0; i < num_classes; i++)
- {
- switch (any->c_class)
- {
- case ValuatorClass:
- XValuatorInfoPtr valuator_info = reinterpret_cast<XValuatorInfoPtr>(any);
- XAxisInfoPtr axis_info = reinterpret_cast<XAxisInfoPtr>(reinterpret_cast<char *>(valuator_info) + sizeof(XValuatorInfo));
- for (int j = 0; j < valuator_info->num_axes; j++, axis_info++)
- {
- if (j == 0)
- {
- 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.minx = axis_info->min_value;
- }
+#else // defined(SDLMAME_SDL2) && !defined(SDLMAME_WIN32) && defined(USE_XINPUT) && USE_XINPUT
- if (j == 1)
- {
- 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.miny = axis_info->min_value;
- }
- }
- break;
- }
+namespace osd { namespace { MODULE_NOT_SUPPORTED(x11_lightgun_module, OSD_LIGHTGUNINPUT_PROVIDER, "x11") } }
- any = reinterpret_cast<XAnyClassPtr>(reinterpret_cast<char *>(any) + any->length);
- }
- }
-};
+#endif // defined(SDLMAME_SDL2) && !defined(SDLMAME_WIN32) && defined(USE_XINPUT) && USE_XINPUT
-#else
-MODULE_NOT_SUPPORTED(x11_lightgun_module, OSD_LIGHTGUNINPUT_PROVIDER, "x11")
-#endif
-MODULE_DEFINITION(LIGHTGUN_X11, x11_lightgun_module)
+MODULE_DEFINITION(LIGHTGUN_X11, osd::x11_lightgun_module)