How do I detect simultaneous gamepad inputs ?

0 favourites
  • 12 posts
From the Asset Store
Supports keyboard, mouse and gamepads. Supports several gamepads at once.
  • Hi,

    I'm having a problem. See, I knew keyboards couldn't sometimes detect multiple simultaneous key inputs but I seem to be meeting a similar problem with an Xbox Gamepad as well oO

    Here is a very simplified version of the problem I've encountered :

    Try inputting two buttons at the same time with a gamepad : you should in theory witness in the debug box "pressed" twice or "--" twice (for released buttons). Except no, oftentimes these words don't come in pairs, meaning one trigger hasn't been detected. Even if I were pressing the two buttons at the exact same frame I don't know why this would happen (and I'd be very surprised if I were able to do this consistently anyway)

    Is there a workaround around this ? Is it a software (C2) or hardware (controller) problem ? I'm developping a run n' gun game a la Metal Slug, you NEED to be able to detect several inputs simultaneously or quasi-simultaneously (such as Crouch + Shoot, Jump + Shoot, etc).

    Thanks in advance for your help. It is really troubling me :/

  • Back from a big holiday travel. This is still bugging me. Can someone please help me find a workaround to deal with this issue ?

    Thanks in advance

  • "On button pressed" is a triggered event. It's triggered only once for every button pressed.

    I think what happens is when you press 2 buttons quickly enough, this event is triggered once for both buttons.

    The problem is, Gamepad.LastButton(0) only stores one of the buttons codes, not both.

    The best you can do is this:

    Here is the output if I press two buttons quickly:


    Button: 4

    Button: 5


    Unfortunately, the same happens if I am holding button 4 and then press button 5.

    So this solution is not very reliable.

    I would recommend not to use "On button pressed" event at all.

    Detect buttons pressed using testing events "Is button down" or "Is button index down". You can add "System->Trigger once" condition if necessary.

  • Thank you dop2000 for your help

    Your workaround is very interesting, but to me the biggest hurdle (in addition to the one you already mentioned) is that it doesn't work at all with the second trigger : the "On any button released". Because of the lack of appropriate property in the Gamepad object.

    Even if I get rid of the triggers altogether like you suggest in your last part it's still very complicated.

    I'm trying to think of something but I feel like I'd have to track the state of each button at every frame, as well as their previous state from the last frame, to see if a button has changed state etc etc... that sounds like a loooot of work. And a looooot of variables to store all these data.

    Or if I manage to know when several buttons are released, I could store the IDs of these buttons in a Text variable, separated with "/".

    I'd use the tokenat function to split the variable later.

    It's almost like building a virtual controller from scratch... Am I the only one to find it incredibly impractical ?

    What surprises me is that it looks like a pretty basic fonctionnality... I mean, it's common to mash several buttons at the same time. This trigger is almost useless, limited as it is

    Maybe I'm just watching it the wrong way.

  • Hi Semoreh,

    I was just passing by, reading your post and I thought of a potential solution :

    How about adding a global variable that stores inputs and triggers what your button should be triggering by using an event ?

    For example :

    on "A" (any button) pressed => store "whatever "A" should do" in your general variable

    compare general variable value : if "value" = "A" => trigger action X

    Or maybe even better, you could associate every button on your pad with a boolean variable that triggers when the button is pressed, and associate your events with the booleans and not with the actual buttons ?

    Not sure that would work in practice, but what do you think about that ?

    Edit : You could even use events like "on variable A and variable B boolean = true" to trigger events while 2 or more specific buttons are pressed (simultaneously, how you want it to be)

  • hi Diablo ! Thanks for stoping by !

    I already have something pretty similar right now. I have :

      On any button pressed >> check if said button is mapped to an action >> toggle boolean variables of this action (ex : "JumpInput" and "JumpInputHold") On any button released >> check if said button is mapped to an action >> toggle "hold" boolean variable of this action

    It works very well, because I can let the player choose his own mapping entirely.

    Except now I've realised the "On any button pressed" trigger didn't work as intended ^^'

    It seems the only obvious solution is, like you say, to associate every button with a boolean. It's pretty tedious but I've been testing this early draft and it works well with my A, B, X and Y buttons on my Xbox360 controller :

    It's pretty tedious though, and I'd better cross my fingers nobody tries to use a weird controller with more buttons than usual :/

  • What I would try if I were creating something similar, is store the tickcount at the time of the button press.

    So I'd probably have a dummy sprite object with variables I can set, like sprite.button1tick, sprite.button2tick

    Then when button is pressed store the tickcount to corresponding variable.

    Then have an event that checks if one of the buttons is down, or both, etc.. and also check if their tick variables are within a certain range.

    for example: abs(sprite.button1tick-sprite.button2tick) < fps*0.25 & (tickcount-sprite.button1tick <= fps*0.25 | tickcount-sprite.button2tick <= fps*0.25) do action for two button press.

    else (tickcount-sprite.button1tick > fps*0.25 & button is pressed & sprite.button1state = 0) do action for 1 button press and set button1state to 1

    if button 1 isn't pressed, set button1state to 0.

    if button1state = 0 and button pressed, set button1tick to tickcount.

    something along those lines..

  • Interesting, but I don't like the "unprecise" aspect of the tick range. I'll stick with my solution so far, but thanks

    It's impressive that we're proposing all these colorful workarounds when it should really be a basic fonctionnality of construct's gamepad object

  • I was worried about the fact my Keyboard triggers may be broken too and would need to be reworked, but surprisingly they're not. You can input several keys at the same time, and one normal trigger is enough to detect them all. Maybe it's just that the detection range is shorter, so it's harder to "mix" them ?

    (of course at one point my keyboard stops detecting too many simultaneous inputs, but I know it's a mechanical limit)

    Here is a V3 of my capx with this result :

  • Try Construct 3

    Develop games in your browser. Powerful, performant & highly capable.

    Try Now Construct 3 users don't see these ads
  • Check this out: ... .capx?dl=0

    I think I managed to make a nice system that tracks the state of all buttons (Pressed->Hold->Released->Nothing) and doesn't use the "On button pressed/released" events.

  • dop2000

    Oh ! I love your system, the use of the For Loop and the Dictionary, much more compact !

    There's a slight difference with my previous system : when a button is pressed, I start "holding" on the same frame it is pressed, when you only start "holding" one frame later since you can't have PRESSED and HOLD at the same time in the Dictionary.

    That said, I'll probably adapt your system a bit and use it, it is much less tedious to write so I can more easily add more buttons

    Also, I love these kinds of expressions :

    [quote:12h3srhn]Set Keyname to loopindex=0 ? "A" : loopindex=1 ? "B" : loopindex=2 ? "X" : "Y"

    What's the name of this advanced way of writing ? Is it Java ? If so I need to give it a shot, it's very convenient.

    (isn't it missing a "loopindex = 3 ?" before the "Y" ? Maybe there's a difference because it is the last one)

    Thanks a bunch \o/

  • Glad to help!

    (loopindex=0 ? "A" : "Z") means if loopindex=0 then "A", otherwise "Z".

    It's called ternary operator, I think it exists in many languages.

    You can nest them one inside another, and yes "Y" at the end basically means "anything else". You can change it to this:

    Set Keyname to loopindex=0 ? "A" : loopindex=1 ? "B" : loopindex=2 ? "X" : loopindex=3 ? "Y" : "other"

    Of course if you have 20 buttons, this expression will become quite long and messy.

    You may use a different method, for example pick name from a string like this "A,B,X,Y,,,DpadUp,DpadDn,....." using TokenAt(KeyNames, loopindex, ",").

Jump to:
Active Users
There are 1 visitors browsing this topic (0 users and 1 guests)