1
0
Fork 0
mirror of https://github.com/zeldaret/oot.git synced 2024-12-29 08:16:11 +00:00

Player Docs: Player_ActionChange_6, Rolling and Put Away (#1949)

* progress

* changing branches

* start comments

* last few changes

* name the handler after rolling only

* comment tweak

* format
This commit is contained in:
fig02 2024-09-25 15:46:15 -04:00 committed by GitHub
parent 7ccb0a641e
commit 8ff4faa084
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
3 changed files with 99 additions and 75 deletions

View file

@ -716,7 +716,7 @@ typedef struct WeaponInfo {
#define PLAYER_STATE2_17 (1 << 17)
#define PLAYER_STATE2_CRAWLING (1 << 18) // Crawling through a crawlspace
#define PLAYER_STATE2_19 (1 << 19)
#define PLAYER_STATE2_20 (1 << 20)
#define PLAYER_STATE2_NAVI_ACTIVE (1 << 20) // Navi is visible and active. Could be hovering idle near Link or hovering over other actors.
#define PLAYER_STATE2_21 (1 << 21)
#define PLAYER_STATE2_22 (1 << 22)
#define PLAYER_STATE2_23 (1 << 23)
@ -850,7 +850,7 @@ typedef struct Player {
/* 0x0830 */ f32 upperAnimInterpWeight;
/* 0x0834 */ s16 unk_834;
/* 0x0836 */ s8 unk_836;
/* 0x0837 */ u8 unk_837;
/* 0x0837 */ u8 putAwayCooldownTimer;
/* 0x0838 */ f32 speedXZ; // Controls horizontal speed, used for `actor.speed`. Current or target value depending on context.
/* 0x083C */ s16 yaw; // General yaw value, used both for world and shape rotation. Current or target value depending on context.
/* 0x083E */ s16 parallelYaw; // yaw in "parallel" mode, Z-Target without an actor lock-on
@ -869,6 +869,7 @@ typedef struct Player {
/* 0x0850 */ union {
s16 actionVar2;
s16 bonked; // Player_Action_Roll: set to true after bonking into a wall or an actor
} av2; // "Action Variable 2": context dependent variable that has different meanings depending on what action is currently running
/* 0x0854 */ f32 unk_854;

View file

@ -1095,7 +1095,7 @@ void func_80A0461C(EnElf* this, PlayState* play) {
} else if (naviHoverActor == NULL || naviHoverActor->category == ACTORCAT_NPC) {
if (naviHoverActor != NULL) {
this->unk_2C0 = 100;
player->stateFlags2 |= PLAYER_STATE2_20;
player->stateFlags2 |= PLAYER_STATE2_NAVI_ACTIVE;
temp = 0;
} else {
switch (this->unk_2A8) {
@ -1116,7 +1116,7 @@ void func_80A0461C(EnElf* this, PlayState* play) {
this->unk_2AE--;
temp = 7;
} else {
player->stateFlags2 |= PLAYER_STATE2_20;
player->stateFlags2 |= PLAYER_STATE2_NAVI_ACTIVE;
temp = 0;
}
} else {
@ -1146,7 +1146,7 @@ void func_80A0461C(EnElf* this, PlayState* play) {
switch (temp) {
case 0:
if (!(player->stateFlags2 & PLAYER_STATE2_20)) {
if (!(player->stateFlags2 & PLAYER_STATE2_NAVI_ACTIVE)) {
temp = 7;
if (this->unk_2C7 == 0) {
Actor_PlaySfx(&this->actor, NA_SE_EV_NAVY_VANISH);
@ -1154,7 +1154,7 @@ void func_80A0461C(EnElf* this, PlayState* play) {
}
break;
case 8:
if (player->stateFlags2 & PLAYER_STATE2_20) {
if (player->stateFlags2 & PLAYER_STATE2_NAVI_ACTIVE) {
func_80A0299C(this, 0x32);
this->unk_2C0 = 42;
temp = 11;
@ -1164,10 +1164,10 @@ void func_80A0461C(EnElf* this, PlayState* play) {
}
break;
case 7:
player->stateFlags2 &= ~PLAYER_STATE2_20;
player->stateFlags2 &= ~PLAYER_STATE2_NAVI_ACTIVE;
break;
default:
player->stateFlags2 |= PLAYER_STATE2_20;
player->stateFlags2 |= PLAYER_STATE2_NAVI_ACTIVE;
break;
}
}

View file

@ -286,7 +286,7 @@ void Player_Action_80843954(Player* this, PlayState* play);
void Player_Action_80843A38(Player* this, PlayState* play);
void Player_Action_80843CEC(Player* this, PlayState* play);
void Player_Action_8084411C(Player* this, PlayState* play);
void Player_Action_80844708(Player* this, PlayState* play);
void Player_Action_Roll(Player* this, PlayState* play);
void Player_Action_80844A44(Player* this, PlayState* play);
void Player_Action_80844AF4(Player* this, PlayState* play);
void Player_Action_80844E68(Player* this, PlayState* play);
@ -3928,7 +3928,7 @@ typedef enum ActionHandlerIndex {
/* 3 */ PLAYER_ACTION_HANDLER_3,
/* 4 */ PLAYER_ACTION_HANDLER_4,
/* 5 */ PLAYER_ACTION_HANDLER_5,
/* 6 */ PLAYER_ACTION_HANDLER_6,
/* 6 */ PLAYER_ACTION_HANDLER_ROLL,
/* 7 */ PLAYER_ACTION_HANDLER_7,
/* 8 */ PLAYER_ACTION_HANDLER_8,
/* 9 */ PLAYER_ACTION_HANDLER_9,
@ -3946,13 +3946,13 @@ static s8 sActionHandlerList1[] = {
static s8 sActionHandlerList2[] = {
PLAYER_ACTION_HANDLER_13, PLAYER_ACTION_HANDLER_1, PLAYER_ACTION_HANDLER_2, PLAYER_ACTION_HANDLER_5,
PLAYER_ACTION_HANDLER_3, PLAYER_ACTION_HANDLER_4, PLAYER_ACTION_HANDLER_9, PLAYER_ACTION_HANDLER_10,
PLAYER_ACTION_HANDLER_11, PLAYER_ACTION_HANDLER_7, PLAYER_ACTION_HANDLER_8, -PLAYER_ACTION_HANDLER_6,
PLAYER_ACTION_HANDLER_11, PLAYER_ACTION_HANDLER_7, PLAYER_ACTION_HANDLER_8, -PLAYER_ACTION_HANDLER_ROLL,
};
static s8 sActionHandlerList3[] = {
PLAYER_ACTION_HANDLER_13, PLAYER_ACTION_HANDLER_1, PLAYER_ACTION_HANDLER_2, PLAYER_ACTION_HANDLER_3,
PLAYER_ACTION_HANDLER_4, PLAYER_ACTION_HANDLER_9, PLAYER_ACTION_HANDLER_10, PLAYER_ACTION_HANDLER_11,
PLAYER_ACTION_HANDLER_8, PLAYER_ACTION_HANDLER_7, -PLAYER_ACTION_HANDLER_6,
PLAYER_ACTION_HANDLER_13, PLAYER_ACTION_HANDLER_1, PLAYER_ACTION_HANDLER_2, PLAYER_ACTION_HANDLER_3,
PLAYER_ACTION_HANDLER_4, PLAYER_ACTION_HANDLER_9, PLAYER_ACTION_HANDLER_10, PLAYER_ACTION_HANDLER_11,
PLAYER_ACTION_HANDLER_8, PLAYER_ACTION_HANDLER_7, -PLAYER_ACTION_HANDLER_ROLL,
};
static s8 sActionHandlerList4[] = {
@ -3971,22 +3971,22 @@ static s8 sActionHandlerList6[] = {
};
static s8 sActionHandlerList7[] = {
PLAYER_ACTION_HANDLER_0, PLAYER_ACTION_HANDLER_11, PLAYER_ACTION_HANDLER_1, PLAYER_ACTION_HANDLER_2,
PLAYER_ACTION_HANDLER_3, PLAYER_ACTION_HANDLER_5, PLAYER_ACTION_HANDLER_4, PLAYER_ACTION_HANDLER_9,
PLAYER_ACTION_HANDLER_8, PLAYER_ACTION_HANDLER_7, -PLAYER_ACTION_HANDLER_6,
PLAYER_ACTION_HANDLER_0, PLAYER_ACTION_HANDLER_11, PLAYER_ACTION_HANDLER_1, PLAYER_ACTION_HANDLER_2,
PLAYER_ACTION_HANDLER_3, PLAYER_ACTION_HANDLER_5, PLAYER_ACTION_HANDLER_4, PLAYER_ACTION_HANDLER_9,
PLAYER_ACTION_HANDLER_8, PLAYER_ACTION_HANDLER_7, -PLAYER_ACTION_HANDLER_ROLL,
};
static s8 sActionHandlerList8[] = {
PLAYER_ACTION_HANDLER_0, PLAYER_ACTION_HANDLER_11, PLAYER_ACTION_HANDLER_1, PLAYER_ACTION_HANDLER_2,
PLAYER_ACTION_HANDLER_3, PLAYER_ACTION_HANDLER_12, PLAYER_ACTION_HANDLER_5, PLAYER_ACTION_HANDLER_4,
PLAYER_ACTION_HANDLER_9, PLAYER_ACTION_HANDLER_8, PLAYER_ACTION_HANDLER_7, -PLAYER_ACTION_HANDLER_6,
PLAYER_ACTION_HANDLER_9, PLAYER_ACTION_HANDLER_8, PLAYER_ACTION_HANDLER_7, -PLAYER_ACTION_HANDLER_ROLL,
};
static s8 sActionHandlerList9[] = {
PLAYER_ACTION_HANDLER_13, PLAYER_ACTION_HANDLER_1, PLAYER_ACTION_HANDLER_2, PLAYER_ACTION_HANDLER_3,
PLAYER_ACTION_HANDLER_12, PLAYER_ACTION_HANDLER_5, PLAYER_ACTION_HANDLER_4, PLAYER_ACTION_HANDLER_9,
PLAYER_ACTION_HANDLER_10, PLAYER_ACTION_HANDLER_11, PLAYER_ACTION_HANDLER_8, PLAYER_ACTION_HANDLER_7,
-PLAYER_ACTION_HANDLER_6,
PLAYER_ACTION_HANDLER_13, PLAYER_ACTION_HANDLER_1, PLAYER_ACTION_HANDLER_2, PLAYER_ACTION_HANDLER_3,
PLAYER_ACTION_HANDLER_12, PLAYER_ACTION_HANDLER_5, PLAYER_ACTION_HANDLER_4, PLAYER_ACTION_HANDLER_9,
PLAYER_ACTION_HANDLER_10, PLAYER_ACTION_HANDLER_11, PLAYER_ACTION_HANDLER_8, PLAYER_ACTION_HANDLER_7,
-PLAYER_ACTION_HANDLER_ROLL,
};
static s8 sActionHandlerList10[] = {
@ -4008,7 +4008,7 @@ s32 Player_ActionHandler_2(Player* this, PlayState* play);
s32 Player_ActionHandler_3(Player* this, PlayState* play);
s32 Player_ActionHandler_4(Player* this, PlayState* play);
s32 Player_ActionHandler_5(Player* this, PlayState* play);
s32 Player_ActionHandler_6(Player* this, PlayState* play);
s32 Player_ActionHandler_Roll(Player* this, PlayState* play);
s32 Player_ActionHandler_7(Player* this, PlayState* play);
s32 Player_ActionHandler_8(Player* this, PlayState* play);
s32 Player_ActionHandler_9(Player* this, PlayState* play);
@ -4018,20 +4018,20 @@ s32 Player_ActionHandler_12(Player* this, PlayState* play);
s32 Player_ActionHandler_13(Player* this, PlayState* play);
static s32 (*sActionHandlerFuncs[])(Player* this, PlayState* play) = {
Player_ActionHandler_0, // PLAYER_ACTION_HANDLER_0
Player_ActionHandler_1, // PLAYER_ACTION_HANDLER_1
Player_ActionHandler_2, // PLAYER_ACTION_HANDLER_2
Player_ActionHandler_3, // PLAYER_ACTION_HANDLER_3
Player_ActionHandler_4, // PLAYER_ACTION_HANDLER_4
Player_ActionHandler_5, // PLAYER_ACTION_HANDLER_5
Player_ActionHandler_6, // PLAYER_ACTION_HANDLER_6
Player_ActionHandler_7, // PLAYER_ACTION_HANDLER_7
Player_ActionHandler_8, // PLAYER_ACTION_HANDLER_8
Player_ActionHandler_9, // PLAYER_ACTION_HANDLER_9
Player_ActionHandler_10, // PLAYER_ACTION_HANDLER_10
Player_ActionHandler_11, // PLAYER_ACTION_HANDLER_11
Player_ActionHandler_12, // PLAYER_ACTION_HANDLER_12
Player_ActionHandler_13, // PLAYER_ACTION_HANDLER_13
Player_ActionHandler_0, // PLAYER_ACTION_HANDLER_0
Player_ActionHandler_1, // PLAYER_ACTION_HANDLER_1
Player_ActionHandler_2, // PLAYER_ACTION_HANDLER_2
Player_ActionHandler_3, // PLAYER_ACTION_HANDLER_3
Player_ActionHandler_4, // PLAYER_ACTION_HANDLER_4
Player_ActionHandler_5, // PLAYER_ACTION_HANDLER_5
Player_ActionHandler_Roll, // PLAYER_ACTION_HANDLER_ROLL
Player_ActionHandler_7, // PLAYER_ACTION_HANDLER_7
Player_ActionHandler_8, // PLAYER_ACTION_HANDLER_8
Player_ActionHandler_9, // PLAYER_ACTION_HANDLER_9
Player_ActionHandler_10, // PLAYER_ACTION_HANDLER_10
Player_ActionHandler_11, // PLAYER_ACTION_HANDLER_11
Player_ActionHandler_12, // PLAYER_ACTION_HANDLER_12
Player_ActionHandler_13, // PLAYER_ACTION_HANDLER_13
};
/**
@ -6083,22 +6083,22 @@ s32 func_8083BBA0(Player* this, PlayState* play) {
return 0;
}
void func_8083BC04(Player* this, PlayState* play) {
Player_SetupAction(play, this, Player_Action_80844708, 0);
void Player_SetupRoll(Player* this, PlayState* play) {
Player_SetupAction(play, this, Player_Action_Roll, 0);
LinkAnimation_PlayOnceSetSpeed(play, &this->skelAnime,
GET_PLAYER_ANIM(PLAYER_ANIMGROUP_landing_roll, this->modelAnimType),
FRAMERATE_CONST(1.25f, 1.5f) * D_808535E8);
}
s32 func_8083BC7C(Player* this, PlayState* play) {
s32 Player_TryRoll(Player* this, PlayState* play) {
if ((this->controlStickDirections[this->controlStickDataIndex] == PLAYER_STICK_DIR_FORWARD) &&
(sFloorType != FLOOR_TYPE_7)) {
func_8083BC04(this, play);
Player_SetupRoll(this, play);
return 1;
return true;
}
return 0;
return false;
}
void func_8083BCD0(Player* this, PlayState* play, s32 controlStickDirection) {
@ -6132,13 +6132,13 @@ s32 Player_ActionHandler_10(Player* this, PlayState* play) {
if (controlStickDirection <= PLAYER_STICK_DIR_NONE) {
func_808389E8(this, &gPlayerAnim_link_normal_jump, REG(69) / 100.0f, play);
} else {
func_8083BC04(this, play);
Player_SetupRoll(this, play);
}
} else {
if ((Player_GetMeleeWeaponHeld(this) != 0) && Player_CanUpdateItems(this)) {
func_8083BA90(play, this, PLAYER_MWA_JUMPSLASH_START, 5.0f, 5.0f);
} else {
func_8083BC04(this, play);
Player_SetupRoll(this, play);
}
}
@ -6211,20 +6211,30 @@ void func_8083C148(Player* this, PlayState* play) {
this->stateFlags1 &= ~(PLAYER_STATE1_13 | PLAYER_STATE1_14 | PLAYER_STATE1_20);
}
s32 Player_ActionHandler_6(Player* this, PlayState* play) {
/**
* Handles setting up a roll if it is appropriate.
*
* If a roll is not applicable, there are two extra behaviors that could occur:
* - If an item is currently held in hand, it can be put away.
* - Navi can be toggled on and off.
* She will either appear and fly around Link's head, or disappear by flying back into his hat
*
* These extra behaviors are not new actions themselves, so they will result in `false` being returned
* even if they occur.
*/
s32 Player_ActionHandler_Roll(Player* this, PlayState* play) {
if (!Player_UpdateHostileLockOn(this) && !sUpperBodyIsBusy && !(this->stateFlags1 & PLAYER_STATE1_23) &&
CHECK_BTN_ALL(sControlInput->press.button, BTN_A)) {
if (func_8083BC7C(this, play)) {
return 1;
}
if ((this->unk_837 == 0) && (this->heldItemAction >= PLAYER_IA_SWORD_MASTER)) {
if (Player_TryRoll(this, play)) {
return true;
} else if ((this->putAwayCooldownTimer == 0) && (this->heldItemAction >= PLAYER_IA_SWORD_MASTER)) {
Player_UseItem(play, this, ITEM_NONE);
} else {
this->stateFlags2 ^= PLAYER_STATE2_20;
this->stateFlags2 ^= PLAYER_STATE2_NAVI_ACTIVE;
}
}
return 0;
return false;
}
s32 Player_ActionHandler_11(Player* this, PlayState* play) {
@ -9279,7 +9289,7 @@ void Player_Action_8084411C(Player* this, PlayState* play) {
} else if ((this->fallDistance < 800) &&
(this->controlStickDirections[this->controlStickDataIndex] == PLAYER_STICK_DIR_FORWARD) &&
!(this->stateFlags1 & PLAYER_STATE1_CARRYING_ACTOR)) {
func_8083BC04(this, play);
Player_SetupRoll(this, play);
return;
}
@ -9299,17 +9309,17 @@ void Player_Action_8084411C(Player* this, PlayState* play) {
}
}
static AnimSfxEntry D_8085460C[] = {
static AnimSfxEntry sRollAnimSfxList[] = {
{ NA_SE_VO_LI_SWORD_N, ANIMSFX_DATA(ANIMSFX_TYPE_VOICE, 1) },
{ NA_SE_PL_WALK_GROUND, ANIMSFX_DATA(ANIMSFX_TYPE_FLOOR_BY_AGE, 6) },
{ NA_SE_PL_ROLL, ANIMSFX_DATA(ANIMSFX_TYPE_GENERAL, 6) },
{ 0, -ANIMSFX_DATA(ANIMSFX_TYPE_LANDING, 18) },
};
void Player_Action_80844708(Player* this, PlayState* play) {
Actor* cylinderOc;
void Player_Action_Roll(Player* this, PlayState* play) {
Actor* ocCollidedActor;
s32 interruptResult;
s32 sp44;
s32 animDone;
DynaPolyActor* wallPolyActor;
s32 pad;
f32 speedTarget;
@ -9317,37 +9327,42 @@ void Player_Action_80844708(Player* this, PlayState* play) {
this->stateFlags2 |= PLAYER_STATE2_5;
cylinderOc = NULL;
sp44 = LinkAnimation_Update(play, &this->skelAnime);
ocCollidedActor = NULL;
animDone = LinkAnimation_Update(play, &this->skelAnime);
if (LinkAnimation_OnFrame(&this->skelAnime, 8.0f)) {
Player_SetInvulnerability(this, FRAMERATE_CONST(-10, -8));
}
if (func_80842964(this, play) == 0) {
if (this->av2.actionVar2 != 0) {
if (!func_80842964(this, play)) {
if (this->av2.bonked) {
Math_StepToF(&this->speedXZ, 0.0f, 2.0f);
interruptResult = Player_TryActionInterrupt(play, this, &this->skelAnime, 5.0f);
if ((interruptResult != PLAYER_INTERRUPT_NEW_ACTION) &&
((interruptResult >= PLAYER_INTERRUPT_MOVE) || sp44)) {
((interruptResult >= PLAYER_INTERRUPT_MOVE) || animDone)) {
func_8083A060(this, play);
}
} else {
// Must have a speed of 7 or above to be able to bonk into something
if (this->speedXZ >= 7.0f) {
if (((this->actor.bgCheckFlags & BGCHECKFLAG_PLAYER_WALL_INTERACT) &&
(sWorldYawToTouchedWall < 0x2000)) ||
((this->cylinder.base.ocFlags1 & OC1_HIT) &&
(cylinderOc = this->cylinder.base.oc,
((cylinderOc->id == ACTOR_EN_WOOD02) &&
(ABS((s16)(this->actor.world.rot.y - cylinderOc->yawTowardsPlayer)) > 0x6000))))) {
if (cylinderOc != NULL) {
cylinderOc->home.rot.y = 1;
(ocCollidedActor = this->cylinder.base.oc,
((ocCollidedActor->id == ACTOR_EN_WOOD02) &&
(ABS((s16)(this->actor.world.rot.y - ocCollidedActor->yawTowardsPlayer)) > 0x6000))))) {
if (ocCollidedActor != NULL) {
// The EN_WOOD02 actor uses home y rotation as a flag to signal that it has been
// bonked into and should try to spawn a drop.
ocCollidedActor->home.rot.y = 1;
} else if (this->actor.wallBgId != BGCHECK_SCENE) {
wallPolyActor = DynaPoly_GetActor(&play->colCtx, this->actor.wallBgId);
if ((wallPolyActor != NULL) && (wallPolyActor->actor.id == ACTOR_OBJ_KIBAKO2)) {
// The OBJ_KIBAKO2 actor uses home z rotation as a flag to signal that it has been
// bonked into and should break.
wallPolyActor->actor.home.rot.z = 1;
}
}
@ -9358,7 +9373,8 @@ void Player_Action_80844708(Player* this, PlayState* play) {
Player_RequestRumble(this, 255, 20, 150, 0);
Player_PlaySfx(this, NA_SE_PL_BODY_HIT);
Player_PlayVoiceSfx(this, NA_SE_VO_LI_CLIMB_END);
this->av2.actionVar2 = 1;
this->av2.bonked = true;
return;
}
}
@ -9366,12 +9382,17 @@ void Player_Action_80844708(Player* this, PlayState* play) {
if ((this->skelAnime.curFrame < 15.0f) || !Player_ActionHandler_7(this, play)) {
if (this->skelAnime.curFrame >= 20.0f) {
func_8083A060(this, play);
return;
}
Player_GetMovementSpeedAndYaw(this, &speedTarget, &yawTarget, SPEED_MODE_CURVED, play);
// `speedTarget` at this point is the speed that would be used for regular walking.
// Rolling speed is 1.5 times faster than what the walking speed would be for the current control stick
// input.
speedTarget *= 1.5f;
if ((speedTarget < 3.0f) ||
(this->controlStickDirections[this->controlStickDataIndex] != PLAYER_STICK_DIR_FORWARD)) {
speedTarget = 3.0f;
@ -9383,7 +9404,7 @@ void Player_Action_80844708(Player* this, PlayState* play) {
Actor_PlaySfx_Flagged2(&this->actor, NA_SE_PL_ROLL_DUST - SFX_FLAG);
}
Player_ProcessAnimSfxList(this, D_8085460C);
Player_ProcessAnimSfxList(this, sRollAnimSfxList);
}
}
}
@ -10563,7 +10584,7 @@ void Player_UpdateInterface(PlayState* play, Player* this) {
Player_IsZTargeting(this) && (controlStickDirection >= PLAYER_STICK_DIR_LEFT)) {
doAction = DO_ACTION_JUMP;
} else if ((this->heldItemAction >= PLAYER_IA_SWORD_MASTER) ||
((this->stateFlags2 & PLAYER_STATE2_20) &&
((this->stateFlags2 & PLAYER_STATE2_NAVI_ACTIVE) &&
(play->actorCtx.attention.naviHoverActor == NULL))) {
doAction = DO_ACTION_PUTAWAY;
}
@ -10572,10 +10593,12 @@ void Player_UpdateInterface(PlayState* play, Player* this) {
}
if (doAction != DO_ACTION_PUTAWAY) {
this->unk_837 = 20;
} else if (this->unk_837 != 0) {
this->putAwayCooldownTimer = 20;
} else if (this->putAwayCooldownTimer != 0) {
// Replace the "Put Away" Do Action label with a blank label while
// the cooldown timer is counting down
doAction = DO_ACTION_NONE;
this->unk_837--;
this->putAwayCooldownTimer--;
}
Interface_SetDoAction(play, doAction);
@ -12885,7 +12908,7 @@ void Player_Action_8084CC98(Player* this, PlayState* play) {
if ((this->csAction != PLAYER_CSACTION_NONE) ||
(!func_8083224C(play) && ((rideActor->actor.speed != 0.0f) || !Player_ActionHandler_4(this, play)) &&
!Player_ActionHandler_6(this, play))) {
!Player_ActionHandler_Roll(this, play))) {
if (!sUpperBodyIsBusy) {
if (this->av1.actionVar1 != 0) {
if (LinkAnimation_Update(play, &this->upperSkelAnime)) {