Errant analog noise from controller preventing sleep
-
tl;dr A cheap but common USB "digital" encoder board produces spikes on one of its "analog" axis, enough to register as a button press and prevent screensaver / sleep.
Hi all, I've been building a cabinet and am using a cheap but ubiquitous USB encoder board for the buttons. It all over Amazon / ebay / etc, a single-sided tan board with "CY-822A" model number on the silkscreen, 12 buttons + 4-way digital discrete / Sanwa connectors, and a blob chip design. USB ID "DragonRise Inc. Generic USB Joystick", 0079:0006.
It works fine, but I was getting issues with getting ES to sleep. I had it set to dim screensaver at 1 minute idle, then sleep at 10 minutes, which I have a
sleep
/wake
script turn off / on the Raspberry Pi 4 HDMI display withvcgencmd
. But what I noticed was the sleep would happen at random times, anywhere from 10 to 30 minutes, and would soon wake up again on its own.The reason turned out to be the encoder board. At a uinput level, the "digital" board actually advertises 7 axes. Axis 0 and 1 are the mappings for the U/D/L/R buttons, while 3/4/5/6 are actually analog axes which are disabled on the board by a balanced resistor pair, so they always sit at 127. (There are hardware mods out there to enable this analog functionality.) That leaves axis 2, which has constant jitter. Usually it's minor, but will occasionally spike enough to exceed ES's
DEADZONE
limit, on average every few minutes. So it's likely a floating analog circuit which occasionally gets enough noise to spike. If this were the case, I would add a resistor set to the board for it, but I can't find the axis on the board. Most likely it doesn't have traces outside the chip blob.My first thought was using
jscal
to nerf axis 2, essentially making it one giant dead zone. That worked, but only forjs0
; I quickly learned ES actually usesinput0
directly, sojscal
adjustments are not used. My next thought was to write a Python script using theuinput
library to read the events frominput0
and create its own virtual device which passes through all events except for axes 2-6. I actually got 95% of the way done with that before noticing that ES will discover and load all input devices as they appear, whether they're configured or not, and will use them for determining whether to take the window out of sleep / screensaver.So I don't think I can work my way around this. I think it would be nice to have one or more of these features:
- Unconfigured input devices are not considered for
sleep
/wake
/screensaver-start
/screensaver-stop
events (so I could use my custom translation controller workaround) - Unmapped axes are not considered (obviously I only have axis 0 / 1 mapped on this controller)
- Ability to completely ignore specific input devices (again, for custom controller workaround)
- Per-axis configurable
DEADZONE
I think I've exhausted all my options so this is basically a wishlist post, but I welcome any suggestions, thanks!
Device is a Raspberry Pi 4 2GB, good Canakit PSU, Raspbian buster, kept up to date, nothing too crazy going on (except my monitor is rotated so I need rotation options at the Linux/ES/lr level). - Unconfigured input devices are not considered for
-
Did you try to adjust the deadzone with evdev?
See section "evdev API deadzones and calibration" in https://wiki.archlinux.org/title/Gamepad#Setting_up_deadzones_and_calibration
-
Huh, thanks! I didn't know you could do evdev adjustment; I thought it was entirely the job of the userland to work with the raw events.
Giving it a fuzz and flatness of 255 gets rid of the dozens of events per second... though oddly, events on the axis do very occasionally come through:
Event: time 1723166450.586188, type 3 (EV_ABS), code 2 (ABS_Z), value 153 Event: time 1723166450.586188, -------------- SYN_REPORT ------------ Event: time 1723166522.124771, type 3 (EV_ABS), code 2 (ABS_Z), value 114 Event: time 1723166522.124771, -------------- SYN_REPORT ------------ Event: time 1723167359.792951, type 3 (EV_ABS), code 2 (ABS_Z), value 149 Event: time 1723167359.792951, -------------- SYN_REPORT ------------
I've been watching it for a few hours and the values are within ES's own DEADZONE so it's not causing wakeups, but that's weird since a fuzz of 255 should cover the entire range of the axis (0-255).
Options within ES to manage input devices more would still be welcome, but I think this should be a workable mitigation. Thank you!
BTW, I also tried ordering a different "zero lag" encoder off Amazon (the one with a full-sized USB-B port and black mask on the top layer of the PCB). I figured it was the exact same chipset but hoped maybe they added resistors to zero out axis 2. It just arrived: same chipset as expected, but same noise problem.
-
@rfinnie said in Errant analog noise from controller preventing sleep:
a fuzz of 255 should cover the entire range of the axis (0-255)
Huh? Analog sticks should go from -32767 to 32767 per each axis. I don't own such a Dragonrise (for reasons) but from what I read online it causes more headache than fun.
Do you know about the https://gp2040-ce.info/ project? They use a cheap RP2040 and do also support an analog stick (https://gp2040-ce.info/add-ons/analog). Plus: Whenever something is odd, you can change the source/firmware or ask for help in their forum.
-
a fuzz of 255 should cover the entire range of the axis (0-255)
Huh? Analog sticks should go from -32767 to 32767 per each axis. I don't own such a Dragonrise (for reasons) but from what I read online it causes more headache than fun.
It appears to be variable for evdev events. The Dragonrise axes mostly appear to be unsigned 8-bit with a midpoint at 127, while the last two are signed 2-bit:
$ evdev-joystick --showcal /dev/input/event0 Supported Absolute axes: Absolute axis 0x00 (0) (X Axis) (value: 127, min: 0, max: 255, flatness: 15 (=5.88%), fuzz: 0) Absolute axis 0x01 (1) (Y Axis) (value: 127, min: 0, max: 255, flatness: 15 (=5.88%), fuzz: 0) Absolute axis 0x02 (2) (Z Axis) (value: 144, min: 0, max: 255, flatness: 15 (=5.88%), fuzz: 255) Absolute axis 0x03 (3) (X Rate Axis) (value: 127, min: 0, max: 255, flatness: 15 (=5.88%), fuzz: 0) Absolute axis 0x05 (5) (Z Rate Axis) (value: 127, min: 0, max: 255, flatness: 15 (=5.88%), fuzz: 0) Absolute axis 0x10 (16) (Hat zero, x axis) (value: 0, min: -1, max: 1, flatness: 0 (=0.00%), fuzz: 0) Absolute axis 0x11 (17) (Hat zero, y axis) (value: 0, min: -1, max: 1, flatness: 0 (=0.00%), fuzz: 0)
Compared to a Logitech flight stick I have handy:
$ evdev-joystick --showcal /dev/input/event14 Supported Absolute axes: Absolute axis 0x00 (0) (X Axis) (value: 511, min: 0, max: 1023, flatness: 63 (=6.16%), fuzz: 3) Absolute axis 0x01 (1) (Y Axis) (value: 529, min: 0, max: 1023, flatness: 63 (=6.16%), fuzz: 3) Absolute axis 0x05 (5) (Z Rate Axis) (value: 128, min: 0, max: 255, flatness: 15 (=5.88%), fuzz: 0) Absolute axis 0x06 (6) (Throttle) (value: 255, min: 0, max: 255, flatness: 15 (=5.88%), fuzz: 0) Absolute axis 0x10 (16) (Hat zero, x axis) (value: 0, min: -1, max: 1, flatness: 0 (=0.00%), fuzz: 0) Absolute axis 0x11 (17) (Hat zero, y axis) (value: 0, min: -1, max: 1, flatness: 0 (=0.00%), fuzz: 0)
Do you know about the https://gp2040-ce.info/ project? They use a cheap RP2040 and do also support an analog stick (https://gp2040-ce.info/add-ons/analog). Plus: Whenever something is odd, you can change the source/firmware or ask for help in their forum.
Sounds nice, I'll keep it in mind for a future project. (If you're curious, I have an Arcade1Up Class of 81 Deluxe cabinet which I'm just doing the bare minimum to make it a functional RetroPie cabinet: replace the LVDS driver and encoder, add a sound amp, replace the marquee lighting. But since this cabinet has a flat combination LCD and input panel, I eventually plan on building my own panel to replace the stock layout.)
-
@rfinnie I guess the min/max values are not a strict specification, thus I said "should". It depends on brand/model as I learned (mine Logitech Rumblepad and a knock-off Switch/XBox controller report in the "should" range).
On a tangent: The Arcade'81 looks nice and gives you at least enough space to add a subwoofer. I added an external subwoofer 6.5" later to my custom bartop which made the games even more fun to play. In any case: Happy tinkering!
But back to your initial request/idea. Maybe @pjft can comment on that, if a or which suggested change (see first post) would be accepted in the ES source tree.
Contributions to the project are always appreciated, so if you would like to support us with a donation you can do so here.
Hosting provided by Mythic-Beasts. See the Hosting Information page for more information.