debug pausing
This commit is contained in:
parent
ccbfc22e84
commit
81d02f3c80
@ -30,7 +30,7 @@
|
||||
#define PIXELS_PER_UNIT 256.0
|
||||
|
||||
#define GAME_FPS 50.0
|
||||
#define GAME_TIMESCALE 1.0
|
||||
#define GAME_TIMESCALE 1
|
||||
|
||||
/* How many ticks back in time should the user blend between?
|
||||
* <Delay ms> = <USER_INTERP_OFFSET_TICK_RATIO> * <Game tick rate>
|
||||
|
||||
@ -113,10 +113,11 @@ struct entity {
|
||||
struct entity_handle equipped;
|
||||
|
||||
/* ====================================================================== */
|
||||
/* Weapon */
|
||||
/* Triggers */
|
||||
|
||||
/* ENTITY_PROP_WEAPON */
|
||||
f32 fire_rate;
|
||||
/* ENTITY_PROP_TRIGGERED_THIS_TICK */
|
||||
f32 trigger_delay; /* Minimum time between triggers */
|
||||
f32 last_triggered;
|
||||
|
||||
/* ====================================================================== */
|
||||
/* Testing */
|
||||
|
||||
61
src/game.c
61
src/game.c
@ -15,6 +15,8 @@ GLOBAL struct {
|
||||
struct atomic_i32 game_thread_shutdown;
|
||||
struct sys_thread game_thread;
|
||||
|
||||
b32 paused;
|
||||
|
||||
/* Game thread input */
|
||||
struct sys_mutex game_cmds_mutex;
|
||||
struct arena game_cmds_arena;
|
||||
@ -101,7 +103,7 @@ INTERNAL struct game_cmd_array pop_cmds(struct arena *arena)
|
||||
|
||||
INTERNAL void spawn_test_entities(void)
|
||||
{
|
||||
/* Player ent */
|
||||
/* Player */
|
||||
struct entity *player_ent;
|
||||
{
|
||||
struct v2 pos = V2(1, 1);
|
||||
@ -109,8 +111,11 @@ INTERNAL void spawn_test_entities(void)
|
||||
f32 r = 0;
|
||||
|
||||
struct entity *e = entity_alloc_top(G.tick.entity_store);
|
||||
entity_set_xform(e, XFORM_TRS(.t = pos, .r = r, .s = size));
|
||||
|
||||
struct xform xf = XFORM_TRS(.t = pos, .r = r, .s = size);
|
||||
entity_set_xform(e, xf);
|
||||
|
||||
entity_enable_prop(e, ENTITY_PROP_ANIMATING);
|
||||
e->sprite = sprite_tag_from_path(STR("res/graphics/tim.ase"));
|
||||
e->sprite_span_name = STR("idle.unarmed");
|
||||
//e->sprite_span_name = STR("idle.one_handed");
|
||||
@ -121,33 +126,32 @@ INTERNAL void spawn_test_entities(void)
|
||||
e->player_acceleration = 20.0f;
|
||||
e->control.focus = V2(0, -1);
|
||||
|
||||
entity_enable_prop(e, ENTITY_PROP_ANIMATING);
|
||||
|
||||
player_ent = e;
|
||||
|
||||
//entity_enable_prop(e, ENTITY_PROP_TEST);
|
||||
}
|
||||
|
||||
/* Child 1 */
|
||||
/* Weapon */
|
||||
{
|
||||
struct v2 pos = V2(1, 0);
|
||||
struct v2 size = V2(1, 1);
|
||||
f32 r = PI / 4;
|
||||
|
||||
struct xform xf = XFORM_TRS(.t = pos, .r = r, .s = size);
|
||||
|
||||
struct entity *e = entity_alloc_top(G.tick.entity_store);
|
||||
|
||||
struct xform xf = XFORM_TRS(.t = pos, .r = r, .s = size);
|
||||
entity_set_local_xform(e, xf);
|
||||
|
||||
entity_enable_prop(e, ENTITY_PROP_ANIMATING);
|
||||
e->sprite = sprite_tag_from_path(STR("res/graphics/gun.ase"));
|
||||
|
||||
entity_enable_prop(e, ENTITY_PROP_ANIMATING);
|
||||
entity_enable_prop(e, ENTITY_PROP_WEAPON);
|
||||
e->trigger_delay = 1.0 / 10.0;
|
||||
|
||||
player_ent->equipped = e->handle;
|
||||
}
|
||||
|
||||
/* Camera ent */
|
||||
/* Camera */
|
||||
{
|
||||
struct entity *e = entity_alloc_top(G.tick.entity_store);
|
||||
entity_set_xform(e, XFORM_IDENT);
|
||||
@ -179,7 +183,7 @@ INTERNAL void publish_game_tick(void)
|
||||
sys_mutex_unlock(&lock);
|
||||
}
|
||||
|
||||
INTERNAL void game_update(void)
|
||||
INTERNAL void game_update(struct game_cmd_array game_cmds)
|
||||
{
|
||||
__prof;
|
||||
|
||||
@ -194,7 +198,7 @@ INTERNAL void game_update(void)
|
||||
G.tick.dt = max_f64(0.0, (1.0 / GAME_FPS) * G.tick.timescale);
|
||||
G.tick.time += G.tick.dt;
|
||||
|
||||
struct game_cmd_array game_cmds = pop_cmds(scratch.arena);
|
||||
f64 time = G.tick.time;
|
||||
struct entity_store *store = G.tick.entity_store;
|
||||
struct entity *root = entity_from_handle(store, store->root);
|
||||
struct sprite_scope *sprite_frame_scope = sprite_scope_begin();
|
||||
@ -367,7 +371,7 @@ INTERNAL void game_update(void)
|
||||
ent->test_start_sprite_xform = ent->sprite_local_xform;
|
||||
}
|
||||
|
||||
f32 t = ((f32)G.tick.time);
|
||||
f32 t = (f32)time;
|
||||
struct v2 og = v2_mul(V2(math_cos(t), math_sin(t)), 3);
|
||||
f32 r = t * 3;
|
||||
struct v2 s = V2(1 + (math_fabs(math_sin(t * 5)) * 3), 1);
|
||||
@ -406,17 +410,23 @@ INTERNAL void game_update(void)
|
||||
}
|
||||
|
||||
/* ========================== *
|
||||
* Fire weapons
|
||||
* Fire triggers
|
||||
* ========================== */
|
||||
|
||||
for (u64 entity_index = 0; entity_index < store->count; ++entity_index) {
|
||||
struct entity *ent = &store->entities[entity_index];
|
||||
if (!ent->valid) continue;
|
||||
if (!entity_has_prop(ent, ENTITY_PROP_TRIGGERED_THIS_TICK)) continue;
|
||||
if ((time - ent->last_triggered < ent->trigger_delay) && ent->last_triggered != 0) continue;
|
||||
|
||||
ent->last_triggered = time;
|
||||
|
||||
/* Fire weapon */
|
||||
if (entity_has_prop(ent, ENTITY_PROP_WEAPON)) {
|
||||
if (entity_has_prop(ent, ENTITY_PROP_TRIGGERED_THIS_TICK)) {
|
||||
ent->sprite_tint = RGBA_32_F(1, 0, 0, 1);
|
||||
}
|
||||
f32 r = 1.0f * ((f32)sys_rand_u32() / U32_MAX);
|
||||
f32 g = 1.0f * ((f32)sys_rand_u32() / U32_MAX);
|
||||
f32 b = 1.0f * ((f32)sys_rand_u32() / U32_MAX);
|
||||
ent->sprite_tint = RGBA_32_F(r, g, b, 1);
|
||||
}
|
||||
}
|
||||
|
||||
@ -661,15 +671,32 @@ INTERNAL void game_update(void)
|
||||
|
||||
INTERNAL SYS_THREAD_ENTRY_POINT_FUNC_DEF(game_thread_entry_point, arg)
|
||||
{
|
||||
struct temp_arena scratch = scratch_begin_no_conflict();
|
||||
|
||||
(UNUSED)arg;
|
||||
sys_timestamp_t last_frame_ts = 0;
|
||||
f64 target_dt = GAME_FPS > (0) ? (1.0 / GAME_FPS) : 0;
|
||||
while (!atomic_i32_eval(&G.game_thread_shutdown)) {
|
||||
__profscope(game_update_w_sleep);
|
||||
struct temp_arena temp = arena_temp_begin(scratch.arena);
|
||||
sleep_frame(last_frame_ts, target_dt);
|
||||
last_frame_ts = sys_timestamp();
|
||||
game_update();
|
||||
{
|
||||
struct game_cmd_array game_cmds = pop_cmds(temp.arena);
|
||||
if (!G.paused) {
|
||||
game_update(game_cmds);
|
||||
}
|
||||
/* Check for pause cmd */
|
||||
for (u64 i = 0; i < game_cmds.count; ++i) {
|
||||
if (game_cmds.cmds[i].kind == GAME_CMD_KIND_PAUSE) {
|
||||
G.paused = !G.paused;
|
||||
}
|
||||
}
|
||||
}
|
||||
arena_temp_end(temp);
|
||||
}
|
||||
|
||||
scratch_end(scratch);
|
||||
}
|
||||
|
||||
/* ========================== *
|
||||
|
||||
@ -21,6 +21,7 @@ enum game_cmd_kind {
|
||||
/* Testing */
|
||||
GAME_CMD_KIND_CLEAR_ALL,
|
||||
GAME_CMD_KIND_SPAWN_TEST,
|
||||
GAME_CMD_KIND_PAUSE,
|
||||
|
||||
GAME_CMD_KIND_COUNT
|
||||
};
|
||||
|
||||
27
src/user.c
27
src/user.c
@ -86,8 +86,9 @@ GLOBAL READONLY enum user_bind_kind g_binds[SYS_BTN_COUNT] = {
|
||||
|
||||
[SYS_BTN_C] = USER_BIND_KIND_DEBUG_CLEAR,
|
||||
[SYS_BTN_V] = USER_BIND_KIND_DEBUG_SPAWN,
|
||||
[SYS_BTN_F6] = USER_BIND_KIND_DEBUG_DRAW,
|
||||
[SYS_BTN_F7] = USER_BIND_KIND_DEBUG_CAMERA,
|
||||
[SYS_BTN_F1] = USER_BIND_KIND_DEBUG_PAUSE,
|
||||
[SYS_BTN_F2] = USER_BIND_KIND_DEBUG_CAMERA,
|
||||
[SYS_BTN_F3] = USER_BIND_KIND_DEBUG_DRAW,
|
||||
[SYS_BTN_F11] = USER_BIND_KIND_FULLSCREEN,
|
||||
[SYS_BTN_MWHEELUP] = USER_BIND_KIND_ZOOM_IN,
|
||||
[SYS_BTN_MWHEELDOWN] = USER_BIND_KIND_ZOOM_OUT,
|
||||
@ -575,6 +576,16 @@ INTERNAL void user_update(void)
|
||||
}
|
||||
}
|
||||
|
||||
/* Test pause */
|
||||
{
|
||||
struct bind_state state = G.bind_states[USER_BIND_KIND_DEBUG_PAUSE];
|
||||
if (state.num_presses) {
|
||||
queue_game_cmd(&cmd_list, (struct game_cmd) {
|
||||
.kind = GAME_CMD_KIND_PAUSE
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
/* Test spawn */
|
||||
{
|
||||
struct bind_state state = G.bind_states[USER_BIND_KIND_DEBUG_SPAWN];
|
||||
@ -766,9 +777,10 @@ INTERNAL void user_update(void)
|
||||
if (!ent->valid) continue;
|
||||
if (ent->is_root) continue;
|
||||
|
||||
struct sprite_tag sprite = ent->sprite;
|
||||
|
||||
/* Skip undrawable entities */
|
||||
if (sprite_tag_is_nil(ent->sprite)
|
||||
&& !entity_has_prop(ent, ENTITY_PROP_CAMERA)) {
|
||||
if (sprite_tag_is_nil(sprite) && !entity_has_prop(ent, ENTITY_PROP_CAMERA)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
@ -783,13 +795,12 @@ INTERNAL void user_update(void)
|
||||
struct xform sprite_xform = xf;
|
||||
|
||||
/* Draw sprite */
|
||||
if (!sprite_tag_is_nil(ent->sprite)) {
|
||||
if (!sprite_tag_is_nil(sprite)) {
|
||||
/* Calculate sprite xform */
|
||||
sprite_xform = xform_mul(xf, ent->sprite_local_xform);
|
||||
|
||||
|
||||
/* Async load */
|
||||
struct sprite_tag sprite = ent->sprite;
|
||||
struct sprite_sheet *sheet = sprite_sheet_from_tag_async(sprite_frame_scope, sprite);
|
||||
struct sprite_texture *texture = sprite_texture_from_tag_async(sprite_frame_scope, sprite);
|
||||
(UNUSED)texture;
|
||||
@ -863,7 +874,6 @@ INTERNAL void user_update(void)
|
||||
|
||||
/* Draw slices */
|
||||
if (!sprite_tag_is_nil(ent->sprite)) {
|
||||
struct sprite_tag sprite = ent->sprite;
|
||||
struct sprite_sheet *sheet = sprite_sheet_from_tag_async(sprite_frame_scope, sprite);
|
||||
|
||||
for (u64 i = 0; i < sheet->slice_groups_count; ++i) {
|
||||
@ -1018,6 +1028,9 @@ INTERNAL void user_update(void)
|
||||
draw_text(G.viewport_canvas, font, pos, string_format(temp.arena, STR("time: %F"), FMT_FLOAT((f64)G.time)));
|
||||
pos.y += spacing;
|
||||
|
||||
draw_text(G.viewport_canvas, font, pos, string_format(temp.arena, STR("world time: %F"), FMT_FLOAT((f64)G.world.time)));
|
||||
pos.y += spacing;
|
||||
|
||||
draw_text(G.viewport_canvas, font, pos, string_format(temp.arena, STR("screen_size: (%F, %F)"), FMT_FLOAT((f64)G.screen_size.x), FMT_FLOAT((f64)G.screen_size.y)));
|
||||
pos.y += spacing;
|
||||
|
||||
|
||||
@ -26,6 +26,7 @@ enum user_bind_kind {
|
||||
USER_BIND_KIND_DEBUG_SPAWN,
|
||||
USER_BIND_KIND_DEBUG_DRAW,
|
||||
USER_BIND_KIND_DEBUG_CAMERA,
|
||||
USER_BIND_KIND_DEBUG_PAUSE,
|
||||
USER_BIND_KIND_FULLSCREEN,
|
||||
USER_BIND_KIND_ZOOM_IN,
|
||||
USER_BIND_KIND_ZOOM_OUT,
|
||||
|
||||
Loading…
Reference in New Issue
Block a user