2023-02-12 00:09:02 -05:00

126 lines
2.7 KiB
C
Executable File

/*
* DESCRIPTION:
* AI for the "Crumbler" enemy.
*/
#include "crumbler.h"
static s32 crumbler_health_get(Enemy* _e, List* _l, Play* _p);
static s32 crumbler_attack_timer_max_get(Enemy* _e, List* _l, Play* _p);
/* Gets the Crumbler health. */
static s32
crumbler_health_get(Enemy* _e, List* _l, Play* _p)
{
s32 health;
health = CRUMBLER_HEALTH_BASE + ((_p->game - 1) * CRUMBLER_HEALTH_GAME_MULTIPLIER);
health = CEIL(health, CRUMBLER_HEALTH_MAX);
return health;
}
/* Gets the Crumbler attack timer max. */
static s32
crumbler_attack_timer_max_get(Enemy* _e, List* _l, Play* _p)
{
s32 attackTimerMax;
attackTimerMax = CRUMBLER_ATTACK_TIMER_MAX_BASE - ((_p->game - 1) * CRUMBLER_ATTACK_TIMER_MAX_GAME_MULTIPLIER);
attackTimerMax = FLOOR(attackTimerMax, CRUMBLER_ATTACK_TIMER_MAX_MIN);
return attackTimerMax;
}
/* Initializes the Crumbler. */
void
crumbler_init(Enemy* _e, List* _l, Play* _p)
{
Atlas atlas;
atlas_init
(
&atlas,
_p->g->textures[TEXTURE_ENEMY_CRUMBLER],
CRUMBLER_ROWS,
CRUMBLER_COLUMNS,
CRUMBLER_WIDTH,
CRUMBLER_HEIGHT
);
sprite_atlas_init
(
&_e->sprite,
&atlas,
ORIGIN_MIDDLE,
CRUMBLER_WIDTH,
CRUMBLER_HEIGHT
);
_e->shadow.r = 0;
_e->sprite.frame = 1;
}
/* Sets the Crumbler. */
void
crumbler_set(Enemy* _e, List* _l, f64 _x, f64 _y, Play* _p)
{
_e->shadow.x = _x + CRUMBLER_SHADOW_OFFSET_X;
_e->shadow.y = _y + CRUMBLER_SHADOW_OFFSET_Y;
_e->sprite.x = _e->shadow.x;
_e->sprite.y = _e->shadow.y - (CRUMBLER_ATTACK_OFFSET_Y + CRUMBLER_SHADOW_OFFSET_Y);
_e->isActive = FALSE;
_e->isActing = TRUE;
_e->attackTimer = crumbler_attack_timer_max_get(_e, _l, _p);
_e->health = crumbler_health_get(_e, _l, _p);
}
/*
* Updates Crumbler.
* Falls into the arena and then remains stationary.
*/
void
crumbler_update(Enemy* _e, List* _l, Play* _p)
{
if (_e->isActing)
{
f64 progress;
_e->attackTimer--;
progress = 1 - ((f64)_e->attackTimer / crumbler_attack_timer_max_get(_e, _l, _p));
_e->shadow.r = CRUMBLER_SHADOW_RADIUS * progress;
_e->sprite.y = _e->shadow.y - CRUMBLER_SHADOW_OFFSET_Y - (CRUMBLER_ATTACK_OFFSET_Y * (1 - progress));
if (_e->attackTimer <= 0)
{
_e->isActing = FALSE;
_e->isActive = TRUE;
_e->shadow.r = CRUMBLER_SHADOW_RADIUS;
_e->sprite.frame = 0;
sound_play(_p->g->sounds[SOUND_RUMBLE], -1);
}
}
else
{
f64 progress;
_e->animationTimer--;
progress = 1 - ((f64)_e->animationTimer / CRUMBLER_ANIMATION_TIMER_MAX);
_e->sprite.squash = (SPRITE_SQUASH_DEFAULT + cos((ROTATION_MAX_RAD * progress)) * CRUMBLER_SQUASH_MULTIPLIER);
_e->sprite.stretch = (SPRITE_STRETCH_DEFAULT + cos((ROTATION_MAX_RAD * progress)) * CRUMBLER_STRETCH_MULTIPLIER);
if (_e->animationTimer <= 0)
_e->animationTimer = CRUMBLER_ANIMATION_TIMER_MAX;
}
}