• Hello [name]! Thanks for joining the GMC. Before making any posts in the Tech Support forum, can we suggest you read the forum rules? These are simple guidelines that we ask you to follow so that you can get the best help possible for your issue.

Linux Gamepads are not working on Linux (Ubuntu)

thom

Member
It appears that gamepads aren't working properly on Linux (Ubuntu). After some tests I have noticed the following:
-The gamepad slot used is not in the 0-11 range, but will start at 12.
-The buttons of XInput (Xbox) gamepads are also assigned wrong on Linux, for example if you press the "LT" button it detects "right stick x+", while PS4 controllers have the right buttons assigned.
-Axis values are wrong.
-Remapping the buttons using gamepad_test_mapping() does not work, the game will crash if you try it on Linux.
 
Last edited:

Yal

🐧 *penguin noises*
GMC Elder
I've also noticed this myself. Didn't notice the "starts at 12" thing, though, that might help solving my issues.

-Remapping the buttons using gamepad_test_mapping() does not work, the game will crash if you try it on Linux.
The manual claims this isn't supported, so that makes sense.

-The buttons of XInput (Xbox) gamepads are also assigned wrong on Linux, for example if you press the "LT" button it detects "right stick x+", while PS4 controllers have the right buttons assigned.
This seems to be a issue on the driver level (below GM), I debugged my controller using the jstest-gtk program and some buttons/axes were mixed up (like the right stick horizontal position being controlled by one of the shoulder buttons).
 

Yal

🐧 *penguin noises*
GMC Elder
I did some experimentation, and I found out the following:
  • For me, gamepads started being found at slot 20. (0-indexed) Thus, the first gamepad slot is machine-dependent. It definitely doesn't stick to the range specified in the manual.
  • Gamepad layout found by GM doesn't match GM's gamepad_ constants nor the layout reported by jstest-gdk.
I've submitted a bug report on this.
 

Yal

🐧 *penguin noises*
GMC Elder
The tutorial also claims that only slots 0-11 will be used (with provisions for functionality being slightly different on Android but no other platform differences pointed out)... and this wasn't the case with neither my nor @thom's testing. In fact, both of us exclusively got numbers outside of this range.

1593805260859.png

Either the manual or the code should be updated to clarify this (preferably the code, since it's consistent for every other platform - at least if you trust the wording in the manual; and I'd rather have a notice that it's not supported at all for the linux target than having to handle all the "under the hood" stuff myself with no documentation of how it works).

In my case, even if I'd blindly use the correct ID from an asynchronous event, I need to know what the valid range of devices are for a bunch of different things (controller customization being one of them - a potentially infinite menu wouldn't fit on the screen).
 

Nocturne

Friendly Tyrant
Forum Staff
Admin
Yup, I agree, but I just wanted to point out that with the async event, you can at least get a pad index without having to worry about the actual index value.
 

Yal

🐧 *penguin noises*
GMC Elder
It's good to know it's an option, it just wouldn't work particularly well with the way my game is structured (gameplay and menu objects are completely separated, so I'd need to duplicate the asynchronous events over a large amount of objects; right now I pretend to read gamepad input everywhere, but the script that actually reads it does nothing for an unplugged device, so it never generates events - thus nothing needs to be aware of whether a gamepad is plugged in or not and the logic gets a lot simpler. I still display the connectedness status to the player where needed, but under the hood there's no difference between a disconnected gamepad and a gamepad nobody is pressing buttons on for 99% of objects). Overall it feels safer to check the current status when needed than to keep track of changes and intuit the state, too... there's always that risk of desync.

But yeah, my complaint boils down to "the reality and the manual doesn't match". Since there's a lot of emphasis on the 0-11 limit, it definitely looks like a bug. I've always assumed that whatever the device enumeration is host-side, GM abstracts it away so the gamepads are mapped to slot 0-11 in the order they're found... on my linux computer, the gamepads get mapped to device files with numbers 1 and 2, so I'm completely clueless as to why the internal numbering would jump to 20 joystick-side.
 

kburkhart84

Firehammer Games
@Nocturne I agree that this is a pretty big concern. I've never messed with testing my input system on Linux or Mac...but since it is 100% gml it should in theory work fine. However...since the manual is pretty clear that there is only gamepad indices 0 - 11, that is all I've set my input system to use. Instead of relying on async events, it loops through whatever gamepads are connected, but won't go over 11. Do you think you could clarify with the internal team what may be going on there? It seems to me to be either a bug or incorrect documentation.

Honestly, the way the documentation makes it out makes the most sense to me. It is a set of known values, with the first 4 corresponding to XInput, and the next 8 being DInput(well....non-XInput at the least). I would have thought based on this that the engine is polling all gamepads that are connected, and simply assigning them IDs from 0 - 11. But the above information, where someone saw ID 20.... that seems like a bug to me.
 
  • Like
Reactions: Yal

Yal

