MAMEWorld >> Programming
View all threads Index   Flat Mode Flat  

byuu
MAME Fan
Reged: 03/17/06
Posts: 41
Send PM
EDIT: I think I understand what's going on now.
03/24/09 01:51 PM


Another copy-paste because I'm lazy, sorry.

-----

Yesterday I requested assistance for a joypad axis mapping issue, but I believe I understand the problem and have the proper solution now.

Background: new joypads have pressure-sensitive buttons; rather than simply being on or off, the joypad reports how far down a button is pressed. Given how new this is, various input APIs and indeed the USB HID itself do not directly support these new buttons. Instead, they are mapped as axes, which are basically bi-directional sticks. Unlike buttons that start off fully depressed, sticks start off centered.

A problem arises in trying to tell them apart: at application startup, polling the joypad state returns zero, or centered, for all axes. Even buttons that are fully depressed. It isn't until a button is pressed or an axis is moved that the actual state of the pressure-sensitive buttons are read correctly.

I believe the reason for this is due to the design of the USB HID. Rather than having an interface to poll the current state of joypads, it instead sends messages with the state of the entire device whenever the state is changed (eg a button is pressed.) On Windows, this would correspond to the raw input WM_INPUT window message. DirectInput appears to buffer this information on an app-by-app basis. On Linux, this data seems to be cached by the input driver globally; so each joypad needs only one message sent per system reset.

So what happens when you first start an application? It can't possibly know the state until a message is sent, so it feeds back what you would expect: unpressed buttons and centered (zero-positioned) axes.

Further, we can't simply check the axis states after the first button press, because the user may decide to move an axis or press an analog button first. Since we can't tell which object state changed, we may end up detecting an analog button as a stick or vice versa.

My solution was to display a popup the first time the user attempts to map a joypad axis. It asks the user not to press any buttons, and to leave all axes alone; and then to press okay. After hitting okay, I then query the states of each axis. To prevent needing to calibrate the joypad every time the application is run, and to avoid issues with swapping out joypads, I save the type of input by appending it onto the assignment name for a given ID, eg "joypad01.axis03::trigger" states that axis03 is a pressure-sensitive button (or trigger), whereas "joypad01.axis03::lo" indicates an axis that is triggered by moving a given axis left or up (depending on direction.) Therefore, on future startups, the type of axis will already be known without having to prompt the user to calibrate the joypad again.

-----

Of course my theory could be wrong. If anyone's certain that it is, I'd certainly like to know. But my solution works regardless, so all is well

And hopefully the above info will be helpful to any emu authors here writing joypad polling code.







Entire thread
Subject Posted by Posted on
* Capturing analog button input on Windows *DELETED* byuu 03/24/09 01:32 AM
. * Did someone talk to you? Dullaron  03/25/09 07:11 PM
. * Re: Did someone talk to you? StilettoAdministrator  03/26/09 03:15 AM
. * EDIT: I think I understand what's going on now. byuu  03/24/09 01:51 PM
. * Re: EDIT: I think I understand what's going on now. R. Belmont  03/30/09 03:47 PM
. * Re: EDIT: I think I understand what's going on now. byuu  04/02/09 04:27 AM
. * Re: EDIT: I think I understand what's going on now. uRebelScum  04/02/09 08:43 PM
. * Re: EDIT: I think I understand what's going on now. byuu  04/02/09 11:59 PM

Extra information Permissions
Moderator:  Pi 
0 registered and 34 anonymous users are browsing this forum.
You cannot start new topics
You cannot reply to topics
HTML is enabled
UBBCode is enabled
Thread views: 5295