Textbox is working now
This commit is contained in:
parent
c69fe1738c
commit
1a1038522c
23
app.c
23
app.c
@ -8,6 +8,8 @@
|
||||
#include "player.h"
|
||||
#include "types.h"
|
||||
#include "render_bundle.h"
|
||||
#include "render_component.h"
|
||||
#include "mapper_misc.h"
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
|
||||
@ -58,6 +60,27 @@ App *app_NewApp() {
|
||||
hit3->hitbox->fixed = true;
|
||||
entity_Commit(app->entity, hit3);
|
||||
|
||||
Entity *text1 = entity_Create(app->entity, "text_plate_large_1");
|
||||
ADD_COMPONENT(text1, position);
|
||||
text1->position->position = vec2(600, 550);
|
||||
text1->render = render_NewComponent(app, "info_plate");
|
||||
misc_InstantiateTextbox(app, text1, "So long lives this,\nAnd this gives life to thee.", misc_TextboxUpright(110, 110), -220);
|
||||
entity_Commit(app->entity, text1);
|
||||
|
||||
Entity *text2 = entity_Create(app->entity, "text_plate_1");
|
||||
ADD_COMPONENT(text2, position);
|
||||
text2->position->position = vec2(250, 200);
|
||||
text2->render = render_NewComponent(app, "info_plate_small_1");
|
||||
misc_InstantiateTextbox(app, text2, "Press Space to jump.\nYou can jump again midair.", misc_TextboxUpright(70, 70), -180);
|
||||
entity_Commit(app->entity, text2);
|
||||
|
||||
Entity *text3 = entity_Create(app->entity, "text_plate_2");
|
||||
ADD_COMPONENT(text3, position);
|
||||
text3->position->position = vec2(750, 200);
|
||||
text3->render = render_NewComponent(app, "info_plate_small_2");
|
||||
misc_InstantiateTextbox(app, text3, "Press ; to dash.\nYou can only dash one time midair.", misc_TextboxUpright(70, 70), -180);
|
||||
entity_Commit(app->entity, text3);
|
||||
|
||||
return app;
|
||||
}
|
||||
|
||||
|
@ -5,6 +5,7 @@
|
||||
#include "physics.h"
|
||||
#include "easyx.h"
|
||||
#include "render_bundle.h"
|
||||
#include "render_component.h"
|
||||
#include "util/tree.h"
|
||||
#include "types.h"
|
||||
#include "render_util.h"
|
||||
@ -63,14 +64,38 @@ void app_Render(App *app) {
|
||||
render_FillCircleW(app, vec2(200, 100), 20);
|
||||
|
||||
|
||||
render_DrawBundleW(app, render_FindBundle("info_plate"), vec2(600, 550));
|
||||
// render_DrawBundleW(app, render_FindBundle("info_plate"), vec2(600, 550));
|
||||
render_DrawBundleW(app, render_FindBundle("info_plate_small_1"), vec2(250, 200));
|
||||
render_DrawBundleW(app, render_FindBundle("info_plate_small_2"), vec2(750, 200));
|
||||
|
||||
// Draw entities
|
||||
for (tree_Node *i = tree_FirstNode(app->entity->entities);
|
||||
i != NULL;
|
||||
i = tree_Node_Next(i)) {
|
||||
Entity *e = (Entity *)i->data;
|
||||
if (e->render) {
|
||||
Component_Render *r = e->render;
|
||||
|
||||
// Calculate global position as offset
|
||||
Vec2 pos = {.x = 0.0, .y = 0.0};
|
||||
if (e->position)
|
||||
pos = e->position->position;
|
||||
// Has bundle
|
||||
if (r->bundle)
|
||||
render_DrawBundleW(app, r->bundle, pos);
|
||||
// Has custom rendering
|
||||
if (r->custom)
|
||||
r->custom(app, e, camera_TransformVec2(app->camera, pos), r->custom_data);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Draw particles
|
||||
setfillcolor(RGB(255, 255, 255));
|
||||
setbkcolor(RGB(0, 0, 0));
|
||||
particle_Render(app->particle);
|
||||
|
||||
|
||||
settextcolor(RGB(255, 255, 255));
|
||||
}
|
||||
}
|
||||
|
@ -2,6 +2,7 @@
|
||||
#include "mapper_misc.h"
|
||||
#include "app.h"
|
||||
#include "entity.h"
|
||||
#include "physics.h"
|
||||
#include "types.h"
|
||||
#include "util/assert.h"
|
||||
#include <stdio.h>
|
||||
@ -31,6 +32,7 @@ void misc_thinker_HazardRespawn(App *app, Entity *e, Duration deltaTime) {
|
||||
if (app->player->player == NULL) // No player
|
||||
return;
|
||||
Component_Player *p = app->player->player;
|
||||
Box2 playerbox = physics_HitboxAbsolute(p->super->hitbox);
|
||||
|
||||
Box2 worldbox; // Offset if position component exists
|
||||
Vec2 worldspawn;
|
||||
@ -42,7 +44,7 @@ void misc_thinker_HazardRespawn(App *app, Entity *e, Duration deltaTime) {
|
||||
worldspawn = e->misc->respawn->respawn_pos;
|
||||
}
|
||||
|
||||
if (box2_Contains(worldbox, p->super->position->position))
|
||||
if (box2_Intersects(worldbox, playerbox, NULL))
|
||||
p->hazardRespawn = worldspawn;
|
||||
}
|
||||
|
||||
@ -57,12 +59,13 @@ void misc_thinker_Textbox(App *app, Entity *e, Duration deltaTime) {
|
||||
return;
|
||||
}
|
||||
Component_Player *p = app->player->player;
|
||||
Box2 playerbox = physics_HitboxAbsolute(p->super->hitbox);
|
||||
|
||||
Box2 worldbox; // Offset if position component exists
|
||||
ASSERT(e->position && "Textboxes must have a position component");
|
||||
worldbox = box2_Offset(t->trigger_box, e->position->position);
|
||||
|
||||
if (box2_Contains(worldbox, p->super->position->position))
|
||||
if (box2_Intersects(worldbox, playerbox, NULL))
|
||||
// Fade in
|
||||
t->progress = fminf(1.0f, t->progress + duration_Seconds(deltaTime) * MISC_TEXTBOX_FADEIN_SPEED);
|
||||
else
|
||||
@ -73,8 +76,8 @@ void misc_thinker_Textbox(App *app, Entity *e, Duration deltaTime) {
|
||||
|
||||
// Utility functions for creating misc entities
|
||||
void misc_InstantiateTextbox(App *app, Entity *e, const char *text, Box2 trigger_box, float offset) {
|
||||
ASSERT(e->misc == NULL && "Instantiate must be called with e.misc not set yet");
|
||||
ASSERT(e->render == NULL && "Instantiate must be called with e.render not set yet");
|
||||
ASSERT(e->misc == NULL && "Instantiate must be called with e.misc not set");
|
||||
ASSERT((e->render == NULL || e->render->custom == NULL) && "Instantiate for Textbox must be called with e.render.custom not set");
|
||||
e->misc = zero_malloc(sizeof(Component_Misc));
|
||||
e->misc->textbox = zero_malloc(sizeof(misc_Textbox));
|
||||
|
||||
@ -82,6 +85,20 @@ void misc_InstantiateTextbox(App *app, Entity *e, const char *text, Box2 trigger
|
||||
e->misc->textbox->trigger_box = trigger_box;
|
||||
e->misc->textbox->offset = offset;
|
||||
|
||||
if (!e->render)
|
||||
e->render = render_NewComponentFunc(app, &misc_render_Textbox, NULL);
|
||||
else
|
||||
e->render->custom = &misc_render_Textbox;
|
||||
e->thinker = &misc_thinker_Textbox;
|
||||
}
|
||||
|
||||
void misc_InstantiateHazardRespawn(App *app, Entity *e, Box2 trigger_box, Vec2 respawn_pos) {
|
||||
ASSERT(e->misc == NULL && "Instantiate must be called with e.misc not set");
|
||||
e->misc = zero_malloc(sizeof(Component_Misc));
|
||||
e->misc->respawn = zero_malloc(sizeof(misc_HazardRespawn));
|
||||
|
||||
e->misc->respawn->respawn_pos = respawn_pos;
|
||||
e->misc->respawn->trigger_box = trigger_box;
|
||||
|
||||
e->thinker = &misc_thinker_HazardRespawn;
|
||||
}
|
||||
|
@ -11,7 +11,7 @@ typedef struct _App App;
|
||||
typedef struct _Entity Entity;
|
||||
|
||||
|
||||
#define MISC_TEXTBOX_FADEIN_SPEED 5.0 // Fades in/out in 1/5 seconds
|
||||
#define MISC_TEXTBOX_FADEIN_SPEED 6.0 // Fades in/out in 1/6 seconds
|
||||
|
||||
// A textbox that shows itself when the player is close
|
||||
typedef struct {
|
||||
@ -55,6 +55,19 @@ void misc_DeleteComponent(Component_Misc *misc);
|
||||
// Creates misc + render components & sets the thinker.
|
||||
void misc_InstantiateTextbox(App *app, Entity *e, const char *text, Box2 trigger_box, float offset);
|
||||
|
||||
// Inserts the components for a hazard respawn area.
|
||||
// Creates misc & sets the thinker.
|
||||
void misc_InstantiateHazardRespawn(App *app, Entity *e, Box2 trigger_box, Vec2 respawn_pos);
|
||||
|
||||
|
||||
static inline Box2 misc_TextboxUpright(double width, double height) {
|
||||
Box2 b = {
|
||||
.lefttop = {
|
||||
.x = -width / 2.0,
|
||||
.y = -height},
|
||||
.size = {.x = width, .y = height}};
|
||||
return b;
|
||||
}
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
@ -62,6 +62,7 @@ extern "C" void misc_render_Textbox(App *app, Entity *e, Vec2 entity_screen_pos,
|
||||
rect.top = (LONG)round(entity_screen_pos.y) + t->offset + 40;
|
||||
|
||||
// Convert & draw
|
||||
// https://docs.easyx.cn/zh-cn/drawtext
|
||||
convert_text(t->text);
|
||||
drawtext((LPCTSTR)vector_Data(tbuf), &rect, DT_CENTER | DT_NOCLIP);
|
||||
}
|
||||
|
9
types.h
9
types.h
@ -55,6 +55,15 @@ typedef struct {
|
||||
Vec2 size;
|
||||
} Box2;
|
||||
|
||||
static inline Box2 box2(double x, double y, double width, double height) {
|
||||
Box2 b;
|
||||
b.lefttop.x = x;
|
||||
b.lefttop.y = y;
|
||||
b.size.x = width;
|
||||
b.size.y = height;
|
||||
return b;
|
||||
}
|
||||
|
||||
|
||||
// Intersection test.
|
||||
bool box2_Intersects(const Box2 x, const Box2 y, Box2 *out_intersection);
|
||||
|
Loading…
Reference in New Issue
Block a user