Sprinting/ja: Difference between revisions

From Minecraft Parkour Wiki
Content added Content deleted
(Created page with "ダッシュ")
(Created page with "空中でのダッシュの発動が1tick遅延しているのは、<code>airMovementFactor</code>の取得が空中移動の適用の際に行われるため(airMovementFactorはプレイヤーが動いた後に更新される)。<br> 対して、プレイヤーが地面にいるときは、移動前に更新が行われる<code>movementSpeed</code>から倍率が直接取得される(<code>setSprinting</code>のメソッドで修飾子が適用される)。<br>...")
 
(23 intermediate revisions by the same user not shown)
Line 1: Line 1:
<languages/>
<languages/>
ダッシュは、より速い移動とより遠くへのジャンプが可能になる、重要な仕組みである。
<div lang="en" dir="ltr" class="mw-content-ltr">
Sprinting is an essential mechanic that makes the player move faster and jump further.
</div>




Line 8: Line 6:
== 発動 ==
== 発動 ==


ダッシュは、'''ダッシュキー'''を押すか、'''前進キー'''を'''二度押し'''(地面でのみ)すると発動する。
<div lang="en" dir="ltr" class="mw-content-ltr">
Sprinting is activated with the '''Sprint key''', or by '''double-tapping''' '''Forward''' (on ground only).
</div>


* 二度押しの場合は前進キーを離す代わりに後退キーを押しても発動できる。どちらの場合も、7tick以内に前進し直す必要がある。
<div lang="en" dir="ltr" class="mw-content-ltr">
* 前進キーを離すと途切れる。
* It can also be activated with the help of the backward key. In any case, the activation timer is 7 ticks.
* ダッシュキーを押し続けない限り、30秒経つと途切れる。
* If the Forward key isn't held, the player stops sprinting.
* [[Special:MyLanguage/Sneaking/ja|スニーク]]中はダッシュできない(1.14以降を除く)。
* The player stops sprinting after 30 seconds, unless the Sprint key is held.
* Sprinting is incompatible with [[Special:MyLanguage/Sneaking|Sneaking]] (except in 1.14+).
</div>


* 壁に衝突するとその次tickに途切れる。
<div lang="en" dir="ltr" class="mw-content-ltr">
* Colliding with a wall causes the player to stop sprinting on the next tick.
</div>


* 空中では1tick遅延する(発動/停止が1tick遅れる)。
<div lang="en" dir="ltr" class="mw-content-ltr">
* 空腹時/アイテム使用中/暗視状態ではダッシュできない。
* Sprinting in air is delayed by one tick (activates and deactivates one tick late)
*Sprinting cannot be activated when hungry, using an item, or being affected by Blindness.
</div>




Line 32: Line 22:
==速度==
==速度==


ダッシュは歩きより30%速く、基本加速度は'''0.13'''である。地面での漸近速度は約0.286m/t。
<div lang="en" dir="ltr" class="mw-content-ltr">
Sprinting is 30% faster than walking, granting a base acceleration of '''0.13'''. The asymptotic speed on ground is ~0.286 m/t.
</div>


加えて、ダッシュ中にジャンプすると、向いている方向に'''0.2'''の加速度が付与される(strafeが入力されているかは無関係)。
<div lang="en" dir="ltr" class="mw-content-ltr">
Additionally, when the player jumps while sprinting, they accelerate by '''0.2''' towards their facing (regardless of whether the player is strafing)
</div>


