Sandbox: Difference between revisions

From Minecraft Parkour Wiki
Content added Content deleted
m (Blanked the page)
Tag: Blanking
mNo edit summary
Line 1: Line 1:
[[File:0t sprintjump graph.png|thumb|600x600px|Movement formulas applied to a 3b jump.]]
The player's movement can be accurately calculated with [https://en.wikipedia.org/wiki/Sequence sequences].

The following formulas come from analyzing the game's [[SourceCode|source code]].



Note that these formulas are '''not exact''', due to how [https://en.wikipedia.org/wiki/Floating-point_arithmetic floats] are computed. When used for calculations, only the first 4-6 decimals should be considered accurate. For a completely accurate simulation, you would need to replicate the source code.



In this article, we only consider standard movement, and ignore mechanics specific to certain blocks.



You will find further documentation of movement physics in these articles:

* [[Soulsand]]
* [[Ladders and Vines|Ladders and Vines]]
* [[Slime Block|Slime Blocks]]
* [[Cobweb|Cobwebs]]


'''Note:''' Minecraft's coordinate system is oriented differently: 0° points towards "positive Z", and 90° points towards "negative X". We choose to work in the standard coordinate system to make calculations more intuitive. If need be, we can simply invert the X axis to match Minecraft's coordinate system.

<br />

== Vertical Movement ==

===Jump Formula===

*<math>V\displaystyle _{Y,1} = 0.42</math>
* <math>V\displaystyle _{Y,t} = \left (V_{Y,t-1} - \underset{gravity}{0.08} \right ) \times \underset{drag}{0.98}</math>


:If <math display="inline"> \left | V\displaystyle _{Y,t} \right | < 0.005 </math>, <math display="inline">V\displaystyle _{Y,t}</math> is set to 0 instead (the player's height doesn't change for that tick)

:In 1.9+, it's compared to 0.003 instead.



'''Notes'''

*<math display="inline"> V\displaystyle _{Y,0}</math> isn't assigned a value because it has no importance. By convention, the 0<sup>th</sup> tick corresponds to the player's initial velocity before jumping.
*<math display="inline"> V\displaystyle _{Y,1}</math> corresponds to the initial jump motion. It is increased by 0.1 per level of [[Status Effects|Jump Boost]]
*Terminal velocity is -3.92 m/t
*When the player collides vertically with a block, vertical momentum is cancelled and only the acceleration is left.



===Vertical Position===

: To get the position on a given tick, you simply need to sum <math display="inline">V\displaystyle _{Y}</math>

:<math display="inline">Y(n) = \sum_{t=1}^{n} V_{Y,t}</math>


===Jump duration===

:The '''duration''' of a jump is the number of ticks between jumping and landing.

:It also corresponds to the period of that jump's cycle when performed repeatedly.

:This notion is linked to the notion of [[Tiers]].

:{| class="wikitable"
!Description
!Duration
|-
|Flat Jump
|12 t
|-
|3bc Jump
|11 t
|-
|<nowiki>+0.5 Jump</nowiki>
|10 t
|-
| +1 Jump
|9 t
|-
|2.5bc Jump
|6 t
|-
|2bc Jump
|3 t
|-
|1.8125bc Jump
|2 t
|}



=== Source code ===
'''from [[SourceCode:EntityLivingBase|EntityLivingBase]]'''

: <syntaxhighlight lang="java">
/* Code unrelated to vertical movement is cut out */

protected float getJumpUpwardsMotion(){
return 0.42F;
}


protected void jump()
{
this.motionY = this.getJumpUpwardsMotion();
if (this.isPotionActive(Potion.jump))
{
this.motionY += (this.getActivePotionEffect(Potion.jump).getAmplifier() + 1) * 0.1F;
}
this.isAirBorne = true;
}


public void moveEntityWithHeading(float strafe, float forward)
{
... /* also moves the player horizontally */

this.motionY -= 0.08;
this.motionY *= 0.98;
}


public void onLivingUpdate()
{
if (this.jumpTicks > 0)
--this.jumpTicks;

if (Math.abs(this.motionY) < 0.005D)
this.motionY = 0.0D;


if (this.isJumping)
{
... /* different if in water or lava */

if (this.onGround && this.jumpTicks == 0)
{
this.jump();
this.jumpTicks = 10; //activate autojump cooldown (0.5s)
}
}
else
{
this.jumpTicks = 0; //reset autojump cooldown
}

...
this.moveEntityWithHeading(this.moveStrafing, this.moveForward);
}

</syntaxhighlight>

== Horizontal Movement ==

Horizontal Movement is a bit more complex than Vertical Movement, as it relies on many more factors: player actions, direction, and ground slipperiness.

On every tick, the game does these three steps:
# Acceleration is added to the player's velocity.
# The player is moved (new position = position + velocity).
# The player's velocity is reduced to simulate drag.

We'll start by introducing Multipliers in an effort to make formulas more readable.


=== Multipliers ===

: '''Movement Multiplier''' (See [[45 Strafe|45° Strafe]])


:: <math>M_{t} = \begin{Bmatrix}1.3 & \textrm{Sprinting} \\ 1.0 & \textrm{Walking}\\ 0.3 & \textrm{Sneaking}\\ 0.0 & \textrm{Stopping} \end{Bmatrix} \times \begin{Bmatrix}0.98 & \textrm{Default}\\ 1.0 & \textrm{45° Strafe} \\ 0.98 \sqrt{2} & \textrm{45° Sneak} \end{Bmatrix}</math>


: '''Effects Multiplier''' (See [[Status Effects]])


:: <math>E_{t} = (\underset{Decreases \; by \; 15\% \; per \; level \; of \; Slowness}{\underset{Increases \; by \; 20\% \; per \; level \; of \; Speed}{\underbrace{\left ( 1 + 0.2\times Speed \right ) \: \times\: \left ( 1 - 0.15\times Slowness \right )}}} \geq 0</math>


: '''Slipperiness Multiplier''' (See [[Slipperiness]])


:: <math>S_{t} = \begin{Bmatrix}0.6 & \textrm{Default}\\ 0.8 & \textrm{Slime}\\ 0.98& \textrm{Ice} \\ 1.0 & \textrm{Airborne} \end{Bmatrix}</math>
:

<br />
=== Linear Formulas ===

: These simplified formulas only apply to linear movement (no change in direction).
:While this condition might seem very restrictive, these formulas are very useful to analyze conventional jumps and momentum
:We'll later expand on these formulas by including angles.
:<br />'''Definition''':
:* <math>V_{H,0}</math> is the player's initial speed (default = 0).
:* <math display="inline">V_{H,t}</math> is the player's speed on tick <math display="inline">t</math>.



: '''Ground Speed''':

::<math>V_{H,t} = \underset{Momentum}{\underbrace{\underset{ }{V_{H,t-1} \times S_{t-1} \times 0.91 }}} \: + \: \underset{Acceleration}{\underbrace{0.1 \times M_{t} \times E_{t} \times \left (\frac{0.6}{S_{t}} \right )^{3}}} </math>


: '''Jump Speed''':

::<math>V_{H,t} = \underset{Momentum}{\underbrace{\underset{ }{V_{H,t-1} \times S_{t-1} \times 0.91 }}} \: + \: \underset{Acceleration}{\underbrace{0.1 \times M_{t} \times E_{t} \times \left (\frac{0.6}{S_{t}} \right )^{3}}} + \underset{Sprintjump \; Boost}{\underbrace{\begin{Bmatrix}0.2 & \textrm{Sprinting}\\ 0.0 & \textrm{Else}\end{Bmatrix} }}</math>


: '''Air Speed''':

::<math>V_{H,t} = \underset{Momentum}{\underbrace{\underset{ }{V_{H,t-1} \times S_{t-1} \times 0.91 }}} \: + \: \underset{Acceleration}{\underbrace{\underset{ }{0.02 \times M_{t}}}} </math>


=== Complete Formulas ===

: Let's introduce two more variables:
:*<math display="inline"> D_{t} </math> , The player's Direction in degrees (defined by their inputs and rotation)
:* <math display="inline"> F_{t} </math> , The player's Facing in degrees (defined by their rotation only)


In reality, angles aren't as simple as that, as there are a limited number of significant angles (see [[Facing and Angles]]).

For the purpose of simplicity, we'll ignore this fact.




: '''Definition''':
:* <math display="inline">V_{X,0}</math> and <math display="inline">V_{Z,0}</math> correspond to the player's initial velocity.
:* <math display="inline">V_{X,t}</math> and <math display="inline">V_{Z,t}</math> correspond to the player's velocity on tick <math display="inline">t</math> <br /> '''Ground Velocity''':

::<math>V\displaystyle _{X,t} = \underset{ }{V\displaystyle _{X,t-1} \times S_{t-1} \times 0.91 } \: + \: 0.1 \times M_{t} \times E_{t} \times \left (\frac{0.6}{S_{t}} \right )^{3} \times \sin (D_{t}) </math>
::<math>V\displaystyle _{Z,t} = \underset{Momentum}{\underbrace{\underset{ }{V\displaystyle _{Z,t-1} \times S_{t-1} \times 0.91 }}} \: + \: \underset{Acceleration}{\underbrace{0.1 \times M_{t} \times E_{t} \times \left (\frac{0.6}{S_{t}} \right )^{3}}} \times \cos (D_{t}) </math>

: '''Jump Velocity''':

::<math>V\displaystyle _{X,t} = \underset{ }{V\displaystyle _{X,t-1} \times S_{t-1} \times 0.91 } \: + \: 0.1 \times M_{t} \times E_{t} \times \left (\frac{0.6}{S_{t}} \right )^{3} \times \sin (D_{t}) + \begin{Bmatrix} 0.2 & \textrm{Sprinting}\\ 0.0 & \textrm{Else}\end{Bmatrix} \times \sin (F_{t}) </math>
::<math>V\displaystyle _{Z,t} = \underset{Momentum}{\underbrace{\underset{ }{V\displaystyle _{Z,t-1} \times S_{t-1} \times 0.91 }}} \: + \: \underset{Acceleration}{\underbrace{0.1 \times M_{t} \times E_{t} \times \left (\frac{0.6}{S_{t}} \right )^{3}}} \times \cos (D_{t}) + \underset{Sprintjump \; Boost }{\underbrace{\begin{Bmatrix} 0.2 & \textrm{Sprinting}\\ 0.0 & \textrm{Else}\end{Bmatrix} \times \cos (F_{t})}} </math>


: '''Air Velocity''':

::<math>V\displaystyle _{X,t} = \underset{ }{V\displaystyle _{X,t-1} \times S_{t-1} \times 0.91 } \: + \: 0.02 \times M_{t} \times \sin (D_{t}) </math>
::<math>V\displaystyle _{Z,t} = \underset{Momentum}{\underbrace{\underset{ }{V\displaystyle _{Z,t-1} \times S_{t-1} \times 0.91 }}} \: + \: \underset{Acceleration}{\underbrace{\underset{}{0.02 \times M_{t}}}} \times \cos (D_{t}) </math>

=== Stopping Conditions ===

: Horizontal speed is set to 0 if the player hits a wall, or if the speed is considered to be negligible.


: '''Wall Collision''':

:: If the player hits a X-facing wall, then <math display="inline">V\displaystyle _{X,t}</math> is set to 0 and the player is placed against the wall.
:: If the player hits a Z-facing wall, then <math display="inline">V\displaystyle _{Z,t}</math> is set to 0 and the player is placed against the wall.


: '''Negligible Speed Threshold''':

:: If <math display="inline"> \left | V\displaystyle _{X,t} \times S_{t} \times 0.91 \right | < 0.005 </math> , momentum is cancelled and only the acceleration is left.
:: If <math display="inline"> \left | V\displaystyle _{Z,t} \times S_{t} \times 0.91 \right | < 0.005 </math> , momentum is cancelled and only the acceleration is left.

:: In 1.9+, they are compared to 0.003 instead.


=== Source Code ===
[...]


<br />

== Non-Recursive Formulas ==
Since [https://en.wikipedia.org/wiki/Arithmetico%E2%80%93geometric_sequence arithmetico-geometric sequences] have explicit formulas, we can build non-recursive formulas to calculate simple but useful results, such as the height of the player on any given tick, or the distance of a jump in terms of the initial speed and duration.

Numeric approximations are given with 6 digits of precision.



'''Definitions:'''

* <math display="inline">v_0</math> is the player's initial speed (speed on <math>t_0</math>, before jumping)
* <math display="inline">t</math> is the number of ticks considered (ex: t=12 on flat ground, see '''Jump Duration''')
*<math display="inline">J</math> is the "jump bonus" (0.3274 for sprintjump, 0.291924 for strafed sprintjump, 0.1 for 45° no-sprint jump...)
*<math display="inline">M</math> is the movement multiplier after jumping (1.3 for 45° sprint, 1.274 for normal sprint, 1.0 for no-sprint 45°...)


=== Vertical Movement (jump) [1.8] ===
Vertical speed after jumping (<math>t \geq 6</math>)
{| class="wikitable"
!<math display="inline">\textrm{V}_Y(t) = 4 \times 0.98^{t-5} - 3.92</math>
|}
Relative height after jumping (<math>t \geq 6</math>)
{| class="wikitable"
!<math display="inline">\textrm{Y}_{rel}(t) = \underset{\textrm{jump peak}}{\underbrace{197.4 - 217 \times 0.98^5}} + 200 (0.98-0.98^{t-4}) - 3.92 (t-5)</math>
|-
|num. approx: <math>\textrm{Y}_{rel}(t) \approx 216.849187 - 216.833157 \times 0.98^t - 3.92t</math>
|}

For <math display="inline">t<6</math>, see below.


=== Vertical Movement (jump) [1.9+] ===
Vertical speed after jumping (<math>t \geq 1</math>)
{| class="wikitable"
!<math display="inline">\textrm{V}_Y(t) = 0.42 \times 0.98^{t-1} + 4 \times 0.98^t - 3.92</math>
|-
|num. approx: <math>\textrm{V}_Y(t) \approx 4.428571 \times 0.98^t - 3.92</math>
|}

Relative height after jumping (<math>t \geq 0</math>)
{| class="wikitable"
!<math display="inline">\textrm{Y}_{rel}(t) = 217 \times (1 - 0.98^t) - 3.92 t</math>
|}



=== Horizontal Movement (instant jump) ===
Assuming the player was airborne before jumping.

Horizontal speed after sprintjumping (<math>t \geq 2</math>)
{| class="wikitable"
!<math display="inline">\textrm{V}_H(v_0,t) = \frac{0.02 M}{0.09} + 0.6 \times 0.91^t \times \left ( v_0 + \frac{J}{0.91} - \frac{0.02 M}{0.6 \times 0.91 \times 0.09} \right )</math>
|-
|45° sprint: <math>\textrm{V}_H(v_0,t) \approx 0.288889 + 0.6 \times 0.91^t \times \left ( v_0 - 0.169320 \right )</math>
|-
|reg. sprint: <math display="inline">\textrm{V}_H(v_0,t) \approx 0.283111 + 0.6 \times 0.91^t \times \left ( v_0 - 0.158738 \right )</math>
|}
Sprintjump distance (<math>t \geq 2</math>)
{| class="wikitable"
!<math display="inline">\textrm{Dist}(v_0,t) = 1.91 v_0 + J + \frac{0.02 M}{0.09} (t-2) + \frac{0.6 \times 0.91^2}{0.09} \times (1 - 0.91^{t-2}) \times \left ( v_0 + \frac{J}{0.91} - \frac{0.02 M}{0.6 \times 0.91 \times 0.09} \right )</math>
|-
|45° sprint: <math display="inline">\textrm{Dist}(v_0,t) \approx 7.430667 v_0 + 0.288889 t -1.185138 - 6.666667 \times 0.91^t \left ( v_0 - 0.169320 \right )</math>
|-
|reg. sprint: <math display="inline">\textrm{Dist}(v_0,t) \approx 7.430667 v_0 + 0.283111 t -1.115163 - 6.666667 \times 0.91^t \left ( v_0 - 0.158738 \right )</math>
|}

'''Note:''' These formulas are accurate for most values of <math>v_0</math>, but some negative values can wind up activating the speed threshold and reset the player's speed at some point, thus rendering these formulas inaccurate.


=== Horizontal Movement (delayed jump) ===
Assuming the player is on ground before jumping (at least 1 tick since landing).

Horizontal speed after sprintjumping (<math>t \geq 2</math>)
{| class="wikitable"
!<math display="inline">\textrm{V}^*_H(v_0,t) = \frac{0.02 M}{0.09} + 0.6 \times 0.91^t \times \left ( 0.6 v_0 + \frac{J}{0.91} - \frac{0.02 M}{0.6 \times 0.91 \times 0.09} \right )</math>
|-
|45° sprint: <math>\textrm{V}^*_H(v_0,t) \approx 0.288889 + 0.36 \times 0.91^t \times \left ( v_0 -0.282201 \right )</math>
|-
|reg. sprint: <math display="inline">\textrm{V}^*_H(v_0,t) \approx 0.283111 + 0.36 \times 0.91^t \times \left ( v_0 - 0.264563 \right )</math>
|}
Sprintjump distance (<math>t \geq 2</math>)
{| class="wikitable"
!<math display="inline">\textrm{Dist}^*(v_0,t) = 1.546 v_0 + J + \frac{0.02 M}{0.09} (t-2) + \frac{0.6 \times 0.91^2}{0.09} \times (1 - 0.91^{t-2}) \times \left ( 0.6v_0 + \frac{J}{0.91} - \frac{0.02 M}{0.6 \times 0.91 \times 0.09} \right )</math>
|-
|45° sprint: <math display="inline">\textrm{Dist}^*(v_0,t) \approx 4.8584 v_0 + 0.288889t -1.185138 + 4 \times 0.91^t (v_0 - 0.169320)</math>
|-
|reg. sprint: <math display="inline">\textrm{Dist}^*(v_0,t) \approx 4.8584 v_0 + 0.283111t -1.115163 + 4 \times 0.91^t (v_0 - 0.158738)</math>
|}



=== Advanced Formulas ===
Horizontal speed after <math>n</math> consecutive sprintjumps on a momentum of period <math display="inline">T</math> (<math>n \geq 0</math>, <math>T \geq 2</math>).

If the first sprintjump is delayed, multiply <math display="inline">v_0</math> by 0.6
{| class="wikitable"
!<math display="inline">\textrm{V}^{\,n}_H(v_0,T,n) = \left ( 0.6 \times 0.91^T \right )^n v_0 + \left ( 0.6 \times 0.91^{T-1} J + 0.02M \frac{1 - 0.91^{T-1}}{0.09} \right ) \frac{1- (0.6 \times 0.91^T)^n}{1 - 0.6 \times 0.91^T} </math>
|}


=== Examples ===

*<math>Y_{rel}(60) </math> gives the relative height of the player 3 seconds (60 ticks) after jumping.
*<math>\textrm{Dist}(0,12)</math> gives the jump distance on flat ground with no initial speed.
*<math>\textrm{Dist}( V_H(0,12) ,9)</math> gives the distance of a +1 jump with one sprintjump of flat momentum as initial speed.
*<math>\textrm{Dist}(V^{10}_H(0,2), 12) </math> gives the jump distance with 10 sprintjumps of momentum under a trapdoor-headhitter.

Revision as of 14:29, 30 August 2020

Movement formulas applied to a 3b jump.

The player's movement can be accurately calculated with sequences.

The following formulas come from analyzing the game's source code.


Note that these formulas are not exact, due to how floats are computed. When used for calculations, only the first 4-6 decimals should be considered accurate. For a completely accurate simulation, you would need to replicate the source code.


In this article, we only consider standard movement, and ignore mechanics specific to certain blocks.


You will find further documentation of movement physics in these articles:


Note: Minecraft's coordinate system is oriented differently: 0° points towards "positive Z", and 90° points towards "negative X". We choose to work in the standard coordinate system to make calculations more intuitive. If need be, we can simply invert the X axis to match Minecraft's coordinate system.


Vertical Movement

Jump Formula


If , is set to 0 instead (the player's height doesn't change for that tick)
In 1.9+, it's compared to 0.003 instead.


Notes

  • isn't assigned a value because it has no importance. By convention, the 0th tick corresponds to the player's initial velocity before jumping.
  • corresponds to the initial jump motion. It is increased by 0.1 per level of Jump Boost
  • Terminal velocity is -3.92 m/t
  • When the player collides vertically with a block, vertical momentum is cancelled and only the acceleration is left.


Vertical Position

To get the position on a given tick, you simply need to sum


Jump duration

The duration of a jump is the number of ticks between jumping and landing.
It also corresponds to the period of that jump's cycle when performed repeatedly.
This notion is linked to the notion of Tiers.
Description Duration
Flat Jump 12 t
3bc Jump 11 t
+0.5 Jump 10 t
+1 Jump 9 t
2.5bc Jump 6 t
2bc Jump 3 t
1.8125bc Jump 2 t


Source code

from EntityLivingBase

/* Code unrelated to vertical movement is cut out */

protected float getJumpUpwardsMotion(){
    return 0.42F;
}


protected void jump()
{
    this.motionY = this.getJumpUpwardsMotion();
    if (this.isPotionActive(Potion.jump))
    {
        this.motionY += (this.getActivePotionEffect(Potion.jump).getAmplifier() + 1) * 0.1F;
    }
    this.isAirBorne = true;
}


public void moveEntityWithHeading(float strafe, float forward)
{
    ... /* also moves the player horizontally */

    this.motionY -= 0.08;
    this.motionY *= 0.98;
}


public void onLivingUpdate()
{
    if (this.jumpTicks > 0)
        --this.jumpTicks;

    if (Math.abs(this.motionY) < 0.005D)
        this.motionY = 0.0D;


    if (this.isJumping)
    {
        ... /* different if in water or lava */

        if (this.onGround && this.jumpTicks == 0)
        {
            this.jump();
            this.jumpTicks = 10; //activate autojump cooldown (0.5s)
        }
    }
        
    else
    {
        this.jumpTicks = 0; //reset autojump cooldown
    }

    ...
    
    this.moveEntityWithHeading(this.moveStrafing, this.moveForward);
}

Horizontal Movement

Horizontal Movement is a bit more complex than Vertical Movement, as it relies on many more factors: player actions, direction, and ground slipperiness.

On every tick, the game does these three steps:

  1. Acceleration is added to the player's velocity.
  2. The player is moved (new position = position + velocity).
  3. The player's velocity is reduced to simulate drag.

We'll start by introducing Multipliers in an effort to make formulas more readable.


Multipliers

Movement Multiplier (See 45° Strafe)


Failed to parse (SVG (MathML can be enabled via browser plugin): Invalid response ("Math extension cannot connect to Restbase.") from server "https://wikimedia.org/api/rest_v1/":): {\displaystyle M_{t} = \begin{Bmatrix}1.3 & \textrm{Sprinting} \\ 1.0 & \textrm{Walking}\\ 0.3 & \textrm{Sneaking}\\ 0.0 & \textrm{Stopping} \end{Bmatrix} \times \begin{Bmatrix}0.98 & \textrm{Default}\\ 1.0 & \textrm{45° Strafe} \\ 0.98 \sqrt{2} & \textrm{45° Sneak} \end{Bmatrix}}


Effects Multiplier (See Status Effects)


Failed to parse (syntax error): {\displaystyle E_{t} = (\underset{Decreases \; by \; 15\% \; per \; level \; of \; Slowness}{\underset{Increases \; by \; 20\% \; per \; level \; of \; Speed}{\underbrace{\left ( 1 + 0.2\times Speed \right ) \: \times\: \left ( 1 - 0.15\times Slowness \right )}}} \geq 0}


Slipperiness Multiplier (See Slipperiness)



Linear Formulas

These simplified formulas only apply to linear movement (no change in direction).
While this condition might seem very restrictive, these formulas are very useful to analyze conventional jumps and momentum
We'll later expand on these formulas by including angles.

Definition:
  • is the player's initial speed (default = 0).
  • is the player's speed on tick .


Ground Speed:
Failed to parse (syntax error): {\displaystyle V_{H,t} = \underset{Momentum}{\underbrace{\underset{ }{V_{H,t-1} \times S_{t-1} \times 0.91 }}} \: + \: \underset{Acceleration}{\underbrace{0.1 \times M_{t} \times E_{t} \times \left (\frac{0.6}{S_{t}} \right )^{3}}} }


Jump Speed:
Failed to parse (syntax error): {\displaystyle V_{H,t} = \underset{Momentum}{\underbrace{\underset{ }{V_{H,t-1} \times S_{t-1} \times 0.91 }}} \: + \: \underset{Acceleration}{\underbrace{0.1 \times M_{t} \times E_{t} \times \left (\frac{0.6}{S_{t}} \right )^{3}}} + \underset{Sprintjump \; Boost}{\underbrace{\begin{Bmatrix}0.2 & \textrm{Sprinting}\\ 0.0 & \textrm{Else}\end{Bmatrix} }}}


Air Speed:
Failed to parse (syntax error): {\displaystyle V_{H,t} = \underset{Momentum}{\underbrace{\underset{ }{V_{H,t-1} \times S_{t-1} \times 0.91 }}} \: + \: \underset{Acceleration}{\underbrace{\underset{ }{0.02 \times M_{t}}}} }


Complete Formulas

Let's introduce two more variables:
  • , The player's Direction in degrees (defined by their inputs and rotation)
  • , The player's Facing in degrees (defined by their rotation only)


In reality, angles aren't as simple as that, as there are a limited number of significant angles (see Facing and Angles).

For the purpose of simplicity, we'll ignore this fact.



Definition:
  • and correspond to the player's initial velocity.
  • and correspond to the player's velocity on tick
    Ground Velocity:
Failed to parse (SVG (MathML can be enabled via browser plugin): Invalid response ("Math extension cannot connect to Restbase.") from server "https://wikimedia.org/api/rest_v1/":): {\displaystyle V\displaystyle _{X,t} = \underset{ }{V\displaystyle _{X,t-1} \times S_{t-1} \times 0.91 } \: + \: 0.1 \times M_{t} \times E_{t} \times \left (\frac{0.6}{S_{t}} \right )^{3} \times \sin (D_{t}) }
Failed to parse (syntax error): {\displaystyle V\displaystyle _{Z,t} = \underset{Momentum}{\underbrace{\underset{ }{V\displaystyle _{Z,t-1} \times S_{t-1} \times 0.91 }}} \: + \: \underset{Acceleration}{\underbrace{0.1 \times M_{t} \times E_{t} \times \left (\frac{0.6}{S_{t}} \right )^{3}}} \times \cos (D_{t}) }
Jump Velocity:
Failed to parse (SVG (MathML can be enabled via browser plugin): Invalid response ("Math extension cannot connect to Restbase.") from server "https://wikimedia.org/api/rest_v1/":): {\displaystyle V\displaystyle _{X,t} = \underset{ }{V\displaystyle _{X,t-1} \times S_{t-1} \times 0.91 } \: + \: 0.1 \times M_{t} \times E_{t} \times \left (\frac{0.6}{S_{t}} \right )^{3} \times \sin (D_{t}) + \begin{Bmatrix} 0.2 & \textrm{Sprinting}\\ 0.0 & \textrm{Else}\end{Bmatrix} \times \sin (F_{t}) }
Failed to parse (syntax error): {\displaystyle V\displaystyle _{Z,t} = \underset{Momentum}{\underbrace{\underset{ }{V\displaystyle _{Z,t-1} \times S_{t-1} \times 0.91 }}} \: + \: \underset{Acceleration}{\underbrace{0.1 \times M_{t} \times E_{t} \times \left (\frac{0.6}{S_{t}} \right )^{3}}} \times \cos (D_{t}) + \underset{Sprintjump \; Boost }{\underbrace{\begin{Bmatrix} 0.2 & \textrm{Sprinting}\\ 0.0 & \textrm{Else}\end{Bmatrix} \times \cos (F_{t})}} }


Air Velocity:
Failed to parse (syntax error): {\displaystyle V\displaystyle _{X,t} = \underset{ }{V\displaystyle _{X,t-1} \times S_{t-1} \times 0.91 } \: + \: 0.02 \times M_{t} \times \sin (D_{t}) }
Failed to parse (syntax error): {\displaystyle V\displaystyle _{Z,t} = \underset{Momentum}{\underbrace{\underset{ }{V\displaystyle _{Z,t-1} \times S_{t-1} \times 0.91 }}} \: + \: \underset{Acceleration}{\underbrace{\underset{}{0.02 \times M_{t}}}} \times \cos (D_{t}) }

Stopping Conditions

Horizontal speed is set to 0 if the player hits a wall, or if the speed is considered to be negligible.


Wall Collision:
If the player hits a X-facing wall, then is set to 0 and the player is placed against the wall.
If the player hits a Z-facing wall, then is set to 0 and the player is placed against the wall.


Negligible Speed Threshold:
If , momentum is cancelled and only the acceleration is left.
If , momentum is cancelled and only the acceleration is left.
In 1.9+, they are compared to 0.003 instead.


Source Code

[...]



Non-Recursive Formulas

Since arithmetico-geometric sequences have explicit formulas, we can build non-recursive formulas to calculate simple but useful results, such as the height of the player on any given tick, or the distance of a jump in terms of the initial speed and duration.

Numeric approximations are given with 6 digits of precision.


Definitions:

  • is the player's initial speed (speed on , before jumping)
  • is the number of ticks considered (ex: t=12 on flat ground, see Jump Duration)
  • is the "jump bonus" (0.3274 for sprintjump, 0.291924 for strafed sprintjump, 0.1 for 45° no-sprint jump...)
  • is the movement multiplier after jumping (1.3 for 45° sprint, 1.274 for normal sprint, 1.0 for no-sprint 45°...)


Vertical Movement (jump) [1.8]

Vertical speed after jumping ()

Relative height after jumping ()

num. approx:

For , see below.


Vertical Movement (jump) [1.9+]

Vertical speed after jumping ()

num. approx:

Relative height after jumping ()


Horizontal Movement (instant jump)

Assuming the player was airborne before jumping.

Horizontal speed after sprintjumping ()

45° sprint:
reg. sprint:

Sprintjump distance ()

45° sprint:
reg. sprint:

Note: These formulas are accurate for most values of , but some negative values can wind up activating the speed threshold and reset the player's speed at some point, thus rendering these formulas inaccurate.


Horizontal Movement (delayed jump)

Assuming the player is on ground before jumping (at least 1 tick since landing).

Horizontal speed after sprintjumping ()

45° sprint:
reg. sprint:

Sprintjump distance ()

45° sprint:
reg. sprint:


Advanced Formulas

Horizontal speed after consecutive sprintjumps on a momentum of period (, ).

If the first sprintjump is delayed, multiply by 0.6


Examples

  • gives the relative height of the player 3 seconds (60 ticks) after jumping.
  • gives the jump distance on flat ground with no initial speed.
  • gives the distance of a +1 jump with one sprintjump of flat momentum as initial speed.
  • gives the jump distance with 10 sprintjumps of momentum under a trapdoor-headhitter.