🐧 *penguin noises*
GMC Elder
Honestly, the way the documentation makes it out makes the most sense to me. It is a set of known values, with the first 4 corresponding to XInput, and the next 8 being DInput(well....non-XInput at the least). I would have thought based on this that the engine is polling all gamepads that are connected, and simply assigning them IDs from 0 - 11. But the above information, where someone saw ID 20.... that seems like a bug to me.
Speaking of this, clarifying which platforms treats XInput as a special case and which ones treat all 11 slots the same could also be nice - I'm assuming only Windows has special XInput treatment and the gamepads just have a fallback on the other platforms? (When testing with a DInput and an XInput gamepad on my Linux machine, they were jumbled together in adjacent slots 20 and 21)

(Also, if ranges outside 0-11 are to be expected, getting new read-only global variables gamepad_first and gamepad_last for the slot range could be useful for all potential iteration needs - the thing where android phones can't use slot 0 because it's used by generic bluetooth devices could also benefit from this)
 

kburkhart84

Firehammer Games
Speaking of this, clarifying which platforms treats XInput as a special case and which ones treat all 11 slots the same could also be nice - I'm assuming only Windows has special XInput treatment and the gamepads just have a fallback on the other platforms? (When testing with a DInput and an XInput gamepad on my Linux machine, they were jumbled together in adjacent slots 20 and 21)

(Also, if ranges outside 0-11 are to be expected, getting new read-only global variables gamepad_first and gamepad_last for the slot range could be useful for all potential iteration needs - the thing where android phones can't use slot 0 because it's used by generic bluetooth devices could also benefit from this)
This all makes sense to me. If it were a documented feature that way, I could easily code my input system accordingly. Right now I'm depending on 0 - 11.

Honestly, I'm thinking that since Linux is simply a market with less influence, they just haven't gotten around to fully integrating the whole 0 - 11 indices mapping for it, rather they are just using some number the OS is giving them. To me, that's a bug. But as you say, if it IS intentional, then something should be done either to verify the range of IDs, or to at the least document what is going on. Otherwise, they should finish the code making it function equally to Windows where possible, and documenting when they can't(like XInput for example).
 

Yal

🐧 *penguin noises*
GMC Elder
they just haven't gotten around to fully integrating the whole 0 - 11 indices mapping for it, rather they are just using some number the OS is giving them.
The "on android, index 0 is used by bluetooth devices and can't be used" thing also smells of this... there's no conceptual reason for the slots to not start at 0 and go up to <max supported value>, fully abstracting the OS's mapping of the devices.
 

kburkhart84

Firehammer Games
The "on android, index 0 is used by bluetooth devices and can't be used" thing also smells of this... there's no conceptual reason for the slots to not start at 0 and go up to <max supported value>, fully abstracting the OS's mapping of the devices.
100% agree...this is why I believe they simply haven't "finished" coding these things anywhere except for Windows. There is no reason we should have to care that index 0 is stuck that way, since theoretically that is on the OS side, not on the GML side. I don't necessarily expect full feature parity between all platforms...but this is one of those things that should in general match up, except maybe where XInput is concerned. So I would expect it to be something where on non-windows platforms, devices 0 - 3 maybe don't function(as they were reserved for XInput). The reason I would agree with that is because the coding internally for devices 0 - 3 isn't the same as 4 - 11, so I could understand if it was easier for them to simply not do anything for 0 - 3 on other platforms, for consistency sake. The alternative would be to use different functions between XInput and DInput, but I don't think that's necessary.
 

COWCAT

Member
I've just sent a support ticket about this because Xbox controller support is still broken.
Personally I don't mind the slot "issue", I already did like Nocturne mentioned.
But the mapping is totally wrong. The left stick is between 0 and 1 for both axis but it's between -1 and 1 on Windows. The right stick has one axis stay at 0, no matter how you move it. Some buttons don't work at all like gp_start. Pressing LT acts like the right stick...

Will you let know if support has a solution to mitigate these issues. I'm just surprised to see it's still not working correctly two years later.
The Xbox controllers are the most used, personally I can't release a Linux version in this state.
 

Juju

Member
Also if anything is broken you can come poke us on the Discord server and we'll try to get it fixed. You don't need to use all the fancy features too, we offer improved direct-and-simple gamepad checkers that take advantage of our backend gamepad support.
 

COWCAT

Member
Have you tried https://www.jujuadams.com/Input/#/5.1/ ? It contains ~1600 mappings of weird and exotic gamepads (from those that costs as much as kidney to those which are for 1$ on aliexpress). This solves lot of issues, and adds tons of new features.
Wait a minute.
I never had to do anything like this on Windows and Mac exports. Why would this be needed?
And as far as I know the mapping function doesn't work on Linux (that's what was said in the topics I've checked anyway)

Also: I'm talking about the most popular PC gamepad ever here, the Xbox One/Series controller! (or Xbox 360 because it's practically the same) There shouldn't be a need to do anything specific to support it.

EDIT: This looks like an extension? I also don't want to use extensions as much as possible because I do multiplatorm, consoles included. So I want to keep the same code working for all platforms.
 
Last edited:

DanC

