diff --git a/src/ase/ase.c b/src/ase/ase.c index 37723322..9e85bc8a 100644 --- a/src/ase/ase.c +++ b/src/ase/ase.c @@ -2,6 +2,7 @@ //~ Inflate // // DEFLATE decoder based on Handmade Hero's png parser +// https://www.youtube.com/watch?v=fuPhHEBTShI //- Bitbuff diff --git a/src/base/base.cgh b/src/base/base.cgh index 3fc7cd7e..db64b312 100644 --- a/src/base/base.cgh +++ b/src/base/base.cgh @@ -771,7 +771,6 @@ Struct(ComputeShaderDesc) { ResourceKey resource; u32 x, y, z; }; #define DeclPixelShader(name, resource_hash) #endif - //////////////////////////////////////////////////////////// //~ Dynamic api linkage diff --git a/src/meta/meta.c b/src/meta/meta.c index 0edf71ea..9b147646 100644 --- a/src/meta/meta.c +++ b/src/meta/meta.c @@ -717,8 +717,8 @@ void M_BuildEntryPoint(WaveLaneCtx *lane) if (arg0_tok->valid) { String shader_name = arg0_tok->s; - Vec3U32 thread_dims = Zi; - i32 thread_dims_count = 1; + Vec3U32 group_dims = Zi; + i32 group_dims_count = 1; { StringList thread_count_args = Zi; for (i32 arg_idx = 1; arg_idx < countof(entry->arg_tokens); ++arg_idx) @@ -733,21 +733,21 @@ void M_BuildEntryPoint(WaveLaneCtx *lane) break; } } - String thread_count_str = StringFromList(perm, thread_count_args, Lit(" ")); - Vec3 tmp = CR_Vec3FromString(thread_count_str); - thread_dims.x = MaxI32(tmp.x, 1); - thread_dims.y = MaxI32(tmp.y, 1); - thread_dims.z = MaxI32(tmp.z, 1); - // Determine compute shader dimensions by counting comma-separated values in dimensions string - for (u64 char_idx = 0; char_idx < thread_count_str.len; ++char_idx) + String group_dims_str = StringFromList(perm, thread_count_args, Lit(" ")); + Vec3 tmp = CR_Vec3FromString(group_dims_str); + group_dims.x = MaxI32(tmp.x, 1); + group_dims.y = MaxI32(tmp.y, 1); + group_dims.z = MaxI32(tmp.z, 1); + // Determine compute shader dimensions type by counting comma-separated values in group size string + for (u64 char_idx = 0; char_idx < group_dims_str.len; ++char_idx) { - u8 c = thread_count_str.text[char_idx]; + u8 c = group_dims_str.text[char_idx]; if (c == ',') { - thread_dims_count += 1; + group_dims_count += 1; } } - thread_dims_count = ClampI32(thread_dims_count, 1, 3); + group_dims_count = ClampI32(group_dims_count, 1, 3); } String decl_type = ( kind == M_EntryKind_VertexShader ? Lit("DeclVertexShader") : @@ -764,8 +764,8 @@ void M_BuildEntryPoint(WaveLaneCtx *lane) "#define %F__ThreadDimsType %F", FmtString(shader_name), FmtString( - thread_dims_count == 1 ? Lit("u32") : - thread_dims_count == 2 ? Lit("Vec2U32") : + group_dims_count == 1 ? Lit("u32") : + group_dims_count == 2 ? Lit("Vec2U32") : Lit("Vec3U32") ) ); @@ -782,9 +782,9 @@ void M_BuildEntryPoint(WaveLaneCtx *lane) FmtString(decl_type), FmtString(shader_name), FmtHex(shader_resource_hash), - FmtUint(thread_dims.x), - FmtUint(thread_dims.y), - FmtUint(thread_dims.z) + FmtUint(group_dims.x), + FmtUint(group_dims.y), + FmtUint(group_dims.z) ); } else diff --git a/src/pp/pp.c b/src/pp/pp.c index ecd0cc4b..271f0b1c 100644 --- a/src/pp/pp.c +++ b/src/pp/pp.c @@ -5,6 +5,7 @@ Readonly P_Ent P_NilEnt = { .xf = CompXformIdentity, .control.look = { 1, 0 }, .health = 1, + .lifetime_seconds = Inf, }; Readonly P_Constraint P_NilConstraint = { @@ -2168,11 +2169,24 @@ void P_StepFrame(P_Frame *frame) i64 sim_dt_ns = SIM_TICK_INTERVAL_NS; f64 sim_dt = SecondsFromNs(sim_dt_ns); + ////////////////////////////// + //- Kill ents with expired lifetimes + + { + for (P_Ent *ent = P_FirstEnt(frame); !P_IsEntNil(ent); ent = P_NextEnt(ent)) + { + if (ent->lifetime_seconds != Inf && SecondsFromNs(frame->time_ns - ent->created_at_ns) >= ent->lifetime_seconds) + { + ent->exists = 0; + } + } + } + ////////////////////////////// //- Prune ents { - // Mark dead entities + // Mark dead child ents for (P_Ent *ent = P_FirstEnt(frame); !P_IsEntNil(ent); ent = P_NextEnt(ent)) { if (ent->exists <= 0) diff --git a/src/pp/pp.h b/src/pp/pp.h index ee46740a..265a5573 100644 --- a/src/pp/pp.h +++ b/src/pp/pp.h @@ -116,6 +116,7 @@ Struct(P_Ent) u64 rand_seq; i64 created_at_ns; i64 created_at_tick; + f64 lifetime_seconds; //- Build data diff --git a/src/pp/pp_sim/pp_sim_core.c b/src/pp/pp_sim/pp_sim_core.c index ebc25f47..1073135d 100644 --- a/src/pp/pp_sim/pp_sim_core.c +++ b/src/pp/pp_sim/pp_sim_core.c @@ -921,33 +921,6 @@ void S_TickForever(WaveLaneCtx *lane) ZeroStruct(&P_tl.out_msgs); } - ////////////////////////////// - //- Prune ents - - // { - // i64 ents_to_prune_count = 0; - // P_Ent **ents_to_prune = PushStructsNoZero(frame_arena, P_Ent *, world_frame->ents_count); - // for (P_Ent *ent = P_FirstEnt(world_frame); !P_IsEntNil(ent); ent = P_NextEnt(ent)) - // { - // if (ent->exists <= 0) - // { - // ents_to_prune[ents_to_prune_count] = ent; - // ents_to_prune_count += 1; - // } - // } - - // for (i64 prune_idx = 0; prune_idx < ents_to_prune_count; ++prune_idx) - // { - // // FIXME: Ensure sure prunes are received by player - // P_Ent *ent = ents_to_prune[prune_idx]; - // P_EntBin *bin = &world_frame->ent_bins[ent->key.v % world_frame->ent_bins_count]; - // DllQueueRemoveNP(bin->first, bin->last, ent, next_in_bin, prev_in_bin); - // DllQueueRemoveNPZ(&P_NilEnt, world_frame->first_ent, world_frame->last_ent, ent, next, prev); - // world_frame->ents_count -= 1; - // SllStackPush(world->first_free_ent, ent); - // } - // } - ////////////////////////////// //- Publish Sim -> User data diff --git a/src/pp/pp_transcode.c b/src/pp/pp_transcode.c index d7456d8b..8f1c96b6 100644 --- a/src/pp/pp_transcode.c +++ b/src/pp/pp_transcode.c @@ -76,6 +76,7 @@ String P_PackWorld(Arena *arena, P_World *src_world) result.len += StringF(arena, " created_at_ns: \"%F\"\n", FmtSint(ent->created_at_ns)).len; result.len += StringF(arena, " created_at_tick: \"%F\"\n", FmtSint(ent->created_at_tick)).len; result.len += StringF(arena, " last_spawn_reset_ns: \"%F\"\n", FmtSint(ent->last_spawn_reset_ns)).len; + result.len += StringF(arena, " lifetime_seconds: \"%F\"\n", FmtFloat(ent->lifetime_seconds)).len; result.len += StringF(arena, " pickup: \"0x%F\"\n", FmtHex(ent->pickup.v)).len; result.len += StringF(arena, " pos: \"%F\"\n", FmtFloat2(ent->xf.t)).len; result.len += StringF(arena, " angle: \"%F\"\n", FmtFloat(AngleFromVec2(ent->xf.r))).len; @@ -216,6 +217,10 @@ P_UnpackedWorld P_UnpackWorld(Arena *arena, String packed) { ent->last_spawn_reset_ns = CR_IntFromString(attr->value); } + if (MatchString(attr->name, Lit("lifetime_seconds"))) + { + ent->lifetime_seconds = CR_FloatFromString(attr->value); + } if (MatchString(attr->name, Lit("pickup"))) { ent->pickup.v = CR_IntFromString(attr->value); diff --git a/src/pp/pp_vis/pp_vis_core.c b/src/pp/pp_vis/pp_vis_core.c index 1611d94e..a33e9eb3 100644 --- a/src/pp/pp_vis/pp_vis_core.c +++ b/src/pp/pp_vis/pp_vis_core.c @@ -1902,6 +1902,10 @@ void V_TickForever(WaveLaneCtx *lane) + + + + ////////////////////////////// //- Query local player