Add level transitions

This commit is contained in:
Edgaru089 2024-04-14 15:22:55 +08:00
parent 46d7d3c7c2
commit 17c5a96786
7 changed files with 64 additions and 10 deletions

View File

@ -68,7 +68,7 @@ static void _app_LevelCommand(App *app, char *cmd) {
c = TOKEN_DOUBLE;
d = TOKEN_DOUBLE;
Entity *e = entity_Create(app->entity, NULL);
Entity *e = entity_Create(app->entity, cmd);
ADD_COMPONENT(e, hitbox);
e->hitbox->box = box2(a, b, c, d);
e->hitbox->fixed = true;
@ -80,7 +80,7 @@ static void _app_LevelCommand(App *app, char *cmd) {
a = TOKEN_DOUBLE;
b = TOKEN_DOUBLE;
Entity *e = entity_Create(app->entity, NULL);
Entity *e = entity_Create(app->entity, cmd);
ADD_COMPONENT(e, player);
e->player->hazardRespawn = vec2(a, b);
ADD_COMPONENT(e, position);
@ -101,7 +101,7 @@ static void _app_LevelCommand(App *app, char *cmd) {
e = TOKEN_DOUBLE;
f = TOKEN_DOUBLE;
Entity *en = entity_Create(app->entity, NULL);
Entity *en = entity_Create(app->entity, cmd);
misc_InstantiateHazardRespawn(app, en, box2(a, b, c, d), vec2(e, f));
entity_Commit(app->entity, en);
}
@ -113,7 +113,7 @@ static void _app_LevelCommand(App *app, char *cmd) {
c = TOKEN_DOUBLE;
d = TOKEN_DOUBLE;
Entity *e = entity_Create(app->entity, NULL);
Entity *e = entity_Create(app->entity, cmd);
misc_InstantiateHazard(app, e, box2(a, b, c, d));
entity_Commit(app->entity, e);
}
@ -125,7 +125,7 @@ static void _app_LevelCommand(App *app, char *cmd) {
c = TOKEN_DOUBLE;
d = TOKEN_DOUBLE;
Entity *e = entity_Create(app->entity, NULL);
Entity *e = entity_Create(app->entity, cmd);
char *bundle = TOKEN;
if (bundle != NULL)
e->render = render_NewComponent(app, bundle);
@ -147,9 +147,17 @@ static void _app_LevelCommand(App *app, char *cmd) {
}
CMD("LEVEL_TRANSITION") {
// TODO
// Entity *e = entity_Create(app->entity, NULL);
// entity_Commit(app->entity, e);
double a, b, c, d;
a = TOKEN_DOUBLE;
b = TOKEN_DOUBLE;
c = TOKEN_DOUBLE;
d = TOKEN_DOUBLE;
char *next_level = TOKEN;
if (next_level) {
Entity *e = entity_Create(app->entity, cmd);
misc_InstantiateChangeLevel(app, e, box2(a, b, c, d), next_level);
entity_Commit(app->entity, e);
}
}
CMD("CUTOFF") {
@ -166,6 +174,7 @@ void _app_SwitchLevel(App *app) {
WARN("called when switch_level is NULL", 0);
return;
}
INFO("Switching level to %s", app->switch_level);
FILE *f = fopen(app->switch_level, "r");
if (!f) {

View File

@ -56,6 +56,8 @@ void app_Render(App *app) {
}
if (e->misc->trigger_flags & misc_Hazard)
setlinecolor(RGB(255, 0, 0));
if (e->misc->change_level)
setlinecolor(RGB(255, 255, 0));
Box2 box;
if (e->position)
box = camera_TransformBox2(app->camera, box2_Offset(e->misc->trigger, e->position->position));

View File

@ -4,6 +4,7 @@
#include "camera.h"
#include "mapper_misc.h"
#include "physics.h"
#include "render_component.h"
#include "util/assert.h"
#include "util/tree.h"
#include "util/vector.h"
@ -98,6 +99,7 @@ static inline void _entity_Delete(System_Entity *sys, uintptr_t id) {
player_DeleteEntity(sys->super->player, e->id);
camera_DeleteEntity(sys->super->camera, e->id);
_entity_FreeMembers(e);
tree_Delete(sys->entities, node);

4
level1.txt Normal file
View File

@ -0,0 +1,4 @@
CUTOFF 600
HITBOX 60 350 1134 65
TEXTBOX 541 191 178 166 info_plate_small_1 Work\sin\sProgress!!
PLAYER 565 350

View File

@ -18,6 +18,8 @@ void misc_DeleteComponent(Component_Misc *misc) {
}
if (misc->respawn_pos)
free(misc->respawn_pos);
if (misc->change_level)
free(misc->change_level);
free(misc);
}
}
@ -96,6 +98,22 @@ void misc_thinker_ToLive(App *app, Entity *e, Duration deltaTime) {
}
}
void misc_thinker_ChangeLevel(App *app, Entity *e, Duration deltaTime) {
if (!e->misc || !e->misc->change_level) {
WARN("called on an entity without misc or misc.change_level", 0);
e->thinker = NULL;
return;
}
if (app->player->player == NULL) // No player
return;
Component_Player *p = app->player->player;
Box2 playerbox = physics_HitboxAbsolute(p->super->hitbox);
Box2 worldbox = ABSOLUTE_BOX(e, e->misc->trigger);
if (box2_Intersects(worldbox, playerbox, NULL))
app_QueueLoadLevel(app, e->misc->change_level);
}
// Utility functions for creating misc entities
void misc_InstantiateTextbox(App *app, Entity *e, const char *text, Box2 trigger_box, float offset) {
@ -140,3 +158,11 @@ void misc_InstantiateToLive(App *app, Entity *e, Duration duration, TimePoint si
e->thinker = &misc_thinker_ToLive;
}
void misc_InstantiateChangeLevel(App *app, Entity *e, Box2 trigger_box, const char *next_level) {
ASSERT(e->misc == NULL && "Instantiate must be called with e.misc not set");
e->misc = zero_malloc(sizeof(Component_Misc));
e->misc->trigger = trigger_box;
e->misc->change_level = copy_malloc(next_level);
e->thinker = &misc_thinker_ChangeLevel;
}

View File

@ -40,6 +40,10 @@ void misc_thinker_Hazard(App *app, Entity *e, Duration deltaTime);
// Kills itself after some time
void misc_thinker_ToLive(App *app, Entity *e, Duration deltaTime);
// Thinker for level transition
void misc_thinker_ChangeLevel(App *app, Entity *e, Duration deltaTime);
typedef enum {
misc_Hazard = 1 << 0, // Hazard, harms the player on contact
} misc_TriggerFlags;
@ -51,7 +55,8 @@ typedef struct {
Box2 trigger; // Relative to Position if exists; absolute otherwise
misc_TriggerFlags trigger_flags;
misc_Textbox *textbox;
Vec2 *respawn_pos; // Set hazard respawn trigger
Vec2 *respawn_pos; // Set hazard respawn trigger
char *change_level; // Change level
TimePoint tolive; // Deletes itself after this time if it is not 0
} Component_Misc;
@ -80,6 +85,11 @@ void misc_InstantiateHazard(App *app, Entity *e, Box2 trigger_box);
void misc_InstantiateToLive(App *app, Entity *e, Duration duration, TimePoint since);
// Inserts components for change level
// Creates misc & the thinker.
void misc_InstantiateChangeLevel(App *app, Entity *e, Box2 trigger_box, const char *next_level);
static inline Box2 misc_TextboxUpright(double width, double height) {
Box2 b = {
.lefttop = {

View File

@ -14,7 +14,8 @@ extern "C" {
#define SCREEN_WIDTH 1600
#define SCREEN_HEIGHT 900
#define WARN(fmt, ...) fprintf(stderr, "[WARN][%s] " fmt "\n", __func__, __VA_ARGS__)
#define WARN(fmt, ...) fprintf(stderr, "[WARN][%s] " fmt "\n", __func__, ##__VA_ARGS__)
#define INFO(fmt, ...) fprintf(stderr, "[%s] " fmt "\n", __func__, ##__VA_ARGS__)
static inline void *zero_malloc(size_t size) {