Paper Mario DX
Paper Mario (N64) modding
 
Loading...
Searching...
No Matches
body_slam.c
Go to the documentation of this file.
1#include "common.h"
2#include "battle/action_cmd.h"
3
4#define NAMESPACE action_command_body_slam
5
6extern s32 actionCmdTableBodySlam[];
7
8// indices into ActionCommandStatus::hudElements for this action command
9enum {
14};
15
16// how much to add to the meter per frame
17#define METER_FILL_RATE 154
18
19API_CALLABLE(N(init)) {
21 BattleStatus* battleStatus = &gBattleStatus;
22 HudElemID hid;
23
24 battleStatus->maxActionQuality = 100;
26 battleStatus->actionResult = ACTION_RESULT_NONE;
27 if (battleStatus->actionCommandMode == AC_MODE_NOT_LEARNED) {
28 battleStatus->actionQuality = 0;
29 return ApiStatus_DONE2;
30 }
31
34 acs->showHud = TRUE;
35 acs->state = AC_STATE_INIT;
36 acs->wrongButtonPressed = FALSE;
37 acs->meterFillLevel = 0;
38 acs->meterFillWidth = 0;
39 acs->isMeterFilled = FALSE;
40 battleStatus->actionQuality = 0;
41 acs->hudPosX = -48;
42 acs->hudPosY = 80;
43
45 acs->hudElemIDs[HIDX_BUTTON] = hid;
49
51 acs->hudElemIDs[HIDX_METER] = hid;
52 hud_element_set_render_pos(hid, acs->hudPosX, acs->hudPosY + 28);
55
57 acs->hudElemIDs[HIDX_FRAME] = hid;
58 hud_element_set_render_pos(hid, acs->hudPosX, acs->hudPosY + 28);
61
63 acs->hudElemIDs[HIDX_LIGHT] = hid;
64 hud_element_set_render_pos(hid, acs->hudPosX + 41, acs->hudPosY + 22);
67 return ApiStatus_DONE2;
68}
69
70API_CALLABLE(N(start)) {
72 BattleStatus* battleStatus = &gBattleStatus;
73 Bytecode* args = script->ptrReadPos;
74
75 if (battleStatus->actionCommandMode == AC_MODE_NOT_LEARNED) {
76 battleStatus->actionQuality = 0;
77 return ApiStatus_DONE2;
78 }
79
81
82 acs->prepareTime = evt_get_variable(script, *args++);
83 acs->duration = evt_get_variable(script, *args++);
84 acs->difficulty = evt_get_variable(script, *args++);
86 acs->statusChance = evt_get_variable(script, *args++); // unused
87
88 acs->wrongButtonPressed = FALSE;
89 acs->meterFillLevel = 0;
90 acs->meterFillWidth = 0;
91 battleStatus->actionQuality = 0;
92 battleStatus->actionResult = ACTION_RESULT_NONE;
93 battleStatus->maxActionQuality = acs->mashMeterCutoffs[(acs->mashMeterNumIntervals - 1)];
94 battleStatus->flags1 &= ~BS_FLAGS1_FREE_ACTION_COMMAND;
95 acs->state = AC_STATE_START;
96
98
99 return ApiStatus_DONE2;
100}
101
102void N(update)(void) {
104 BattleStatus* battleStatus = &gBattleStatus;
105 HudElemID hid;
106
107 switch (acs->state) {
108 case AC_STATE_INIT:
110
111 hid = acs->hudElemIDs[HIDX_BUTTON];
112 hud_element_set_alpha(hid, 255);
113 if (acs->showHud) {
115 }
116
117 hid = acs->hudElemIDs[HIDX_METER];
118 hud_element_set_alpha(hid, 255);
119 if (acs->showHud) {
121 }
122
123 hid = acs->hudElemIDs[HIDX_LIGHT];
124 hud_element_set_alpha(hid, 255);
125 if (acs->showHud) {
127 }
128
129 hid = acs->hudElemIDs[HIDX_FRAME];
130 hud_element_set_alpha(hid, 255);
131 if (acs->showHud) {
133 }
134
135 acs->state = AC_STATE_APPEAR;
136 break;
137 case AC_STATE_APPEAR:
139 acs->hudPosX += 20;
140 if (acs->hudPosX > 50) {
141 acs->hudPosX = 50;
142 }
147 break;
148 case AC_STATE_START:
150 if (acs->prepareTime != 0) {
151 acs->prepareTime--;
152 return;
153 }
155 acs->meterFillLevel = 0;
156 acs->escapeThreshold = 0;
157 acs->stateTimer = acs->duration;
159 acs->state = AC_STATE_ACTIVE;
160
161 // fallthrough
162 case AC_STATE_ACTIVE:
164
165 // check for meter-filling input
166 if (battleStatus->curButtonsDown & BUTTON_A) {
169 } else {
170 acs->stateTimer = 0;
171 }
172
173 // handle meter reaching 100%
174 if (acs->meterFillLevel >= MAX_MASH_UNITS) {
178 if (!acs->isMeterFilled) {
180 acs->isMeterFilled = TRUE;
181 }
182 }
183
184 battleStatus->actionProgress = acs->meterFillLevel / ONE_PCT_MASH;
186 if (acs->stateTimer != 0) {
187 acs->stateTimer--;
188 return;
189 }
190
191 if (acs->escapeThreshold < MAX_MASH_UNITS) {
192 battleStatus->actionQuality = AC_QUALITY_FAILED;
193 } else {
194 s32 window = battleStatus->actionCmdDifficultyTable[acs->difficulty] * METER_FILL_RATE;
195 // release needs to be within 2 frames + modifier from difficulty table
196 if (acs->escapeThreshold - window >= MAX_MASH_UNITS + 2 * METER_FILL_RATE + 1) {
197 battleStatus->actionQuality = AC_QUALITY_FAILED;
198 } else {
199 battleStatus->actionQuality = 1;
200 }
201 }
202
203 battleStatus->actionResult = ACTION_RESULT_FAIL;
204 if (battleStatus->actionQuality == 1) {
206 }
207
210 acs->stateTimer = 5;
211 acs->state = AC_STATE_DISPOSE;
212 break;
213 case AC_STATE_DISPOSE:
214 if (acs->stateTimer != 0) {
215 acs->stateTimer--;
216 return;
217 }
219 break;
220 }
221}
222
235
BSS ActionCommandStatus gActionCommandStatus
Definition action_cmd.c:91
void draw_mash_meter_multicolor(s32 posX, s32 posY, s32 fillValue)
Definition action_cmd.c:226
void action_command_free(void)
Definition action_cmd.c:446
void increment_action_command_attempt_count(void)
Definition action_cmd.c:641
s32 adjust_action_command_difficulty(s32 difficultyLevel)
Definition action_cmd.c:101
void increment_action_command_success_count(void)
Definition action_cmd.c:655
void action_command_init_status(void)
Definition action_cmd.c:256
#define AC_QUALITY_FAILED
Definition action_cmd.h:66
HudScript HES_AButton
HudElemID hudElemIDs[16]
Definition action_cmd.h:83
HudScript HES_TimingReady
@ AC_STATE_APPEAR
Definition action_cmd.h:35
@ AC_STATE_DISPOSE
Definition action_cmd.h:38
@ AC_STATE_INIT
Definition action_cmd.h:34
@ AC_STATE_ACTIVE
Definition action_cmd.h:37
@ AC_STATE_START
Definition action_cmd.h:36
HudScript HES_TimingWait
#define ONE_PCT_MASH
Definition action_cmd.h:69
HudScript HES_BlueMeter
HudScript HES_AButtonDown
HudScript HES_FillGaugeResult
@ AC_MODE_NOT_LEARNED
Definition action_cmd.h:60
#define MAX_MASH_UNITS
Definition action_cmd.h:75
#define METER_FILL_RATE
Definition body_slam.c:17
void N free(void)
Definition body_slam.c:236
s32 actionCmdTableBodySlam[]
Definition action_cmd.c:39
void N update(void)
Definition body_slam.c:102
@ HIDX_LIGHT
Definition body_slam.c:12
@ HIDX_METER
Definition body_slam.c:11
@ HIDX_BUTTON
Definition body_slam.c:10
@ HIDX_FRAME
Definition body_slam.c:13
void N draw(void)
Definition body_slam.c:223
s32 HudElemID
@ ACTION_COMMAND_BODY_SLAM
Definition enums.h:3484
@ BUTTON_A
Definition enums.h:2790
@ SOUND_TIMING_BAR_GO
Definition enums.h:953
@ SOUND_LOOP_CHARGE_METER
Definition enums.h:1646
@ ACTION_RESULT_NONE
Definition enums.h:1963
@ ACTION_RESULT_FAIL
Definition enums.h:1967
#define ApiStatus_DONE2
Definition evt.h:118
s32 Bytecode
Definition evt.h:7
void btl_set_popup_duration(s32 duration)
s32 evt_get_variable(Evt *script, Bytecode var)
Definition evt.c:1689
void hud_element_get_render_pos(s32 id, s32 *x, s32 *y)
void hud_element_set_alpha(s32 id, s32 opacity)
void hud_element_set_script(s32 id, HudScript *anim)
void hud_element_set_render_depth(s32 id, s32 z)
void hud_element_set_render_pos(s32 id, s32 x, s32 y)
s32 hud_element_create(HudScript *anim)
Creates a new HUD element and returns its ID.
void hud_element_set_flags(s32 id, s32 flags)
Turns on the given flags.
void hud_element_clear_flags(s32 id, s32 flags)
Turns off the given flags.
void hud_element_draw_clipped(s32 id)
void hud_element_free(s32 id)
@ HUD_ELEMENT_FLAG_DISABLED
Definition hud_element.h:72
@ HUD_ELEMENT_FLAG_80
Definition hud_element.h:78
void sfx_stop_sound(s32 soundID)
Definition sfx.c:507
void sfx_adjust_env_sound_params(s32 soundID, u8 volume, u8 pan, s16 pitchShift)
Definition sfx.c:492
void sfx_play_sound_with_params(s32 soundID, u8 volume, u8 pan, s16 pitchShift)
Definition sfx.c:458
void sfx_play_sound(s32 soundID)
Definition sfx.c:517
#define POPUP_MSG_OFF
Definition battle.h:270
#define POPUP_MSG_ON
Definition battle.h:269
s32 * actionCmdDifficultyTable
BattleStatus gBattleStatus
Definition battle.c:11
void N init(Npc *bombette)
Definition bombette.c:66