Making a character go from walking to running by pressing the input twice

What way is there that I can do this?

You need to check the state of the mouse each frame (is pressed, is held or is release) and you’re looking for a pattern of press → release → hold or hold → release → hold that takes place in x seconds. Because releasing a key can only be done after pressing it, you’re really looking for something like this: release → hold. I would do this, by setting a counter every time the player releases the key (Input.GetKey/ButtonUp) to some seconds ( 0.1 seconds would be good I think), each frame I would substract the deltaTime and while it’s not 0, I would check for a hold (Input.GetKey/Button)

You could keep track of when the input has pressed for the last time; just store Time.time or Time.realtimeSinceStartup into a variable. Then each time the input is pressed, compute the duration since the last time it has been pressed. If the duration is less than a given threshold, consider it as a double press. Then you would need to adjust the character speed and animation accordingly.

I’m sorry, this is a brilliant response but it feels like I asked a question beyond my capabilities at this point and don’t fully understand what you’re saying. Is it okay if you could go into more detail with this? I’m with you up to the point where you subtract the deltaTime each frame. Thank you

You set a float value to let’s say 0.1, this is your cooldown period, if you release then press the same button in this timefram you will get a double press. So you have a value set to 0.1 each time you release the forward key, now we want to make this counter functional, so we want to substract the time that passed since the last frame. This can be done by yourCounterNameHere - Time.deltaTime;
now your variable is 0.1 at the start and it will reach 0 in about 0.1 seconds (Time.deltaTime won’t reach exactly 0, it will most likely be -0.03 or something, so after the substraction you need to check if it’s less than 0 and set it to 0 if yes)
Now we need the last if statement
if (buttonIsHeldDown && counter > 0)
run

This whole thing looks like this in pseudocode:

counter := your counter
cooldown := max time between key presses to count  as a double press
if walkButtonIsReleased then
    counter = cooldown
endif

if counter > 0 then
    if walkButtonIsPressed then
        You are running
    endif
    counter -= Time.deltaTime
    if counter < 0 then
        counter = 0
    endif
endif
1 Like

Okay so my code looks like this after reading that, and honestly this looks a lot like the code I did after the first reply you wrote. This all makes sense in my head. Am I missing something?

if (Input.GetKey(KeyCode.D))
        {
            moveVelocity = moveSpeed;
           
        }
        if (Input.GetKeyUp(KeyCode.D))
        {
            runThresholdCounter = runThreshold;

            if (runThresholdCounter > 0)
            { if (Input.GetKey(KeyCode.D))
                    moveVelocity = runSpeed;
            }
            runThresholdCounter -= Time.deltaTime;
            if (runThresholdCounter < 0)
            {
                runThresholdCounter = 0;
            }
        }

Yes, first of all, you don’t want to put everything inside Input.GetKeyUp, only the runTresholdCounter = … line
then you want to have everything else be in if runTresholdCounter > 0 because then you wont substract Time.deltaTime every time, only when needed

Okay, so I think I’ve just put the runThresholdCounter = runThreshold in the GetKeyUp statement. and It looks like I’ve put everything inside the runThresholdCounter > 0 statement here. Is there anything else I’m missing? Or is there something else I overlooked?

if (Input.GetKey(KeyCode.D))
        {
            moveVelocity = moveSpeed;           
        }
        
        if (Input.GetKeyUp(KeyCode.D))
        {
            runThresholdCounter = runThreshold;
        }
       
        if (runThresholdCounter > 0)
        {
            if (Input.GetKey(KeyCode.D))
            { 
                moveVelocity = runSpeed;
            }
                runThresholdCounter -= Time.deltaTime;
                if (runThresholdCounter < 0)
                {
                    runThresholdCounter = 0;
                }
        }

Yeah that’s it, for the matter of fact if you look at the pseudocode I posted it should be the same

1 Like

Using the ‘Input.GetKey(KeyCode.D)’ more than once one into another doesn’t make sense, since them will be all true or false in a single loop.

I agree, I think if he removed the Input.GetKey from within the “if (runThresholdCounter > 0)” if-statement he should be fine.