Adds skills, 'flurry' skill and sip_potion skill.
Removes shift-h sipping.
This commit is contained in:
parent
20cb94b529
commit
2253479532
|
@ -137,14 +137,14 @@ if (NOT WIN32)
|
||||||
)
|
)
|
||||||
endif (NOT WIN32)
|
endif (NOT WIN32)
|
||||||
|
|
||||||
if (WIN32)
|
if (MSVC)
|
||||||
set_target_properties(breakhack PROPERTIES LINK_FLAGS_DEBUG "/SUBSYSTEM:CONSOLE")
|
set_target_properties(breakhack PROPERTIES LINK_FLAGS_DEBUG "/SUBSYSTEM:CONSOLE")
|
||||||
set_target_properties(breakhack PROPERTIES COMPILE_DEFINITIONS_DEBUG "_CONSOLE")
|
set_target_properties(breakhack PROPERTIES COMPILE_DEFINITIONS_DEBUG "_CONSOLE")
|
||||||
set_target_properties(breakhack PROPERTIES LINK_FLAGS_RELWITHDEBINFO "/SUBSYSTEM:CONSOLE")
|
set_target_properties(breakhack PROPERTIES LINK_FLAGS_RELWITHDEBINFO "/SUBSYSTEM:CONSOLE")
|
||||||
set_target_properties(breakhack PROPERTIES COMPILE_DEFINITIONS_RELWITHDEBINFO "_CONSOLE")
|
set_target_properties(breakhack PROPERTIES COMPILE_DEFINITIONS_RELWITHDEBINFO "_CONSOLE")
|
||||||
set_target_properties(breakhack PROPERTIES LINK_FLAGS_RELEASE "/SUBSYSTEM:WINDOWS")
|
set_target_properties(breakhack PROPERTIES LINK_FLAGS_RELEASE "/SUBSYSTEM:WINDOWS")
|
||||||
set_target_properties(breakhack PROPERTIES LINK_FLAGS_MINSIZEREL "/SUBSYSTEM:WINDOWS")
|
set_target_properties(breakhack PROPERTIES LINK_FLAGS_MINSIZEREL "/SUBSYSTEM:WINDOWS")
|
||||||
endif (WIN32)
|
endif (MSVC)
|
||||||
|
|
||||||
# TESTS:
|
# TESTS:
|
||||||
IF (CHECK_FOUND AND NOT WIN32)
|
IF (CHECK_FOUND AND NOT WIN32)
|
||||||
|
@ -187,7 +187,6 @@ if (NOT CMAKE_BUILD_TYPE MATCHES Debug)
|
||||||
)
|
)
|
||||||
endif (NOT CMAKE_BUILD_TYPE MATCHES Debug)
|
endif (NOT CMAKE_BUILD_TYPE MATCHES Debug)
|
||||||
|
|
||||||
SET(CMAKE_INSTALL_UCRT_LIBRARIES TRUE)
|
|
||||||
SET(CMAKE_INSTALL_SYSTEM_RUNTIME_COMPONENT "Release")
|
SET(CMAKE_INSTALL_SYSTEM_RUNTIME_COMPONENT "Release")
|
||||||
SET(CMAKE_INSTALL_SYSTEM_RUNTIME_DESTINATION ".")
|
SET(CMAKE_INSTALL_SYSTEM_RUNTIME_DESTINATION ".")
|
||||||
SET(CMAKE_INSTALL_SYSTEM_RUNTIME_LIBS
|
SET(CMAKE_INSTALL_SYSTEM_RUNTIME_LIBS
|
||||||
|
|
|
@ -95,7 +95,7 @@ static Item *
|
||||||
create_treasure(int current_level)
|
create_treasure(int current_level)
|
||||||
{
|
{
|
||||||
double amt;
|
double amt;
|
||||||
char label[50];
|
char label[50] = "";
|
||||||
unsigned int highest_treasure;
|
unsigned int highest_treasure;
|
||||||
unsigned int value;
|
unsigned int value;
|
||||||
|
|
||||||
|
@ -109,25 +109,25 @@ create_treasure(int current_level)
|
||||||
highest_treasure = GOLD;
|
highest_treasure = GOLD;
|
||||||
}
|
}
|
||||||
|
|
||||||
value = get_random(highest_treasure);
|
value = get_random(highest_treasure) - 1;
|
||||||
|
|
||||||
SDL_Rect clip = CLIP16(0, 0);
|
SDL_Rect clip = CLIP16(0, 0);
|
||||||
switch (value) {
|
switch (value) {
|
||||||
case COPPER:
|
case COPPER:
|
||||||
m_sprintf(&label[0], 50, "%.0f copper", amt);
|
m_sprintf(label, 50, "%.0f copper", amt);
|
||||||
amt /= 100;
|
amt /= 100;
|
||||||
break;
|
break;
|
||||||
case SILVER:
|
case SILVER:
|
||||||
m_sprintf(&label[0], 50, "%.0f silver", amt);
|
m_sprintf(label, 50, "%.0f silver", amt);
|
||||||
clip.x = 48;
|
clip.x = 48;
|
||||||
amt /= 10;
|
amt /= 10;
|
||||||
break;
|
break;
|
||||||
case GOLD:
|
case GOLD:
|
||||||
m_sprintf(&label[0], 50, "%.0f gold", amt);
|
m_sprintf(label, 50, "%.0f gold", amt);
|
||||||
clip.y = 16;
|
clip.y = 16;
|
||||||
break;
|
break;
|
||||||
case PLATINUM:
|
case PLATINUM:
|
||||||
m_sprintf(&label[0], 50, "%.0f platinum", amt);
|
m_sprintf(label, 50, "%.0f platinum", amt);
|
||||||
clip.x = 48;
|
clip.x = 48;
|
||||||
clip.y = 16;
|
clip.y = 16;
|
||||||
amt *= 10;
|
amt *= 10;
|
||||||
|
|
|
@ -489,7 +489,7 @@ run_game(void)
|
||||||
RIGHT_GUI_HEIGHT, &gCamera);
|
RIGHT_GUI_HEIGHT, &gCamera);
|
||||||
|
|
||||||
SDL_RenderSetViewport(gRenderer, &skillBarViewport);
|
SDL_RenderSetViewport(gRenderer, &skillBarViewport);
|
||||||
skillbar_render(gSkillBar, &gCamera);
|
skillbar_render(gSkillBar, gPlayer, &gCamera);
|
||||||
|
|
||||||
SDL_RenderSetViewport(gRenderer, &bottomGuiViewport);
|
SDL_RenderSetViewport(gRenderer, &bottomGuiViewport);
|
||||||
gui_render_log(gGui, BOTTOM_GUI_WIDTH,
|
gui_render_log(gGui, BOTTOM_GUI_WIDTH,
|
||||||
|
|
|
@ -94,7 +94,7 @@ particle_engine_bloodspray(Position pos, Dimension dim, unsigned int count)
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
create_explosion(Position pos, Dimension dim, size_t c_count, ...)
|
create_explosion(Position pos, Dimension dim, unsigned int c_count, ...)
|
||||||
{
|
{
|
||||||
SDL_Color *colors = ec_malloc(c_count * sizeof(SDL_Color));
|
SDL_Color *colors = ec_malloc(c_count * sizeof(SDL_Color));
|
||||||
|
|
||||||
|
|
133
src/player.c
133
src/player.c
|
@ -113,15 +113,8 @@ has_collided(Player *player, RoomMatrix *matrix)
|
||||||
else
|
else
|
||||||
gui_log("You missed %s", space->monster->lclabel);
|
gui_log("You missed %s", space->monster->lclabel);
|
||||||
|
|
||||||
if (space->monster->stats.hp <= 0) {
|
player_monster_kill_check(player, space->monster);
|
||||||
unsigned int gained_xp = 5 * space->monster->stats.lvl;
|
|
||||||
player->kills += 1;
|
|
||||||
|
|
||||||
mixer_play_effect(DEATH);
|
|
||||||
gui_log("You killed %s and gained %d xp",
|
|
||||||
space->monster->lclabel, gained_xp);
|
|
||||||
player_gain_xp(player, gained_xp);
|
|
||||||
}
|
|
||||||
} else if (collided) {
|
} else if (collided) {
|
||||||
mixer_play_effect(BONK);
|
mixer_play_effect(BONK);
|
||||||
gui_log("Ouch! There is something in the way");
|
gui_log("Ouch! There is something in the way");
|
||||||
|
@ -146,6 +139,11 @@ player_step(Player *p)
|
||||||
p->steps++;
|
p->steps++;
|
||||||
p->missText->pos = p->sprite->pos;
|
p->missText->pos = p->sprite->pos;
|
||||||
p->hitText->pos = p->sprite->pos;
|
p->hitText->pos = p->sprite->pos;
|
||||||
|
|
||||||
|
for (size_t i = 0; i < PLAYER_SKILL_COUNT; ++i) {
|
||||||
|
if (p->skills[i] != NULL && p->skills[i]->resetCountdown > 0)
|
||||||
|
p->skills[i]->resetCountdown--;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
|
@ -192,8 +190,8 @@ move_down(Player *player, RoomMatrix *matrix)
|
||||||
player_step(player);
|
player_step(player);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
void
|
||||||
sip_health(Player *player)
|
player_sip_health(Player *player)
|
||||||
{
|
{
|
||||||
if (player->potion_sips > 0) {
|
if (player->potion_sips > 0) {
|
||||||
--player->potion_sips;
|
--player->potion_sips;
|
||||||
|
@ -244,17 +242,92 @@ handle_movement_input(Player *player, RoomMatrix *matrix, SDL_Event *event)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
check_skill_activation(Player *player, RoomMatrix *matrix, SDL_Event *event)
|
||||||
|
{
|
||||||
|
// TODO(Linus): This could be "smarter"
|
||||||
|
unsigned int selected = 0;
|
||||||
|
if (keyboard_press(SDLK_1, event)) {
|
||||||
|
selected = 1;
|
||||||
|
}
|
||||||
|
else if (keyboard_press(SDLK_2, event)) {
|
||||||
|
selected = 2;
|
||||||
|
}
|
||||||
|
else if (keyboard_press(SDLK_3, event)) {
|
||||||
|
selected = 3;
|
||||||
|
}
|
||||||
|
else if (keyboard_press(SDLK_4, event)) {
|
||||||
|
selected = 4;
|
||||||
|
}
|
||||||
|
else if (keyboard_press(SDLK_5, event)) {
|
||||||
|
selected = 5;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (selected == 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
for (size_t i = 0; i < PLAYER_SKILL_COUNT; ++i) {
|
||||||
|
if (!player->skills[i])
|
||||||
|
continue;
|
||||||
|
|
||||||
|
Skill *skill = player->skills[i];
|
||||||
|
skill->active = (selected - 1) == i && !skill->active && skill->resetCountdown == 0;
|
||||||
|
if (skill->active && skill->instantUse) {
|
||||||
|
SkillData skillData = { player, matrix, VECTOR2D_NODIR };
|
||||||
|
skill->active = false;
|
||||||
|
skill->use(skill, &skillData);
|
||||||
|
if (skill->actionRequired)
|
||||||
|
player_step(player);
|
||||||
|
skill->resetCountdown = skill->resetTime;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool
|
||||||
|
check_skill_trigger(Player *player, RoomMatrix *matrix, SDL_Event *event)
|
||||||
|
{
|
||||||
|
int activeSkill = -1;
|
||||||
|
for (size_t i = 0; i < PLAYER_SKILL_COUNT; ++i) {
|
||||||
|
if (player->skills[i] && player->skills[i]->active) {
|
||||||
|
activeSkill = i;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (activeSkill < 0)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
Vector2d dir;
|
||||||
|
if (keyboard_direction_press(UP, event))
|
||||||
|
dir = VECTOR2D_UP;
|
||||||
|
else if (keyboard_direction_press(DOWN, event))
|
||||||
|
dir = VECTOR2D_DOWN;
|
||||||
|
else if (keyboard_direction_press(LEFT, event))
|
||||||
|
dir = VECTOR2D_LEFT;
|
||||||
|
else if (keyboard_direction_press(RIGHT, event))
|
||||||
|
dir = VECTOR2D_RIGHT;
|
||||||
|
else
|
||||||
|
return false;
|
||||||
|
|
||||||
|
SkillData skillData = { player, matrix, dir };
|
||||||
|
player->skills[activeSkill]->use(player->skills[activeSkill], &skillData);
|
||||||
|
player->skills[activeSkill]->active = false;
|
||||||
|
if (player->skills[activeSkill]->actionRequired)
|
||||||
|
player_step(player);
|
||||||
|
player->skills[activeSkill]->resetCountdown = player->skills[activeSkill]->resetTime;
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
handle_player_input(Player *player, RoomMatrix *matrix, SDL_Event *event)
|
handle_player_input(Player *player, RoomMatrix *matrix, SDL_Event *event)
|
||||||
{
|
{
|
||||||
if (event->type != SDL_KEYDOWN)
|
if (event->type != SDL_KEYDOWN)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (keyboard_mod_press(SDLK_h, KMOD_SHIFT, event)) {
|
check_skill_activation(player, matrix, event);
|
||||||
sip_health(player);
|
if (!check_skill_trigger(player, matrix, event))
|
||||||
} else {
|
|
||||||
handle_movement_input(player, matrix, event);
|
handle_movement_input(player, matrix, event);
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
|
@ -282,7 +355,7 @@ player_create(class_t class, SDL_Renderer *renderer)
|
||||||
player->sprite = sprite_create();
|
player->sprite = sprite_create();
|
||||||
player->total_steps = 0;
|
player->total_steps = 0;
|
||||||
player->steps = 0;
|
player->steps = 0;
|
||||||
player->xp = 0;
|
player->xp = 0;
|
||||||
player->hits = 0;
|
player->hits = 0;
|
||||||
player->kills = 0;
|
player->kills = 0;
|
||||||
player->misses = 0;
|
player->misses = 0;
|
||||||
|
@ -290,6 +363,10 @@ player_create(class_t class, SDL_Renderer *renderer)
|
||||||
player->potion_sips = 0;
|
player->potion_sips = 0;
|
||||||
player->class = class;
|
player->class = class;
|
||||||
|
|
||||||
|
for (size_t i = 0; i < PLAYER_SKILL_COUNT; ++i) {
|
||||||
|
player->skills[i] = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
char asset[100];
|
char asset[100];
|
||||||
switch (class) {
|
switch (class) {
|
||||||
case ENGINEER:
|
case ENGINEER:
|
||||||
|
@ -311,9 +388,12 @@ player_create(class_t class, SDL_Renderer *renderer)
|
||||||
case WARRIOR:
|
case WARRIOR:
|
||||||
m_strcpy(asset, 100, "Commissions/Warrior.png");
|
m_strcpy(asset, 100, "Commissions/Warrior.png");
|
||||||
player->stats = (Stats) WARRIOR_STATS;
|
player->stats = (Stats) WARRIOR_STATS;
|
||||||
|
player->skills[0] = skill_create(FLURRY);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
player->skills[4] = skill_create(SIP_HEALTH);
|
||||||
|
|
||||||
sprite_load_texture(player->sprite, asset, 0, renderer);
|
sprite_load_texture(player->sprite, asset, 0, renderer);
|
||||||
player->sprite->pos = (Position) { TILE_DIMENSION, TILE_DIMENSION };
|
player->sprite->pos = (Position) { TILE_DIMENSION, TILE_DIMENSION };
|
||||||
player->sprite->dim = GAME_DIMENSION;
|
player->sprite->dim = GAME_DIMENSION;
|
||||||
|
@ -334,6 +414,23 @@ ExperienceData player_get_xp_data(Player *p)
|
||||||
return data;
|
return data;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
player_monster_kill_check(Player *player, Monster *monster)
|
||||||
|
{
|
||||||
|
if (!monster)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (monster->stats.hp <= 0) {
|
||||||
|
unsigned int gained_xp = 5 * monster->stats.lvl;
|
||||||
|
player->kills += 1;
|
||||||
|
|
||||||
|
mixer_play_effect(DEATH);
|
||||||
|
gui_log("You killed %s and gained %d xp",
|
||||||
|
monster->lclabel, gained_xp);
|
||||||
|
player_gain_xp(player, gained_xp);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
player_hit(Player *p, unsigned int dmg)
|
player_hit(Player *p, unsigned int dmg)
|
||||||
{
|
{
|
||||||
|
@ -393,5 +490,11 @@ player_destroy(Player *player)
|
||||||
actiontext_destroy(player->hitText);
|
actiontext_destroy(player->hitText);
|
||||||
actiontext_destroy(player->missText);
|
actiontext_destroy(player->missText);
|
||||||
|
|
||||||
|
for (size_t i = 0; i < PLAYER_SKILL_COUNT; ++i) {
|
||||||
|
if (player->skills[i])
|
||||||
|
skill_destroy(player->skills[i]);
|
||||||
|
player->skills[i] = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
free(player);
|
free(player);
|
||||||
}
|
}
|
||||||
|
|
10
src/player.h
10
src/player.h
|
@ -24,6 +24,9 @@
|
||||||
#include "stats.h"
|
#include "stats.h"
|
||||||
#include "actiontext.h"
|
#include "actiontext.h"
|
||||||
#include "camera.h"
|
#include "camera.h"
|
||||||
|
#include "skill.h"
|
||||||
|
|
||||||
|
#define PLAYER_SKILL_COUNT 5
|
||||||
|
|
||||||
enum PlayerClass { ENGINEER, MAGE, PALADIN, ROGUE, WARRIOR };
|
enum PlayerClass { ENGINEER, MAGE, PALADIN, ROGUE, WARRIOR };
|
||||||
typedef enum PlayerClass class_t;
|
typedef enum PlayerClass class_t;
|
||||||
|
@ -49,6 +52,7 @@ typedef struct Player_t {
|
||||||
double gold;
|
double gold;
|
||||||
unsigned int potion_sips;
|
unsigned int potion_sips;
|
||||||
class_t class;
|
class_t class;
|
||||||
|
Skill *skills[PLAYER_SKILL_COUNT];
|
||||||
void (*handle_event)(struct Player_t*, RoomMatrix*, SDL_Event*);
|
void (*handle_event)(struct Player_t*, RoomMatrix*, SDL_Event*);
|
||||||
} Player;
|
} Player;
|
||||||
|
|
||||||
|
@ -58,6 +62,12 @@ player_create(class_t, SDL_Renderer*);
|
||||||
ExperienceData
|
ExperienceData
|
||||||
player_get_xp_data(Player*);
|
player_get_xp_data(Player*);
|
||||||
|
|
||||||
|
void
|
||||||
|
player_monster_kill_check(Player*, Monster*);
|
||||||
|
|
||||||
|
void
|
||||||
|
player_sip_health(Player*);
|
||||||
|
|
||||||
void
|
void
|
||||||
player_hit(Player*, unsigned int dmg);
|
player_hit(Player*, unsigned int dmg);
|
||||||
|
|
||||||
|
|
61
src/skill.c
61
src/skill.c
|
@ -21,6 +21,13 @@
|
||||||
#include "texturecache.h"
|
#include "texturecache.h"
|
||||||
#include "skill.h"
|
#include "skill.h"
|
||||||
#include "util.h"
|
#include "util.h"
|
||||||
|
#include "player.h"
|
||||||
|
#include "roommatrix.h"
|
||||||
|
#include "stats.h"
|
||||||
|
#include "monster.h"
|
||||||
|
#include "mixer.h"
|
||||||
|
#include "gui.h"
|
||||||
|
#include "random.h"
|
||||||
|
|
||||||
static Skill *
|
static Skill *
|
||||||
create_default(const char *s_label, Sprite *s)
|
create_default(const char *s_label, Sprite *s)
|
||||||
|
@ -30,6 +37,9 @@ create_default(const char *s_label, Sprite *s)
|
||||||
skill->resetTime = 5;
|
skill->resetTime = 5;
|
||||||
skill->resetCountdown = 0;
|
skill->resetCountdown = 0;
|
||||||
skill->icon = s;
|
skill->icon = s;
|
||||||
|
skill->actionRequired = true;
|
||||||
|
skill->instantUse = false;
|
||||||
|
skill->active = false;
|
||||||
skill->use = NULL;
|
skill->use = NULL;
|
||||||
return skill;
|
return skill;
|
||||||
}
|
}
|
||||||
|
@ -37,9 +47,29 @@ create_default(const char *s_label, Sprite *s)
|
||||||
static bool
|
static bool
|
||||||
skill_use_flurry(Skill *skill, SkillData *data)
|
skill_use_flurry(Skill *skill, SkillData *data)
|
||||||
{
|
{
|
||||||
Position pos = position_to_matrix_coords(&data->player->sprite->pos);
|
Position playerPos = position_to_matrix_coords(&data->player->sprite->pos);
|
||||||
UNUSED(pos);
|
Position targetPos = playerPos;
|
||||||
UNUSED(skill);
|
targetPos.x += (int) data->direction.x;
|
||||||
|
targetPos.y += (int) data->direction.y;
|
||||||
|
|
||||||
|
Monster *monster = data->matrix->spaces[targetPos.x][targetPos.y].monster;
|
||||||
|
if (monster) {
|
||||||
|
gui_log("You attack %s with a flurry of strikes", monster->lclabel);
|
||||||
|
for (size_t i = 0; i < 3; ++i) {
|
||||||
|
unsigned int dmg = stats_fight(&data->player->stats, &monster->stats);
|
||||||
|
mixer_play_effect((SWING0 - 1) + get_random(3));
|
||||||
|
if (dmg > 0) {
|
||||||
|
gui_log("You hit for %u damage", dmg);
|
||||||
|
mixer_play_effect(SWORD_HIT);
|
||||||
|
monster_hit(monster, dmg);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
} else {
|
||||||
|
gui_log("You swing at thin air with a flurry of strikes");
|
||||||
|
}
|
||||||
|
player_monster_kill_check(data->player, monster);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -57,12 +87,37 @@ create_flurry(void)
|
||||||
return skill;
|
return skill;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static bool
|
||||||
|
skill_sip_health(Skill *skill, SkillData *data)
|
||||||
|
{
|
||||||
|
player_sip_health(data->player);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
static Skill *
|
||||||
|
create_sip_health()
|
||||||
|
{
|
||||||
|
Texture *t = texturecache_add("Items/Potion.png");
|
||||||
|
Sprite *s = sprite_create();
|
||||||
|
sprite_set_texture(s, t, 0);
|
||||||
|
s->dim = DEFAULT_DIMENSION;
|
||||||
|
s->clip = CLIP16(0, 0);
|
||||||
|
s->fixed = true;
|
||||||
|
Skill *skill = create_default("Sip health", s);
|
||||||
|
skill->instantUse = true;
|
||||||
|
skill->use = skill_sip_health;
|
||||||
|
skill->resetTime = 0;
|
||||||
|
return skill;
|
||||||
|
}
|
||||||
|
|
||||||
Skill*
|
Skill*
|
||||||
skill_create(enum SkillType t)
|
skill_create(enum SkillType t)
|
||||||
{
|
{
|
||||||
switch (t) {
|
switch (t) {
|
||||||
case FLURRY:
|
case FLURRY:
|
||||||
return create_flurry();
|
return create_flurry();
|
||||||
|
case SIP_HEALTH:
|
||||||
|
return create_sip_health();
|
||||||
default:
|
default:
|
||||||
fatal("Unknown SkillType %u", (unsigned int) t);
|
fatal("Unknown SkillType %u", (unsigned int) t);
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
11
src/skill.h
11
src/skill.h
|
@ -20,17 +20,20 @@
|
||||||
#define SKILL_H_
|
#define SKILL_H_
|
||||||
|
|
||||||
#include <stdbool.h>
|
#include <stdbool.h>
|
||||||
#include "player.h"
|
|
||||||
#include "roommatrix.h"
|
#include "roommatrix.h"
|
||||||
#include "sprite.h"
|
#include "sprite.h"
|
||||||
#include "vector2d.h"
|
#include "vector2d.h"
|
||||||
|
|
||||||
|
// Forward declaration
|
||||||
|
struct Player_t;
|
||||||
|
|
||||||
enum SkillType {
|
enum SkillType {
|
||||||
FLURRY
|
FLURRY,
|
||||||
|
SIP_HEALTH
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef struct SkillData_t {
|
typedef struct SkillData_t {
|
||||||
Player *player;
|
struct Player_t *player;
|
||||||
RoomMatrix *matrix;
|
RoomMatrix *matrix;
|
||||||
Vector2d direction;
|
Vector2d direction;
|
||||||
} SkillData;
|
} SkillData;
|
||||||
|
@ -40,6 +43,8 @@ typedef struct Skill_t {
|
||||||
Sprite *icon;
|
Sprite *icon;
|
||||||
unsigned int resetTime;
|
unsigned int resetTime;
|
||||||
unsigned int resetCountdown;
|
unsigned int resetCountdown;
|
||||||
|
bool actionRequired;
|
||||||
|
bool instantUse;
|
||||||
bool active;
|
bool active;
|
||||||
bool (*use)(struct Skill_t*, SkillData*);
|
bool (*use)(struct Skill_t*, SkillData*);
|
||||||
} Skill;
|
} Skill;
|
||||||
|
|
|
@ -34,7 +34,7 @@ load_texture(SkillBar *bar, const char *path, SDL_Renderer *renderer)
|
||||||
t->dim.width = 16;
|
t->dim.width = 16;
|
||||||
t->dim.height = 16;
|
t->dim.height = 16;
|
||||||
|
|
||||||
for (unsigned int i = 0; i < 4; ++i) {
|
for (unsigned int i = 0; i < 5; ++i) {
|
||||||
char buffer[4];
|
char buffer[4];
|
||||||
Sprite *s = sprite_create();
|
Sprite *s = sprite_create();
|
||||||
s->pos = (Position) { i * 32 + 20, 20 };
|
s->pos = (Position) { i * 32 + 20, 20 };
|
||||||
|
@ -113,11 +113,56 @@ render_activation_indicator(SkillBar *bar, Camera *cam)
|
||||||
SDL_RenderDrawRect(cam->renderer, &square);
|
SDL_RenderDrawRect(cam->renderer, &square);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
render_skills(SkillBar *bar, Player *player, Camera *cam)
|
||||||
|
{
|
||||||
|
static SDL_Rect activeSkillBox = { 0, 0, 32, 32 };
|
||||||
|
|
||||||
|
for (size_t i = 0; i < PLAYER_SKILL_COUNT; ++i) {
|
||||||
|
if (!player->skills[i])
|
||||||
|
continue;
|
||||||
|
|
||||||
|
Skill *skill = player->skills[i];
|
||||||
|
skill->icon->pos = (Position) { 8 + i * 32, 8 };
|
||||||
|
sprite_render(skill->icon, cam);
|
||||||
|
|
||||||
|
if (player->skills[i]->active) {
|
||||||
|
activeSkillBox.x = i * 32;
|
||||||
|
SDL_SetRenderDrawColor(cam->renderer, 0, 0, 255, 100);
|
||||||
|
SDL_RenderFillRect(cam->renderer, &activeSkillBox);
|
||||||
|
}
|
||||||
|
if (player->skills[i]->resetCountdown > 0) {
|
||||||
|
activeSkillBox.x = i * 32;
|
||||||
|
SDL_SetRenderDrawColor(cam->renderer, 255, 0, 0, 100);
|
||||||
|
SDL_RenderFillRect(cam->renderer, &activeSkillBox);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
render_skill_unavailable(SkillBar *bar, Player *player, Camera *cam)
|
||||||
|
{
|
||||||
|
static SDL_Rect unavailableSkillBox = { 0, 0, 32, 32 };
|
||||||
|
|
||||||
|
for (size_t i = 0; i < PLAYER_SKILL_COUNT; ++i) {
|
||||||
|
if (!player->skills[i])
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if (player->skills[i]->resetCountdown > 0) {
|
||||||
|
unavailableSkillBox.x = i * 32;
|
||||||
|
SDL_SetRenderDrawColor(cam->renderer, 255, 0, 0, 70);
|
||||||
|
SDL_RenderFillRect(cam->renderer, &unavailableSkillBox);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
skillbar_render(SkillBar *bar, Camera *cam)
|
skillbar_render(SkillBar *bar, Player *player, Camera *cam)
|
||||||
{
|
{
|
||||||
render_frame(cam);
|
render_frame(cam);
|
||||||
|
render_skills(bar, player, cam);
|
||||||
render_sprites(bar, cam);
|
render_sprites(bar, cam);
|
||||||
|
render_skill_unavailable(bar, player, cam);
|
||||||
render_activation_indicator(bar, cam);
|
render_activation_indicator(bar, cam);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -136,6 +181,8 @@ skillbar_handle_event(SkillBar *bar, SDL_Event *event)
|
||||||
key = 3;
|
key = 3;
|
||||||
else if (keyboard_press(SDLK_4, event))
|
else if (keyboard_press(SDLK_4, event))
|
||||||
key = 4;
|
key = 4;
|
||||||
|
else if (keyboard_press(SDLK_5, event))
|
||||||
|
key = 5;
|
||||||
|
|
||||||
if (key != 0) {
|
if (key != 0) {
|
||||||
bar->lastActivation = key;
|
bar->lastActivation = key;
|
||||||
|
|
|
@ -23,6 +23,7 @@
|
||||||
#include "linkedlist.h"
|
#include "linkedlist.h"
|
||||||
#include "camera.h"
|
#include "camera.h"
|
||||||
#include "timer.h"
|
#include "timer.h"
|
||||||
|
#include "player.h"
|
||||||
|
|
||||||
typedef struct SkillBar_t {
|
typedef struct SkillBar_t {
|
||||||
LinkedList *sprites;
|
LinkedList *sprites;
|
||||||
|
@ -34,7 +35,7 @@ SkillBar *
|
||||||
skillbar_create(SDL_Renderer*);
|
skillbar_create(SDL_Renderer*);
|
||||||
|
|
||||||
void
|
void
|
||||||
skillbar_render(SkillBar*, Camera*);
|
skillbar_render(SkillBar*, Player*, Camera*);
|
||||||
|
|
||||||
void
|
void
|
||||||
skillbar_handle_event(SkillBar*, SDL_Event*);
|
skillbar_handle_event(SkillBar*, SDL_Event*);
|
||||||
|
|
|
@ -19,6 +19,7 @@
|
||||||
#ifndef VECTOR2D_H_
|
#ifndef VECTOR2D_H_
|
||||||
#define VECTOR2D_H_
|
#define VECTOR2D_H_
|
||||||
|
|
||||||
|
#define VECTOR2D_NODIR (Vector2d) { 0, 0 }
|
||||||
#define VECTOR2D_RIGHT (Vector2d) { 1, 0 }
|
#define VECTOR2D_RIGHT (Vector2d) { 1, 0 }
|
||||||
#define VECTOR2D_LEFT (Vector2d) { -1, 0 }
|
#define VECTOR2D_LEFT (Vector2d) { -1, 0 }
|
||||||
#define VECTOR2D_UP (Vector2d) { 0, -1 }
|
#define VECTOR2D_UP (Vector2d) { 0, -1 }
|
||||||
|
|
Loading…
Reference in New Issue