GMC Member
GameMaker Dev.
I've just sent a support ticket about this because Xbox controller support is still broken.
Personally I don't mind the slot "issue", I already did like Nocturne mentioned.
But the mapping is totally wrong. The left stick is between 0 and 1 for both axis but it's between -1 and 1 on Windows. The right stick has one axis stay at 0, no matter how you move it. Some buttons don't work at all like gp_start. Pressing LT acts like the right stick...

Will you let know if support has a solution to mitigate these issues. I'm just surprised to see it's still not working correctly two years later.
The Xbox controllers are the most used, personally I can't release a Linux version in this state.
I just tested the Linux controller mappings with a handful of Xbox controllers I happen to have lying around and your behaviour matches that of a "Day One" marked controller. The later v2 controller and (knockoff) 360 controller seem to have the correct mappings (aside from the Xbox/Home button being mapped to select rather than the select button).
 

COWCAT

Member
Oh wow that's weird. My controllers are definitely not "day one", they're from Xbox One S devkits.
I will try with a Xbox Series controller I just got.
Anyway, support replied with the following:

" The issue is the default pad mapping as supplied by Steam/SDL2 for when on Ubuntu - you should use GameMaker's own gamepad mapping functions to create your own override for your game(s) in order to fix this in the short-term, but we will look to update to the current version of their database in a future GM release. "

So as often, I guess it's a matter of Linux export not being used much compared to Windows, Mac and mobile exports because I never had to mess with that before.
So I guess the information that "gamepad_test_mapping" crashes on Linux is wrong?
Will attempt and see.
 

gnysek

Member
I also don't want to use extensions as much as possible because I do multiplatorm, consoles included. So I want to keep the same code working for all platforms.
This extension is multiplatform already, consoles including - as JuJu helped to ship many console games, so it's based on his best knowledge what can go wrong on each possible platform. It even supports Switch JoyCons on non-Switch platforms, where by default they returning wrong buttons (similar to your current Linux problem). There are same functions to work on ALL platforms, so it's one code to rule them all.

Of course you can report to YYG, that there's issue with gamepads on Linux - but I with my current expirience, even for such easy job as support for gamepad/keyboard on Windows only, Input is best choice (for example - it have auto-switch function between keyboard / gamepad / mouse, or ability to re-bind buttons by players).
 

Juju

Member
Why would this be needed?
Because YYG haven't maintained their Linux gamepad implementation.
as far as I know the mapping function doesn't work on Linux
We don't use the native mapping function, we have our own (better) solution that reads raw input values.
There shouldn't be a need to do anything specific to support it.
I agree! But until YYG fix their gamepad support...
This looks like an extension?
It's a library not an extension. All the code is open source and you can read it and edit it however you want.
I also don't want to use extensions as much as possible because I do multiplatorm
Extensions aren't necessarily single platform only. Input is written in 100% native GML code so it will compile for every platform that GameMaker supports.
I want to keep the same code working for all platforms.
That is the entire point of Input, yes. If you scroll down on the front page of the documentation you'll see this:

1664366132812.png

Input has been used in countless projects. As an example, around this time last year, the Samurai Gunn 2 team got so frustrated with the out-of-the-box GameMaker support for gamepads that they replaced their entire gamepad solution with Input. An older version of Input powers Shovel Knight: Pocket Dungeon cross-platform. I also implemented Input for Poinpy at the start of 2021, though we ended up turning off gamepad support on mobile because the gameplay didn't suit gamepad controls by the end of development (Ojiro wanted gameplay to be more tactile than what a gamepad permits).
 

COWCAT

Member
Alright, I see your point but at this stage of development (my game is finished and I'm porting it now) I really don't want to make more changes like this, potentially breaking, JUST for supporting ONE controller for Linux.
For now, I'm stuck exactly at what people reported: gamepad_test_mapping crashes on Linux. Investigating.

EDIT: Yep gamepad_test_mapping() is definitely broken on Linux...it always crashes. Sigh.
If your library uses only GML code I wonder how you can get past this issue.

EDIT 2: I've also tested with a Xbox Series gamepad and I get the exact same results with the axis values totally wrong etc
I have no idea why @DanC doesn't get the same results.

I have replied to the support ticket with a project to demonstrate the crash, wait & see.
 
Last edited:

kburkhart84

Firehammer Games
I also have my input system I use(in my sig). I've never dived into Juju's Input but it seems similar enough to mine, with a few things handled differently. One thing that mine does not do at all(on purpose in fact) is trying to handle the whole mapping thing. Instead, mine just uses the raw axis and button values(still GML, just not using gp_constants for the axes/buttons). This means that I don't know for sure that axis 0 is the X axis(though it is most often). But it DOES give me full access to any and every input on these devices. The APIs actually support up to 10 axes, 32 buttons, and 4 separate POV hats. And the mapping code and gp_constants for that does not have any of that stuff. It is more geared to traditional gamepads. My system supports non-traditional stuff too. I don't know if and how Juju's handles that, I would guess it has a way to do it as well.
 
Top