173 lines
4.7 KiB
C
173 lines
4.7 KiB
C
#include <gint/defs/util.h>
|
|
#include "skills.h"
|
|
#include "comp/fighter.h"
|
|
#include "comp/physical.h"
|
|
#include "comp/visible.h"
|
|
#include "enemies.h"
|
|
#include "aoe.h"
|
|
|
|
fixed_t skill_cooldown(int skill)
|
|
{
|
|
if(skill == SKILL_DASH)
|
|
return fix(1.0);
|
|
else if(skill == SKILL_SPEED)
|
|
return fix(5.0);
|
|
else if(skill == AOE_PROJECTILE)
|
|
return fix(2.0);
|
|
else if(skill == AOE_PROJECTILE_FAST)
|
|
return fix(0.2);
|
|
else if(skill == AOE_SHOCK)
|
|
return fix(6.0);
|
|
else if(skill == AOE_JUDGEMENT)
|
|
return fix(3.0);
|
|
else if(skill == AOE_BULLET)
|
|
return fix(4.0);
|
|
else if(skill == AOE_FIRE_CHARGE
|
|
|| skill == AOE_WATER_CHARGE
|
|
|| skill == AOE_CHEMICAL_CHARGE)
|
|
return fix(3.0);
|
|
|
|
return fix(0.0);
|
|
}
|
|
|
|
bool skill_use(game_t *game, entity_t *e, int slot, vec2 dir)
|
|
{
|
|
fighter_t *f = getcomp(e, fighter);
|
|
int skill = f->skills[slot];
|
|
|
|
if(skill < 0 || f->actions_cooldown[slot] > 0)
|
|
return false;
|
|
f->actions_cooldown[slot] = skill_cooldown(skill);
|
|
|
|
if(skill == SKILL_DASH) {
|
|
mechanical_dash(e, frdir(dir));
|
|
}
|
|
else if(skill == SKILL_SPEED) {
|
|
fighter_effect_speed(e, fix(2.0));
|
|
}
|
|
else if(skill == AOE_PROJECTILE) {
|
|
if(f->current_attack)
|
|
return false;
|
|
entity_t *aoe = aoe_make_attack(AOE_PROJECTILE, e, dir);
|
|
game_add_entity(game, aoe);
|
|
|
|
if(!f->enemy)
|
|
visible_set_anim(e, &anims_player_Attack, 2);
|
|
else
|
|
visible_set_anim(e, f->enemy->id->anim_attack, 2);
|
|
}
|
|
else if(skill == AOE_PROJECTILE_FAST) {
|
|
if(f->current_attack)
|
|
return false;
|
|
entity_t *aoe = aoe_make_attack(AOE_PROJECTILE_FAST, e, dir);
|
|
|
|
getcomp(aoe, visible)->z = fix(0.25);
|
|
game_add_entity(game, aoe);
|
|
|
|
if(!f->enemy)
|
|
visible_set_anim(e, &anims_player_Attack, 2);
|
|
else
|
|
visible_set_anim(e, f->enemy->id->anim_attack, 2);
|
|
}
|
|
else if(skill == AOE_SHOCK) {
|
|
if(f->current_attack)
|
|
return false;
|
|
entity_t *aoe = aoe_make_attack(AOE_SHOCK, e, dir);
|
|
game_add_entity(game, aoe);
|
|
|
|
if(!f->enemy)
|
|
visible_set_anim(e, &anims_player_Attack, 2);
|
|
else
|
|
visible_set_anim(e, f->enemy->id->anim_attack, 2);
|
|
|
|
f->current_attack = aoe;
|
|
f->attack_follows_movement = true;
|
|
fighter_effect_stun(e, fix(0.5));
|
|
game_shake(game, 5, fix(0.7));
|
|
}
|
|
else if(skill == AOE_JUDGEMENT) {
|
|
if(f->current_attack)
|
|
return false;
|
|
entity_t *aoe = aoe_make_attack(AOE_JUDGEMENT, e, dir);
|
|
game_add_entity(game, aoe);
|
|
|
|
if(!f->enemy)
|
|
visible_set_anim(e, &anims_player_Attack, 2);
|
|
else
|
|
visible_set_anim(e, f->enemy->id->anim_attack, 2);
|
|
|
|
game_shake(game, 3, fix(1.3));
|
|
}
|
|
else if(skill == AOE_BULLET) {
|
|
if(f->current_attack)
|
|
return false;
|
|
entity_t *aoe = aoe_make_attack(AOE_BULLET, e, dir);
|
|
game_add_entity(game, aoe);
|
|
|
|
if(!f->enemy)
|
|
visible_set_anim(e, &anims_player_Attack, 2);
|
|
else
|
|
visible_set_anim(e, f->enemy->id->anim_attack, 2);
|
|
}
|
|
else if(skill == AOE_FIRE_CHARGE
|
|
|| skill == AOE_WATER_CHARGE
|
|
|| skill == AOE_CHEMICAL_CHARGE) {
|
|
if(f->current_attack)
|
|
return false;
|
|
entity_t *aoe = aoe_make_attack(skill, e, dir);
|
|
game_add_entity(game, aoe);
|
|
|
|
f->current_attack = aoe;
|
|
f->attack_follows_movement = true;
|
|
|
|
/* This skill is used by enemies, the AI will set the animation
|
|
themselves on a per-enemy basis */
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
bool skill_render_get(int skill, image_t **img, int *left, int *top)
|
|
{
|
|
extern bopti_image_t img_skillicons;
|
|
*img = &img_skillicons;
|
|
*top = 0;
|
|
|
|
int base = 3;
|
|
|
|
if(skill == SKILL_DASH)
|
|
*left = 23 * (base + 0);
|
|
else if(skill == AOE_SHOCK)
|
|
*left = 23 * (base + 1);
|
|
else if(skill == AOE_JUDGEMENT)
|
|
*left = 23 * (base + 2);
|
|
else if(skill == AOE_BULLET)
|
|
*left = 23 * (base + 3);
|
|
else
|
|
return false;
|
|
|
|
return true;
|
|
}
|
|
|
|
void skill_render(int x, int y, int skill, int bg, int color)
|
|
{
|
|
image_t *img;
|
|
int left, top;
|
|
bool exists = skill_render_get(skill, &img, &left, &top);
|
|
|
|
if(bg > 0)
|
|
dsubimage(x, y, img, 23*(bg-1), 0, 23, 23, DIMAGE_NONE);
|
|
if(!exists)
|
|
return;
|
|
|
|
dsubimage(x, y, img, left, top, 23, 23, DIMAGE_NONE);
|
|
|
|
/* Hacky color change */
|
|
for(int dy = 0; dy < 23; dy++)
|
|
for(int dx = 0; dx < 23; dx++) {
|
|
int i = (y+dy) * DWIDTH + (x+dx);
|
|
if(gint_vram[i] == 0xffff)
|
|
gint_vram[i] = color;
|
|
}
|
|
}
|