* これにより、ダッシュジャンプ時は素早く加速することができるため、速度を得るもっとも良い方法になっている。
<div lang="en" dir="ltr" class="mw-content-ltr">
* Strafeを入力しながらのダッシュジャンプは正面にジャンプするよりも実際には遅く、方向もずれてしまうが、使い道は存在する。
* This means the player accelerates quickly when sprint-jumping, making it the best way to build speed.
** [[Special:MyLanguage/Backward Momentum|Backward Momentum]]との組み合わせ時など、通常のダッシュジャンプでは速度が出過ぎてしまう場合に役立つ。
*Sprint-jumping sideways is actually slower than forward, and goes off-track. But it does have applications:
** 振り向きが必要なジャンプにおいて、「サイドステップ」の技術内で使用される。([https://youtu.be/fo2VlHOHiwo 例])
**Useful for [[Special:MyLanguage/Backward Momentum|Backward Momentum]], in cases where a regular sprint-jump would give too much speed.
**Used in the "Sidestep" technique for jumps that require turning. ([https://youtu.be/fo2VlHOHiwo example])
</div>






==ソースコード==
<div lang="en" dir="ltr" class="mw-content-ltr">
==Code==
</div>


以下はダッシュがどのように発動しているかに関するコード。<syntaxhighlight lang="java">
<div lang="en" dir="ltr" class="mw-content-ltr">
The following snippets of code deal with how sprinting is activated.<syntaxhighlight lang="java">
/* EntityPlayerSP.java */
/* EntityPlayerSP.java */
public void onLivingUpdate()
public void onLivingUpdate()
Line 61: Line 42:
{
{
--this.sprintingTicksLeft;
--this.sprintingTicksLeft;
</div>


if (this.sprintingTicksLeft == 0)
<div lang="en" dir="ltr" class="mw-content-ltr">
if (this.sprintingTicksLeft == 0)
this.setSprinting(false);
this.setSprinting(false);
}
}
</div>


if (this.sprintToggleTimer > 0)
<div lang="en" dir="ltr" class="mw-content-ltr">
if (this.sprintToggleTimer > 0)
{
{
--this.sprintToggleTimer;
--this.sprintToggleTimer;
}
}
</div>


//1tick前のプレイヤーの動きを取得する。
<div lang="en" dir="ltr" class="mw-content-ltr">
//Takes the player's actions from the previous tick.
boolean prevJumping = this.movementInput.jump;
boolean prevJumping = this.movementInput.jump;
boolean prevSneaking = this.movementInput.sneak;
boolean prevSneaking = this.movementInput.sneak;
Line 83: Line 58:
boolean prevMovingForward = this.movementInput.moveForward >= f;
boolean prevMovingForward = this.movementInput.moveForward >= f;
//動きの入力を更新する(moveForwardを含む - スニークしている際は0.3倍される)。
//the movement input is updated (including moveForward - keep in mind it's multiplied by 0.3 when sneaking).
this.movementInput.updatePlayerMoveState();
this.movementInput.updatePlayerMoveState();
</div>


[...]
<div lang="en" dir="ltr" class="mw-content-ltr">
[...]
</div>


//従来の方法: プレイヤーは前tickに前方に動いていなかったが今tickでは動いている。地面にいる必要がある。
<div lang="en" dir="ltr" class="mw-content-ltr">
//LEGACY METHOD: the player wasn't moving forward on the previous tick but is now. Must be on ground.
if (!this.isSprinting() && this.onGround && !prevSneaking && !prevMovingForward && this.movementInput.moveForward >= f && isntHungry && !this.isUsingItem() && !this.isPotionActive(Potion.blindness))
if (!this.isSprinting() && this.onGround && !prevSneaking && !prevMovingForward && this.movementInput.moveForward >= f && isntHungry && !this.isUsingItem() && !this.isPotionActive(Potion.blindness))
{
{
if (this.sprintToggleTimer <= 0 && !keyBindSprint.isKeyDown())
if (this.sprintToggleTimer <= 0 && !keyBindSprint.isKeyDown())
this.sprintToggleTimer = 7; //the timer is 7 ticks
this.sprintToggleTimer = 7; //タイマーは7tick
else
else
this.setSprinting(true);
this.setSprinting(true);
}
}
//プレイヤーが前tickに前方に動いていた場合に発動する
//Activated when the player was moving forward on the previous tick
if (!this.isSprinting() && this.movementInput.moveForward >= f && isntHungry && !this.isUsingItem() && !this.isPotionActive(Potion.blindness) && keyBindSprint.isKeyDown())
if (!this.isSprinting() && this.movementInput.moveForward >= f && isntHungry && !this.isUsingItem() && !this.isPotionActive(Potion.blindness) && keyBindSprint.isKeyDown())
{
{
this.setSprinting(true);
this.setSprinting(true);
}
}
</div>


if (this.isSprinting() && (this.movementInput.moveForward < f || this.isCollidedHorizontally || !isntHungry))
<div lang="en" dir="ltr" class="mw-content-ltr">
if (this.isSprinting() && (this.movementInput.moveForward < f || this.isCollidedHorizontally || !isntHungry))
{
{
this.setSprinting(false);
this.setSprinting(false);
}
}
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
}
}
</div>






/* Entity、EntityLivingBase、EntityPlayerSPから */
<div lang="en" dir="ltr" class="mw-content-ltr">
/* From Entity, EntityLivingBase, EntityPlayerSP */
public void setSprinting(boolean sprinting)
public void setSprinting(boolean sprinting)
{
{
this.setFlag(3, sprinting);
this.setFlag(3, sprinting);
</div>


EntityAttribute movementSpeed = this.getEntityAttribute(movementSpeed);
EntityAttribute movementSpeed = this.getEntityAttribute(movementSpeed);


if (movementSpeed.getModifier(sprintModifierUUID) != null)
<div lang="en" dir="ltr" class="mw-content-ltr">
if (movementSpeed.getModifier(sprintModifierUUID) != null)
movementSpeed.removeModifier(sprintModifier);
movementSpeed.removeModifier(sprintModifier);
</div>


if (sprinting)
<div lang="en" dir="ltr" class="mw-content-ltr">
movementSpeed.applyModifier(sprintModifier); //sprintModifierが倍率に0.3を加える。
if (sprinting)
movementSpeed.applyModifier(sprintModifier); //sprintModifier adds 0.3 to the multiplier.
</div>


this.sprintingTicksLeft = sprinting ? 600 : 0;
<div lang="en" dir="ltr" class="mw-content-ltr">
this.sprintingTicksLeft = sprinting ? 600 : 0;
}
}
</syntaxhighlight>
</syntaxhighlight>
</div>




以下は、1tick内に行われる手順を簡略化したもの:
<div lang="en" dir="ltr" class="mw-content-ltr">
#ダッシュ状態を更新する。
Here is the simplified sequence of steps performed during a tick:
#速度を計算しプレイヤーを動かす。
#Update sprinting status
#移動速度に影響する、<code>groundMovementFactor</code>と<code>airMovementFactor</code>(ダッシュ時は1.3倍)を更新する。
#Calculate velocity and move the player
#Update <code>groundMovementFactor</code> and <code>airMovementFactor</code> (multiplied by 1.3 if sprinting), which affect movement speed.
</div>




空中でのダッシュの発動が1tick遅延しているのは、<code>airMovementFactor</code>の取得が空中移動の適用の際に行われるため(airMovementFactorはプレイヤーが動いた後に更新される)。<br>
<div lang="en" dir="ltr" class="mw-content-ltr">
対して、プレイヤーが地面にいるときは、移動前に更新が行われる<code>movementSpeed</code>から倍率が直接取得される(<code>setSprinting</code>のメソッドで修飾子が適用される)。<br>
The reason air sprinting activation is delayed by one tick is because the game fetches <code>airMovementFactor</code> when applying air movement (which is updated after the player has already moved). In contrast, when the player is on ground, the game gets the multiplier directly from <code>movementSpeed</code>, which is updated before moving (applies modifier in method <code>setSprinting</code>). <code>groundMovementFactor</code> is essentially useless in the case of Player entities.
<code>groundMovementFactor</code>は、対象エンティティがプレイヤーの場合は基本的に無意味。
</div>

Latest revision as of 14:45, 4 July 2022

Other languages:

ダッシュは、より速い移動とより遠くへのジャンプが可能になる、重要な仕組みである。


発動

ダッシュは、ダッシュキーを押すか、前進キー二度押し(地面でのみ)すると発動する。

  • 二度押しの場合は前進キーを離す代わりに後退キーを押しても発動できる。どちらの場合も、7tick以内に前進し直す必要がある。
  • 前進キーを離すと途切れる。
  • ダッシュキーを押し続けない限り、30秒経つと途切れる。
  • スニーク中はダッシュできない(1.14以降を除く)。
  • 壁に衝突するとその次tickに途切れる。
  • 空中では1tick遅延する(発動/停止が1tick遅れる)。
  • 空腹時/アイテム使用中/暗視状態ではダッシュできない。


速度

ダッシュは歩きより30%速く、基本加速度は0.13である。地面での漸近速度は約0.286m/t。

加えて、ダッシュ中にジャンプすると、向いている方向に0.2の加速度が付与される(strafeが入力されているかは無関係)。

  • これにより、ダッシュジャンプ時は素早く加速することができるため、速度を得るもっとも良い方法になっている。
  • Strafeを入力しながらのダッシュジャンプは正面にジャンプするよりも実際には遅く、方向もずれてしまうが、使い道は存在する。
    • Backward Momentumとの組み合わせ時など、通常のダッシュジャンプでは速度が出過ぎてしまう場合に役立つ。
    • 振り向きが必要なジャンプにおいて、「サイドステップ」の技術内で使用される。(


ソースコード

以下はダッシュがどのように発動しているかに関するコード。

/* EntityPlayerSP.java */
public void onLivingUpdate()
{
    if (this.sprintingTicksLeft > 0)
    {
        --this.sprintingTicksLeft;

        if (this.sprintingTicksLeft == 0)
            this.setSprinting(false);
    }

    if (this.sprintToggleTimer > 0)
    {
        --this.sprintToggleTimer;
    }

    //1tick前のプレイヤーの動きを取得する。
    boolean prevJumping = this.movementInput.jump;
    boolean prevSneaking = this.movementInput.sneak;
    float f = 0.8F;
    boolean prevMovingForward = this.movementInput.moveForward >= f;
        
    //動きの入力を更新する(moveForwardを含む - スニークしている際は0.3倍される)。
    this.movementInput.updatePlayerMoveState();

    [...]

    //従来の方法: プレイヤーは前tickに前方に動いていなかったが今tickでは動いている。地面にいる必要がある。
    if (!this.isSprinting() && this.onGround && !prevSneaking && !prevMovingForward && this.movementInput.moveForward >= f && isntHungry && !this.isUsingItem() && !this.isPotionActive(Potion.blindness))
    {
        if (this.sprintToggleTimer <= 0 && !keyBindSprint.isKeyDown())
            this.sprintToggleTimer = 7; //タイマーは7tick
        else
            this.setSprinting(true);
        }
        
    //プレイヤーが前tickに前方に動いていた場合に発動する
    if (!this.isSprinting() && this.movementInput.moveForward >= f && isntHungry && !this.isUsingItem() && !this.isPotionActive(Potion.blindness) && keyBindSprint.isKeyDown())
    {
        this.setSprinting(true);
    }

        
    if (this.isSprinting() && (this.movementInput.moveForward < f || this.isCollidedHorizontally || !isntHungry))
    {
        this.setSprinting(false);
    }

}



/* Entity、EntityLivingBase、EntityPlayerSPから */
public void setSprinting(boolean sprinting)
{
    this.setFlag(3, sprinting);

    EntityAttribute movementSpeed = this.getEntityAttribute(movementSpeed);

    if (movementSpeed.getModifier(sprintModifierUUID) != null)
        movementSpeed.removeModifier(sprintModifier);

    if (sprinting)
        movementSpeed.applyModifier(sprintModifier); //sprintModifierが倍率に0.3を加える。

    this.sprintingTicksLeft = sprinting ? 600 : 0;
}


以下は、1tick内に行われる手順を簡略化したもの:

  1. ダッシュ状態を更新する。
  2. 速度を計算しプレイヤーを動かす。
  3. 移動速度に影響する、groundMovementFactorairMovementFactor(ダッシュ時は1.3倍)を更新する。


空中でのダッシュの発動が1tick遅延しているのは、airMovementFactorの取得が空中移動の適用の際に行われるため(airMovementFactorはプレイヤーが動いた後に更新される)。
対して、プレイヤーが地面にいるときは、移動前に更新が行われるmovementSpeedから倍率が直接取得される(setSprintingのメソッドで修飾子が適用される)。
groundMovementFactorは、対象エンティティがプレイヤーの場合は基本的に無意味。