move shared vis-sim functionality to pp layer
This commit is contained in:
parent
4df1418aa5
commit
32938a9abe
1258
src/pp/pp.c
Normal file
1258
src/pp/pp.c
Normal file
File diff suppressed because it is too large
Load Diff
454
src/pp/pp.h
Normal file
454
src/pp/pp.h
Normal file
@ -0,0 +1,454 @@
|
|||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Key types
|
||||||
|
|
||||||
|
#define P_NilKey ((P_Key) { 0 })
|
||||||
|
|
||||||
|
Struct(P_Key)
|
||||||
|
{
|
||||||
|
u64 v;
|
||||||
|
};
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Shape types
|
||||||
|
|
||||||
|
Struct(P_ShapeDesc)
|
||||||
|
{
|
||||||
|
f32 radius;
|
||||||
|
f32 mass;
|
||||||
|
i32 count;
|
||||||
|
Vec2 points[8];
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_Shape)
|
||||||
|
{
|
||||||
|
f32 mass;
|
||||||
|
Vec2 centroid;
|
||||||
|
Vec2 center_of_mass;
|
||||||
|
|
||||||
|
f32 radius;
|
||||||
|
i32 points_count;
|
||||||
|
Vec2 points[8];
|
||||||
|
};
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Ent types
|
||||||
|
|
||||||
|
// TODO: Move boolean fields into bitwise property flags
|
||||||
|
|
||||||
|
// TODO: Pack efficiently, deduplicate redundant fields
|
||||||
|
|
||||||
|
Struct(P_Ent)
|
||||||
|
{
|
||||||
|
//////////////////////////////
|
||||||
|
//- Internal world state
|
||||||
|
|
||||||
|
P_Ent *next;
|
||||||
|
P_Ent *prev;
|
||||||
|
|
||||||
|
P_Ent *next_in_bin;
|
||||||
|
P_Ent *prev_in_bin;
|
||||||
|
|
||||||
|
//////////////////////////////
|
||||||
|
//- Persistent data
|
||||||
|
|
||||||
|
P_Key key;
|
||||||
|
b32 valid;
|
||||||
|
|
||||||
|
//////////////////////////////
|
||||||
|
//- Build data
|
||||||
|
|
||||||
|
f32 exists;
|
||||||
|
|
||||||
|
b32 is_player;
|
||||||
|
f32 health;
|
||||||
|
|
||||||
|
Xform last_xf;
|
||||||
|
Xform xf;
|
||||||
|
|
||||||
|
Vec2 move;
|
||||||
|
Vec2 look;
|
||||||
|
f32 fire_held;
|
||||||
|
f32 fire_presses;
|
||||||
|
|
||||||
|
// TODO: Remove this (weapon testing)
|
||||||
|
i64 last_fire_ns;
|
||||||
|
b32 has_weapon;
|
||||||
|
|
||||||
|
P_Key bullet_firer;
|
||||||
|
b32 is_bullet;
|
||||||
|
Vec2 bullet_start;
|
||||||
|
Vec2 bullet_end;
|
||||||
|
|
||||||
|
b32 has_hit;
|
||||||
|
Vec2 hit_entry;
|
||||||
|
Vec2 hit_entry_normal;
|
||||||
|
|
||||||
|
//////////////////////////////
|
||||||
|
//- Solver data
|
||||||
|
|
||||||
|
Vec2 solved_v;
|
||||||
|
f32 solved_w;
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_EntListNode)
|
||||||
|
{
|
||||||
|
P_EntListNode *next;
|
||||||
|
P_Ent ent;
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_EntList)
|
||||||
|
{
|
||||||
|
P_EntListNode *first;
|
||||||
|
P_EntListNode *last;
|
||||||
|
i64 count;
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_EntBin)
|
||||||
|
{
|
||||||
|
P_Ent *first;
|
||||||
|
P_Ent *last;
|
||||||
|
};
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ World types
|
||||||
|
|
||||||
|
Struct(P_World)
|
||||||
|
{
|
||||||
|
u64 seed;
|
||||||
|
i64 tick;
|
||||||
|
i64 time_ns;
|
||||||
|
|
||||||
|
i64 ents_count;
|
||||||
|
P_Ent *first_ent;
|
||||||
|
P_Ent *last_ent;
|
||||||
|
|
||||||
|
i64 ent_bins_count;
|
||||||
|
P_EntBin *ent_bins;
|
||||||
|
|
||||||
|
u8 *tiles;
|
||||||
|
};
|
||||||
|
|
||||||
|
Enum(P_DeltaKind)
|
||||||
|
{
|
||||||
|
P_DeltaKind_Reset,
|
||||||
|
P_DeltaKind_RawEnt,
|
||||||
|
P_DeltaKind_RawTiles,
|
||||||
|
P_DeltaKind_Tile,
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_Delta)
|
||||||
|
{
|
||||||
|
P_DeltaKind kind;
|
||||||
|
|
||||||
|
P_Ent ent;
|
||||||
|
|
||||||
|
u8 *raw_tiles;
|
||||||
|
P_TileKind tile_kind;
|
||||||
|
Rng2I32 tile_range;
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_DeltaNode)
|
||||||
|
{
|
||||||
|
P_DeltaNode *next;
|
||||||
|
P_Delta delta;
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_Snapshot)
|
||||||
|
{
|
||||||
|
u64 seed;
|
||||||
|
i64 tick;
|
||||||
|
i64 time_ns;
|
||||||
|
|
||||||
|
i64 deltas_count;
|
||||||
|
P_DeltaNode *first_delta_node;
|
||||||
|
P_DeltaNode *last_delta_node;
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_SnapshotNode)
|
||||||
|
{
|
||||||
|
P_SnapshotNode *next;
|
||||||
|
P_Snapshot snapshot;
|
||||||
|
};
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Collision types
|
||||||
|
|
||||||
|
Struct(P_SupportPoint)
|
||||||
|
{
|
||||||
|
Vec2 p;
|
||||||
|
u32 id; // Index of the originating piont in the shape
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_CollisionPoint)
|
||||||
|
{
|
||||||
|
Vec2 p;
|
||||||
|
f32 separation;
|
||||||
|
u32 id; // Based on polygon edge-to-edge
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_MenkowskiPoint)
|
||||||
|
{
|
||||||
|
Vec2 p; // Menkowski difference point
|
||||||
|
P_SupportPoint s0; // Support point of first shape in dir
|
||||||
|
P_SupportPoint s1; // Support point of second shape in -dir
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_MenkowskiSimplex)
|
||||||
|
{
|
||||||
|
i32 count;
|
||||||
|
P_MenkowskiPoint a, b, c;
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_ClippedLine)
|
||||||
|
{
|
||||||
|
Vec2 a0_clipped, b0_clipped;
|
||||||
|
Vec2 a1_clipped, b1_clipped;
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_CollisionResult)
|
||||||
|
{
|
||||||
|
// Collision manifold
|
||||||
|
i32 collision_points_count;
|
||||||
|
P_CollisionPoint collision_points[2];
|
||||||
|
Vec2 collision_normal;
|
||||||
|
|
||||||
|
// Closest points
|
||||||
|
Vec2 closest_p0;
|
||||||
|
Vec2 closest_p1;
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_RaycastResult)
|
||||||
|
{
|
||||||
|
b32 is_intersecting;
|
||||||
|
Vec2 p;
|
||||||
|
Vec2 normal;
|
||||||
|
};
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Constraint types
|
||||||
|
|
||||||
|
Struct(P_ContactPoint)
|
||||||
|
{
|
||||||
|
Vec2 vcp0;
|
||||||
|
Vec2 vcp1;
|
||||||
|
f32 starting_separation;
|
||||||
|
f32 inv_normal_mass;
|
||||||
|
f32 inv_tangent_mass;
|
||||||
|
u32 id;
|
||||||
|
|
||||||
|
f32 solved_normal_impulse;
|
||||||
|
f32 solved_tangent_impulse;
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_Constraint)
|
||||||
|
{
|
||||||
|
i64 last_touched_tick;
|
||||||
|
P_Key ent0;
|
||||||
|
P_Key ent1;
|
||||||
|
|
||||||
|
Vec2 static_center0;
|
||||||
|
Vec2 static_center1;
|
||||||
|
|
||||||
|
f32 inv_m0;
|
||||||
|
f32 inv_m1;
|
||||||
|
f32 inv_i0;
|
||||||
|
f32 inv_i1;
|
||||||
|
|
||||||
|
Vec2 normal;
|
||||||
|
f32 friction;
|
||||||
|
|
||||||
|
i32 points_count;
|
||||||
|
P_ContactPoint points[2];
|
||||||
|
};
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Debug visualization types
|
||||||
|
|
||||||
|
Enum(P_DebugDrawKind)
|
||||||
|
{
|
||||||
|
P_DebugDrawKind_Point,
|
||||||
|
P_DebugDrawKind_Line,
|
||||||
|
P_DebugDrawKind_Rect,
|
||||||
|
P_DebugDrawKind_Shape,
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_DebugDrawNode)
|
||||||
|
{
|
||||||
|
P_DebugDrawNode *next;
|
||||||
|
P_DebugDrawKind kind;
|
||||||
|
u32 srgb32;
|
||||||
|
union
|
||||||
|
{
|
||||||
|
struct
|
||||||
|
{
|
||||||
|
Vec2 p;
|
||||||
|
} point;
|
||||||
|
struct
|
||||||
|
{
|
||||||
|
Vec2 p0;
|
||||||
|
Vec2 p1;
|
||||||
|
} line;
|
||||||
|
Rng2 rect;
|
||||||
|
P_Shape shape;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Command types
|
||||||
|
|
||||||
|
Enum(P_CmdKind)
|
||||||
|
{
|
||||||
|
P_CmdKind_Nop,
|
||||||
|
P_CmdKind_Save,
|
||||||
|
P_CmdKind_Delta,
|
||||||
|
P_CmdKind_Control,
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_Cmd)
|
||||||
|
{
|
||||||
|
P_CmdKind kind;
|
||||||
|
|
||||||
|
// Delta
|
||||||
|
P_Delta delta;
|
||||||
|
|
||||||
|
// Control
|
||||||
|
P_Key target;
|
||||||
|
Vec2 move;
|
||||||
|
Vec2 look;
|
||||||
|
b32 fire_held;
|
||||||
|
i32 fire_presses;
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_CmdNode)
|
||||||
|
{
|
||||||
|
P_CmdNode *next;
|
||||||
|
P_Cmd cmd;
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_InputState)
|
||||||
|
{
|
||||||
|
Arena *arena;
|
||||||
|
P_CmdNode *first_cmd_node;
|
||||||
|
P_CmdNode *last_cmd_node;
|
||||||
|
u64 cmds_count;
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_OutputState)
|
||||||
|
{
|
||||||
|
Arena *arena;
|
||||||
|
P_SnapshotNode *first_snapshot_node;
|
||||||
|
P_SnapshotNode *last_snapshot_node;
|
||||||
|
u64 snapshots_count;
|
||||||
|
|
||||||
|
P_DebugDrawNode *first_debug_draw_node;
|
||||||
|
P_DebugDrawNode *last_debug_draw_node;
|
||||||
|
i64 debug_draw_nodes_count;
|
||||||
|
};
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ State types
|
||||||
|
|
||||||
|
Struct(P_Ctx)
|
||||||
|
{
|
||||||
|
//- Sim input
|
||||||
|
TicketMutex sim_input_back_tm;
|
||||||
|
i32 sim_input_back_idx;
|
||||||
|
P_InputState sim_input_states[2];
|
||||||
|
|
||||||
|
//- Sim output
|
||||||
|
TicketMutex sim_output_back_tm;
|
||||||
|
i32 sim_output_back_idx;
|
||||||
|
P_OutputState sim_output_states[2];
|
||||||
|
};
|
||||||
|
|
||||||
|
Struct(P_ThreadLocalCtx)
|
||||||
|
{
|
||||||
|
Arena *debug_arena;
|
||||||
|
b32 debug_draw_enabled;
|
||||||
|
P_DebugDrawNode *first_debug_draw_node;
|
||||||
|
P_DebugDrawNode *last_debug_draw_node;
|
||||||
|
i64 debug_draw_nodes_count;
|
||||||
|
};
|
||||||
|
|
||||||
|
extern P_Ctx P;
|
||||||
|
extern ThreadLocal P_ThreadLocalCtx P_tl;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Bootstrap
|
||||||
|
|
||||||
|
void P_Bootstrap(void);
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Nil helpers
|
||||||
|
|
||||||
|
b32 P_IsKeyNil(P_Key key);
|
||||||
|
b32 P_IsEntNil(P_Ent *ent);
|
||||||
|
b32 P_MatchKey(P_Key a, P_Key b);
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Key helpers
|
||||||
|
|
||||||
|
P_Key P_RandKey(void);
|
||||||
|
|
||||||
|
#define P_FmtKey(key) FmtHandle((key).v)
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Tile helpers
|
||||||
|
|
||||||
|
String P_NameFromTileKind(P_TileKind kind);
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Delta helpers
|
||||||
|
|
||||||
|
void P_UpdateWorldFromDelta(Arena *arena, P_World *world, P_Delta *delta);
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Shape helpers
|
||||||
|
|
||||||
|
P_Shape P_ShapeFromDescEx(P_ShapeDesc desc);
|
||||||
|
#define P_ShapeFromDesc(...) P_ShapeFromDescEx((P_ShapeDesc) { __VA_ARGS__ })
|
||||||
|
|
||||||
|
P_Shape P_MulXformShape(Xform xf, P_Shape shape);
|
||||||
|
Rng2 P_BoundingBoxFromShape(P_Shape shape);
|
||||||
|
|
||||||
|
P_Shape P_LocalShapeFromEnt(P_Ent *ent);
|
||||||
|
P_Shape P_WorldShapeFromEnt(P_Ent *ent);
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Collision
|
||||||
|
|
||||||
|
P_SupportPoint P_SupportPointFromShapeEx(P_Shape shape, Vec2 dir, i32 ignore_idx);
|
||||||
|
P_SupportPoint P_SupportPointFromShape(P_Shape shape, Vec2 dir);
|
||||||
|
P_MenkowskiPoint P_MenkowskiPointFromShapes(P_Shape shape0, P_Shape shape1, Vec2 dir);
|
||||||
|
P_ClippedLine P_ClipLineToLine(Vec2 a0, Vec2 b0, Vec2 a1, Vec2 b1, Vec2 normal);
|
||||||
|
Vec2 P_ClipPointToLine(Vec2 a, Vec2 b, Vec2 p, Vec2 normal);
|
||||||
|
|
||||||
|
P_CollisionResult P_CollisionResultFromShapes(P_Shape shape0, P_Shape shape1);
|
||||||
|
P_RaycastResult P_RaycastShape(P_Shape shape, Vec2 ray_start, Vec2 ray_dir);
|
||||||
|
|
||||||
|
Vec2 P_EdgePointFromShape(P_Shape shape, Vec2 dir);
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Lookup helpers
|
||||||
|
|
||||||
|
P_Ent *P_EntFromKey(P_World *world, P_Key key);
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Iteration helpers
|
||||||
|
|
||||||
|
P_Ent *P_FirstEnt(P_World *world);
|
||||||
|
P_Ent *P_NextEnt(P_Ent *e);
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ List helpers
|
||||||
|
|
||||||
|
P_Ent *P_PushTempEnt(Arena *arena, P_EntList *list);
|
||||||
|
void P_SpawnEntsFromList(Arena *arena, P_World *world, P_EntList ents);
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Debug draw
|
||||||
|
|
||||||
|
void P_DebugDrawPoint(Vec2 p, Vec4 srgb);
|
||||||
|
void P_DebugDrawLine(Vec2 p0, Vec2 p1, Vec4 srgb);
|
||||||
|
void P_DebugDrawRect(Rng2 rect, Vec4 srgb);
|
||||||
|
void P_DebugDrawShape(P_Shape shape, Vec4 srgb);
|
||||||
@ -5,8 +5,23 @@
|
|||||||
|
|
||||||
@EmbedDir P_Resources pp_res
|
@EmbedDir P_Resources pp_res
|
||||||
|
|
||||||
|
//////////////////////////////
|
||||||
|
//- Api
|
||||||
|
|
||||||
|
@IncludeC pp_shared.cgh
|
||||||
|
@IncludeG pp_shared.cgh
|
||||||
|
@IncludeC pp.h
|
||||||
|
@IncludeC pp_transcode.h
|
||||||
|
|
||||||
|
@Bootstrap P_Bootstrap
|
||||||
|
|
||||||
//////////////////////////////
|
//////////////////////////////
|
||||||
//- Impl
|
//- Impl
|
||||||
|
|
||||||
@DefaultDownstream Any pp_vis
|
@IncludeC pp_shared.cg
|
||||||
|
@IncludeG pp_shared.cg
|
||||||
|
@IncludeC pp.c
|
||||||
|
@IncludeC pp_transcode.c
|
||||||
|
|
||||||
@DefaultDownstream Any pp_sim
|
@DefaultDownstream Any pp_sim
|
||||||
|
@DefaultDownstream Any pp_vis
|
||||||
|
|||||||
27
src/pp/pp_shared.cg
Normal file
27
src/pp/pp_shared.cg
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Tile helpers
|
||||||
|
|
||||||
|
i32 P_TileIdxFromTilePos(Vec2 p)
|
||||||
|
{
|
||||||
|
i32 x = ClampI32(FloorF32(p.x), 0, P_TilesPitch - 1);
|
||||||
|
i32 y = ClampI32(FloorF32(p.y), 0, P_TilesPitch - 1);
|
||||||
|
i32 result = x + (y * P_TilesPitch);
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
#if IsLanguageC
|
||||||
|
String P_TileNameFromKind(P_TileKind kind)
|
||||||
|
{
|
||||||
|
PERSIST Readonly String tile_names[P_TileKind_COUNT] = {
|
||||||
|
#define X(name, ...) [P_TileKind_##name] = CompLit(#name),
|
||||||
|
P_TilesXMacro(X)
|
||||||
|
#undef X
|
||||||
|
};
|
||||||
|
String result = Zi;
|
||||||
|
if (kind >= 0 && kind < countof(tile_names))
|
||||||
|
{
|
||||||
|
result = tile_names[kind];
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
35
src/pp/pp_shared.cgh
Normal file
35
src/pp/pp_shared.cgh
Normal file
@ -0,0 +1,35 @@
|
|||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Tile types
|
||||||
|
|
||||||
|
#define P_WorldPitch 64.0
|
||||||
|
|
||||||
|
#define P_TilesPerMeter 2.0
|
||||||
|
#define P_TilesPerSqMeter (V_TilesPerMeter * V_TilesPerMeter)
|
||||||
|
|
||||||
|
#define P_TilesPitch (P_WorldPitch * P_TilesPerMeter)
|
||||||
|
#define P_TilesCount (P_TilesPitch * P_TilesPitch)
|
||||||
|
|
||||||
|
#define P_TilesXMacro(X) \
|
||||||
|
X(Empty) \
|
||||||
|
X(Tile) \
|
||||||
|
X(Carpet) \
|
||||||
|
X(Wall) \
|
||||||
|
/* -------------------- */
|
||||||
|
|
||||||
|
//- Tiles kinds enum
|
||||||
|
Enum(P_TileKind)
|
||||||
|
{
|
||||||
|
#define X(name, ...) P_TileKind_##name,
|
||||||
|
P_TilesXMacro(X)
|
||||||
|
#undef X
|
||||||
|
P_TileKind_COUNT
|
||||||
|
};
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Tile helpers
|
||||||
|
|
||||||
|
i32 P_TileIdxFromTilePos(Vec2 p);
|
||||||
|
|
||||||
|
#if IsLanguageC
|
||||||
|
String P_TileNameFromKind(P_TileKind kind);
|
||||||
|
#endif
|
||||||
@ -9,11 +9,7 @@
|
|||||||
//////////////////////////////
|
//////////////////////////////
|
||||||
//- Api
|
//- Api
|
||||||
|
|
||||||
@IncludeC pp_sim_shared.cgh
|
|
||||||
@IncludeG pp_sim_shared.cgh
|
|
||||||
|
|
||||||
@IncludeC pp_sim_core.h
|
@IncludeC pp_sim_core.h
|
||||||
@IncludeC pp_sim_transcode.h
|
|
||||||
|
|
||||||
@Bootstrap S_Bootstrap
|
@Bootstrap S_Bootstrap
|
||||||
|
|
||||||
@ -21,6 +17,3 @@
|
|||||||
//- Impl
|
//- Impl
|
||||||
|
|
||||||
@IncludeC pp_sim_core.c
|
@IncludeC pp_sim_core.c
|
||||||
@IncludeC pp_sim_transcode.c
|
|
||||||
@IncludeC pp_sim_shared.cg
|
|
||||||
@IncludeG pp_sim_shared.cg
|
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@ -1,382 +1,13 @@
|
|||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Key types
|
|
||||||
|
|
||||||
#define S_NilKey ((S_Key) { 0 })
|
|
||||||
|
|
||||||
Struct(S_Key)
|
|
||||||
{
|
|
||||||
u64 v;
|
|
||||||
};
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Shape types
|
|
||||||
|
|
||||||
Struct(S_ShapeDesc)
|
|
||||||
{
|
|
||||||
f32 radius;
|
|
||||||
f32 mass;
|
|
||||||
i32 count;
|
|
||||||
Vec2 points[8];
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_Shape)
|
|
||||||
{
|
|
||||||
f32 mass;
|
|
||||||
Vec2 centroid;
|
|
||||||
Vec2 center_of_mass;
|
|
||||||
|
|
||||||
f32 radius;
|
|
||||||
i32 points_count;
|
|
||||||
Vec2 points[8];
|
|
||||||
};
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Ent types
|
|
||||||
|
|
||||||
// TODO: Move boolean fields into bitwise property flags
|
|
||||||
|
|
||||||
// TODO: Pack efficiently, deduplicate redundant fields
|
|
||||||
|
|
||||||
Struct(S_Ent)
|
|
||||||
{
|
|
||||||
//////////////////////////////
|
|
||||||
//- Internal world state
|
|
||||||
|
|
||||||
S_Ent *next;
|
|
||||||
S_Ent *prev;
|
|
||||||
|
|
||||||
S_Ent *next_in_bin;
|
|
||||||
S_Ent *prev_in_bin;
|
|
||||||
|
|
||||||
//////////////////////////////
|
|
||||||
//- Persistent data
|
|
||||||
|
|
||||||
S_Key key;
|
|
||||||
b32 valid;
|
|
||||||
|
|
||||||
//////////////////////////////
|
|
||||||
//- Build data
|
|
||||||
|
|
||||||
f32 exists;
|
|
||||||
|
|
||||||
b32 is_player;
|
|
||||||
f32 health;
|
|
||||||
|
|
||||||
Xform last_xf;
|
|
||||||
Xform xf;
|
|
||||||
|
|
||||||
Vec2 move;
|
|
||||||
Vec2 look;
|
|
||||||
f32 fire_held;
|
|
||||||
f32 fire_presses;
|
|
||||||
|
|
||||||
// TODO: Remove this (weapon testing)
|
|
||||||
i64 last_fire_ns;
|
|
||||||
b32 has_weapon;
|
|
||||||
|
|
||||||
S_Key bullet_firer;
|
|
||||||
b32 is_bullet;
|
|
||||||
Vec2 bullet_start;
|
|
||||||
Vec2 bullet_end;
|
|
||||||
|
|
||||||
b32 has_hit;
|
|
||||||
Vec2 hit_entry;
|
|
||||||
Vec2 hit_entry_normal;
|
|
||||||
|
|
||||||
//////////////////////////////
|
|
||||||
//- Solver data
|
|
||||||
|
|
||||||
Vec2 solved_v;
|
|
||||||
f32 solved_w;
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_EntListNode)
|
|
||||||
{
|
|
||||||
S_EntListNode *next;
|
|
||||||
S_Ent ent;
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_EntList)
|
|
||||||
{
|
|
||||||
S_EntListNode *first;
|
|
||||||
S_EntListNode *last;
|
|
||||||
i64 count;
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_EntBin)
|
|
||||||
{
|
|
||||||
S_Ent *first;
|
|
||||||
S_Ent *last;
|
|
||||||
};
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Collision types
|
|
||||||
|
|
||||||
Struct(S_SupportPoint)
|
|
||||||
{
|
|
||||||
Vec2 p;
|
|
||||||
u32 id; // Index of the originating piont in the shape
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_CollisionPoint)
|
|
||||||
{
|
|
||||||
Vec2 p;
|
|
||||||
f32 separation;
|
|
||||||
u32 id; // Based on polygon edge-to-edge
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_MenkowskiPoint)
|
|
||||||
{
|
|
||||||
Vec2 p; // Menkowski difference point
|
|
||||||
S_SupportPoint s0; // Support point of first shape in dir
|
|
||||||
S_SupportPoint s1; // Support point of second shape in -dir
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_MenkowskiSimplex)
|
|
||||||
{
|
|
||||||
i32 count;
|
|
||||||
S_MenkowskiPoint a, b, c;
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_ClippedLine)
|
|
||||||
{
|
|
||||||
Vec2 a0_clipped, b0_clipped;
|
|
||||||
Vec2 a1_clipped, b1_clipped;
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_CollisionResult)
|
|
||||||
{
|
|
||||||
// Collision manifold
|
|
||||||
i32 collision_points_count;
|
|
||||||
S_CollisionPoint collision_points[2];
|
|
||||||
Vec2 collision_normal;
|
|
||||||
|
|
||||||
// Closest points
|
|
||||||
Vec2 closest_p0;
|
|
||||||
Vec2 closest_p1;
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_RaycastResult)
|
|
||||||
{
|
|
||||||
b32 is_intersecting;
|
|
||||||
Vec2 p;
|
|
||||||
Vec2 normal;
|
|
||||||
};
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Constraint types
|
|
||||||
|
|
||||||
Struct(S_ContactPoint)
|
|
||||||
{
|
|
||||||
Vec2 vcp0;
|
|
||||||
Vec2 vcp1;
|
|
||||||
f32 starting_separation;
|
|
||||||
f32 inv_normal_mass;
|
|
||||||
f32 inv_tangent_mass;
|
|
||||||
u32 id;
|
|
||||||
|
|
||||||
f32 solved_normal_impulse;
|
|
||||||
f32 solved_tangent_impulse;
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_Constraint)
|
|
||||||
{
|
|
||||||
i64 last_touched_tick;
|
|
||||||
S_Key ent0;
|
|
||||||
S_Key ent1;
|
|
||||||
|
|
||||||
Vec2 static_center0;
|
|
||||||
Vec2 static_center1;
|
|
||||||
|
|
||||||
f32 inv_m0;
|
|
||||||
f32 inv_m1;
|
|
||||||
f32 inv_i0;
|
|
||||||
f32 inv_i1;
|
|
||||||
|
|
||||||
Vec2 normal;
|
|
||||||
f32 friction;
|
|
||||||
|
|
||||||
i32 points_count;
|
|
||||||
S_ContactPoint points[2];
|
|
||||||
};
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ World types
|
|
||||||
|
|
||||||
Struct(S_World)
|
|
||||||
{
|
|
||||||
u64 seed;
|
|
||||||
i64 tick;
|
|
||||||
i64 time_ns;
|
|
||||||
|
|
||||||
i64 ents_count;
|
|
||||||
S_Ent *first_ent;
|
|
||||||
S_Ent *last_ent;
|
|
||||||
|
|
||||||
i64 ent_bins_count;
|
|
||||||
S_EntBin *ent_bins;
|
|
||||||
|
|
||||||
u8 *tiles;
|
|
||||||
};
|
|
||||||
|
|
||||||
Enum(S_DeltaKind)
|
|
||||||
{
|
|
||||||
S_DeltaKind_Reset,
|
|
||||||
S_DeltaKind_RawEnt,
|
|
||||||
S_DeltaKind_RawTiles,
|
|
||||||
S_DeltaKind_Tile,
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_Delta)
|
|
||||||
{
|
|
||||||
S_DeltaKind kind;
|
|
||||||
|
|
||||||
S_Ent ent;
|
|
||||||
|
|
||||||
u8 *raw_tiles;
|
|
||||||
S_TileKind tile_kind;
|
|
||||||
Rng2I32 tile_range;
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_DeltaNode)
|
|
||||||
{
|
|
||||||
S_DeltaNode *next;
|
|
||||||
S_Delta delta;
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_Snapshot)
|
|
||||||
{
|
|
||||||
u64 seed;
|
|
||||||
i64 tick;
|
|
||||||
i64 time_ns;
|
|
||||||
|
|
||||||
i64 deltas_count;
|
|
||||||
S_DeltaNode *first_delta_node;
|
|
||||||
S_DeltaNode *last_delta_node;
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_SnapshotNode)
|
|
||||||
{
|
|
||||||
S_SnapshotNode *next;
|
|
||||||
S_Snapshot snapshot;
|
|
||||||
};
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Command types
|
|
||||||
|
|
||||||
Enum(S_CmdKind)
|
|
||||||
{
|
|
||||||
S_CmdKind_Nop,
|
|
||||||
S_CmdKind_Save,
|
|
||||||
S_CmdKind_Delta,
|
|
||||||
S_CmdKind_Control,
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_Cmd)
|
|
||||||
{
|
|
||||||
S_CmdKind kind;
|
|
||||||
|
|
||||||
// Delta
|
|
||||||
S_Delta delta;
|
|
||||||
|
|
||||||
// Control
|
|
||||||
S_Key target;
|
|
||||||
Vec2 move;
|
|
||||||
Vec2 look;
|
|
||||||
b32 fire_held;
|
|
||||||
i32 fire_presses;
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_CmdNode)
|
|
||||||
{
|
|
||||||
S_CmdNode *next;
|
|
||||||
S_Cmd cmd;
|
|
||||||
};
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Debug visualization types
|
|
||||||
|
|
||||||
Enum(S_DebugDrawKind)
|
|
||||||
{
|
|
||||||
S_DebugDrawKind_Point,
|
|
||||||
S_DebugDrawKind_Line,
|
|
||||||
S_DebugDrawKind_Rect,
|
|
||||||
S_DebugDrawKind_Shape,
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_DebugDrawDesc)
|
|
||||||
{
|
|
||||||
S_DebugDrawKind kind;
|
|
||||||
u32 srgb32;
|
|
||||||
union
|
|
||||||
{
|
|
||||||
struct
|
|
||||||
{
|
|
||||||
Vec2 p;
|
|
||||||
} point;
|
|
||||||
|
|
||||||
struct
|
|
||||||
{
|
|
||||||
Vec2 p0;
|
|
||||||
Vec2 p1;
|
|
||||||
} line;
|
|
||||||
|
|
||||||
Rng2 rect;
|
|
||||||
|
|
||||||
S_Shape shape;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
//~ State types
|
//~ State types
|
||||||
|
|
||||||
Struct(S_InputState)
|
|
||||||
{
|
|
||||||
Arena *arena;
|
|
||||||
S_CmdNode *first_cmd_node;
|
|
||||||
S_CmdNode *last_cmd_node;
|
|
||||||
u64 cmds_count;
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_OutputState)
|
|
||||||
{
|
|
||||||
Arena *arena;
|
|
||||||
|
|
||||||
S_SnapshotNode *first_snapshot_node;
|
|
||||||
S_SnapshotNode *last_snapshot_node;
|
|
||||||
u64 snapshots_count;
|
|
||||||
|
|
||||||
u64 debug_draw_descs_count;
|
|
||||||
S_DebugDrawDesc *debug_draw_descs;
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_Ctx)
|
Struct(S_Ctx)
|
||||||
{
|
{
|
||||||
Atomic32 shutdown;
|
Atomic32 shutdown;
|
||||||
Fence shutdown_fence;
|
Fence shutdown_fence;
|
||||||
|
|
||||||
b32 debug_draw_enabled;
|
|
||||||
Arena *debug_draw_descs_arena;
|
|
||||||
|
|
||||||
//- Sim input
|
|
||||||
TicketMutex input_back_tm;
|
|
||||||
i32 input_back_idx;
|
|
||||||
S_InputState input_states[2];
|
|
||||||
|
|
||||||
//- Sim output
|
|
||||||
TicketMutex output_back_tm;
|
|
||||||
i32 output_back_idx;
|
|
||||||
S_OutputState output_states[2];
|
|
||||||
};
|
|
||||||
|
|
||||||
Struct(S_ThreadLocalCtx)
|
|
||||||
{
|
|
||||||
b32 is_sim_tick_thread;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
extern S_Ctx S;
|
extern S_Ctx S;
|
||||||
extern ThreadLocal S_ThreadLocalCtx S_tl;
|
|
||||||
extern Readonly S_Ent S_NilEnt;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
//~ Bootstrap
|
//~ Bootstrap
|
||||||
@ -384,81 +15,6 @@ extern Readonly S_Ent S_NilEnt;
|
|||||||
void S_Bootstrap(void);
|
void S_Bootstrap(void);
|
||||||
void S_Shutdown(void);
|
void S_Shutdown(void);
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Nil helpers
|
|
||||||
|
|
||||||
b32 S_IsKeyNil(S_Key key);
|
|
||||||
b32 S_IsEntNil(S_Ent *ent);
|
|
||||||
b32 S_MatchKey(S_Key a, S_Key b);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Key helpers
|
|
||||||
|
|
||||||
S_Key S_RandKey(void);
|
|
||||||
|
|
||||||
#define S_FmtKey(key) FmtHandle((key).v)
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Tile helpers
|
|
||||||
|
|
||||||
String S_NameFromTileKind(S_TileKind kind);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Delta helpers
|
|
||||||
|
|
||||||
void S_UpdateWorldFromDelta(Arena *arena, S_World *world, S_Delta *delta);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Shape helpers
|
|
||||||
|
|
||||||
S_Shape S_ShapeFromDescEx(S_ShapeDesc desc);
|
|
||||||
#define S_ShapeFromDesc(...) S_ShapeFromDescEx((S_ShapeDesc) { __VA_ARGS__ })
|
|
||||||
|
|
||||||
S_Shape S_MulXformShape(Xform xf, S_Shape shape);
|
|
||||||
Rng2 S_BoundingBoxFromShape(S_Shape shape);
|
|
||||||
|
|
||||||
S_Shape S_LocalShapeFromEnt(S_Ent *ent);
|
|
||||||
S_Shape S_WorldShapeFromEnt(S_Ent *ent);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Collision
|
|
||||||
|
|
||||||
S_SupportPoint S_SupportPointFromShapeEx(S_Shape shape, Vec2 dir, i32 ignore_idx);
|
|
||||||
S_SupportPoint S_SupportPointFromShape(S_Shape shape, Vec2 dir);
|
|
||||||
S_MenkowskiPoint S_MenkowskiPointFromShapes(S_Shape shape0, S_Shape shape1, Vec2 dir);
|
|
||||||
S_ClippedLine S_ClipLineToLine(Vec2 a0, Vec2 b0, Vec2 a1, Vec2 b1, Vec2 normal);
|
|
||||||
Vec2 S_ClipPointToLine(Vec2 a, Vec2 b, Vec2 p, Vec2 normal);
|
|
||||||
|
|
||||||
S_CollisionResult S_CollisionResultFromShapes(S_Shape shape0, S_Shape shape1);
|
|
||||||
S_RaycastResult S_RaycastShape(S_Shape shape, Vec2 ray_start, Vec2 ray_dir);
|
|
||||||
|
|
||||||
Vec2 S_EdgePointFromShape(S_Shape shape, Vec2 dir);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Lookup helpers
|
|
||||||
|
|
||||||
S_Ent *S_EntFromKey(S_World *world, S_Key key);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Iteration helpers
|
|
||||||
|
|
||||||
S_Ent *S_FirstEnt(S_World *world);
|
|
||||||
S_Ent *S_NextEnt(S_Ent *e);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ List helpers
|
|
||||||
|
|
||||||
S_Ent *S_PushTempEnt(Arena *arena, S_EntList *list);
|
|
||||||
void S_SpawnEntsFromList(Arena *arena, S_World *world, S_EntList ents);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Debug draw
|
|
||||||
|
|
||||||
void S_DebugDrawPoint(Vec2 p, Vec4 srgb);
|
|
||||||
void S_DebugDrawLine(Vec2 p0, Vec2 p1, Vec4 srgb);
|
|
||||||
void S_DebugDrawRect(Rng2 rect, Vec4 srgb);
|
|
||||||
void S_DebugDrawShape(S_Shape shape, Vec4 srgb);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
//~ Sim tick
|
//~ Sim tick
|
||||||
|
|
||||||
|
|||||||
@ -1,27 +0,0 @@
|
|||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Tile helpers
|
|
||||||
|
|
||||||
i32 S_TileIdxFromTilePos(Vec2 p)
|
|
||||||
{
|
|
||||||
i32 x = ClampI32(FloorF32(p.x), 0, S_TilesPitch - 1);
|
|
||||||
i32 y = ClampI32(FloorF32(p.y), 0, S_TilesPitch - 1);
|
|
||||||
i32 result = x + (y * S_TilesPitch);
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
#if IsLanguageC
|
|
||||||
String S_TileNameFromKind(S_TileKind kind)
|
|
||||||
{
|
|
||||||
PERSIST Readonly String tile_names[S_TileKind_COUNT] = {
|
|
||||||
#define X(name, ...) [S_TileKind_##name] = CompLit(#name),
|
|
||||||
S_TilesXMacro(X)
|
|
||||||
#undef X
|
|
||||||
};
|
|
||||||
String result = Zi;
|
|
||||||
if (kind >= 0 && kind < countof(tile_names))
|
|
||||||
{
|
|
||||||
result = tile_names[kind];
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
@ -1,35 +0,0 @@
|
|||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Tile types
|
|
||||||
|
|
||||||
#define S_WorldPitch 64.0
|
|
||||||
|
|
||||||
#define S_TilesPerMeter 2.0
|
|
||||||
#define S_TilesPerSqMeter (V_TilesPerMeter * V_TilesPerMeter)
|
|
||||||
|
|
||||||
#define S_TilesPitch (S_WorldPitch * S_TilesPerMeter)
|
|
||||||
#define S_TilesCount (S_TilesPitch * S_TilesPitch)
|
|
||||||
|
|
||||||
#define S_TilesXMacro(X) \
|
|
||||||
X(Empty) \
|
|
||||||
X(Tile) \
|
|
||||||
X(Carpet) \
|
|
||||||
X(Wall) \
|
|
||||||
/* -------------------- */
|
|
||||||
|
|
||||||
//- Tiles kinds enum
|
|
||||||
Enum(S_TileKind)
|
|
||||||
{
|
|
||||||
#define X(name, ...) S_TileKind_##name,
|
|
||||||
S_TilesXMacro(X)
|
|
||||||
#undef X
|
|
||||||
S_TileKind_COUNT
|
|
||||||
};
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Tile helpers
|
|
||||||
|
|
||||||
i32 S_TileIdxFromTilePos(Vec2 p);
|
|
||||||
|
|
||||||
#if IsLanguageC
|
|
||||||
String S_TileNameFromKind(S_TileKind kind);
|
|
||||||
#endif
|
|
||||||
@ -1,30 +0,0 @@
|
|||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Transcode types
|
|
||||||
|
|
||||||
Enum(S_Tv)
|
|
||||||
{
|
|
||||||
S_Tv_None = 0,
|
|
||||||
S_Tv_Initial = 1,
|
|
||||||
|
|
||||||
S_Tv_COUNT
|
|
||||||
};
|
|
||||||
|
|
||||||
#define S_Tv_Latest (S_Tv_COUNT - 1)
|
|
||||||
|
|
||||||
Struct(S_UnpackedWorld)
|
|
||||||
{
|
|
||||||
S_Tv version;
|
|
||||||
|
|
||||||
u64 seed;
|
|
||||||
i64 tick;
|
|
||||||
i64 time_ns;
|
|
||||||
|
|
||||||
S_EntList ents;
|
|
||||||
u8 *tiles;
|
|
||||||
};
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
|
||||||
//~ Transcode
|
|
||||||
|
|
||||||
String S_PackWorld(Arena *arena, S_World *src_world);
|
|
||||||
S_UnpackedWorld S_UnpackWorld(Arena *arena, String packed);
|
|
||||||
@ -1,19 +1,13 @@
|
|||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
//~ Transcode
|
//~ Transcode
|
||||||
|
|
||||||
|
String P_PackWorld(Arena *arena, P_World *src_world)
|
||||||
|
|
||||||
// FIXME: Header
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
String S_PackWorld(Arena *arena, S_World *src_world)
|
|
||||||
{
|
{
|
||||||
String result = Zi;
|
String result = Zi;
|
||||||
result.text = ArenaNext(arena, u8);
|
result.text = ArenaNext(arena, u8);
|
||||||
TempArena scratch = BeginScratch(arena);
|
TempArena scratch = BeginScratch(arena);
|
||||||
|
|
||||||
result.len += StringF(arena, "version: %F\n", FmtUint(S_Tv_Latest)).len;
|
result.len += StringF(arena, "version: %F\n", FmtUint(P_Tv_Latest)).len;
|
||||||
|
|
||||||
result.len += StringF(arena, "\n").len;
|
result.len += StringF(arena, "\n").len;
|
||||||
result.len += StringF(arena, "seed: 0x%F\n", FmtHex(src_world->seed)).len;
|
result.len += StringF(arena, "seed: 0x%F\n", FmtHex(src_world->seed)).len;
|
||||||
@ -24,7 +18,7 @@ String S_PackWorld(Arena *arena, S_World *src_world)
|
|||||||
// FIXME: Precision
|
// FIXME: Precision
|
||||||
result.len += PushString(arena, Lit("\nentities:\n")).len;
|
result.len += PushString(arena, Lit("\nentities:\n")).len;
|
||||||
result.len += PushString(arena, Lit("{\n")).len;
|
result.len += PushString(arena, Lit("{\n")).len;
|
||||||
for (S_Ent *ent = S_FirstEnt(src_world); ent->valid; ent = S_NextEnt(ent))
|
for (P_Ent *ent = P_FirstEnt(src_world); ent->valid; ent = P_NextEnt(ent))
|
||||||
{
|
{
|
||||||
// TODO: Pack bullets
|
// TODO: Pack bullets
|
||||||
if (!ent->is_bullet)
|
if (!ent->is_bullet)
|
||||||
@ -60,7 +54,7 @@ String S_PackWorld(Arena *arena, S_World *src_world)
|
|||||||
result.len += PushString(arena, Lit("\ntiles:\n")).len;
|
result.len += PushString(arena, Lit("\ntiles:\n")).len;
|
||||||
result.len += PushString(arena, Lit("{\n")).len;
|
result.len += PushString(arena, Lit("{\n")).len;
|
||||||
{
|
{
|
||||||
String tiles_str = Base64FromString(scratch.arena, STRING(S_TilesCount, src_world->tiles));
|
String tiles_str = Base64FromString(scratch.arena, STRING(P_TilesCount, src_world->tiles));
|
||||||
u64 tile_chars_per_line = 128;
|
u64 tile_chars_per_line = 128;
|
||||||
u64 tile_char_pos = 0;
|
u64 tile_char_pos = 0;
|
||||||
while (tile_char_pos < tiles_str.len)
|
while (tile_char_pos < tiles_str.len)
|
||||||
@ -80,15 +74,15 @@ String S_PackWorld(Arena *arena, S_World *src_world)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
S_UnpackedWorld S_UnpackWorld(Arena *arena, String packed)
|
P_UnpackedWorld P_UnpackWorld(Arena *arena, String packed)
|
||||||
{
|
{
|
||||||
S_UnpackedWorld result = Zi;
|
P_UnpackedWorld result = Zi;
|
||||||
TempArena scratch = BeginScratch(arena);
|
TempArena scratch = BeginScratch(arena);
|
||||||
|
|
||||||
CR_Item *root = CR_ItemFromString(scratch.arena, packed);
|
CR_Item *root = CR_ItemFromString(scratch.arena, packed);
|
||||||
|
|
||||||
// Unpack version
|
// Unpack version
|
||||||
S_Tv version = 0;
|
P_Tv version = 0;
|
||||||
for (CR_Item *root_item = root->first; root_item; root_item = root_item->next)
|
for (CR_Item *root_item = root->first; root_item; root_item = root_item->next)
|
||||||
{
|
{
|
||||||
if (MatchString(root_item->name, Lit("version")))
|
if (MatchString(root_item->name, Lit("version")))
|
||||||
@ -119,8 +113,8 @@ S_UnpackedWorld S_UnpackWorld(Arena *arena, String packed)
|
|||||||
{
|
{
|
||||||
for (CR_Item *ent_item = top_item->first; ent_item; ent_item = ent_item->next)
|
for (CR_Item *ent_item = top_item->first; ent_item; ent_item = ent_item->next)
|
||||||
{
|
{
|
||||||
S_Ent *ent = S_PushTempEnt(arena, &result.ents);
|
P_Ent *ent = P_PushTempEnt(arena, &result.ents);
|
||||||
ent->key = (S_Key) { .v = CR_IntFromString(ent_item->name) };
|
ent->key = (P_Key) { .v = CR_IntFromString(ent_item->name) };
|
||||||
for (CR_Item *attr = ent_item->first; attr; attr = attr->next)
|
for (CR_Item *attr = ent_item->first; attr; attr = attr->next)
|
||||||
{
|
{
|
||||||
if (MatchString(attr->name, Lit("props")))
|
if (MatchString(attr->name, Lit("props")))
|
||||||
@ -175,7 +169,7 @@ S_UnpackedWorld S_UnpackWorld(Arena *arena, String packed)
|
|||||||
tiles_base64.len += PushString(scratch.arena, tile_item->value).len;
|
tiles_base64.len += PushString(scratch.arena, tile_item->value).len;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (StringLenFromBase64Len(tiles_base64.len) == S_TilesCount)
|
if (StringLenFromBase64Len(tiles_base64.len) == P_TilesCount)
|
||||||
{
|
{
|
||||||
result.tiles = StringFromBase64(arena, tiles_base64).text;
|
result.tiles = StringFromBase64(arena, tiles_base64).text;
|
||||||
}
|
}
|
||||||
@ -183,7 +177,7 @@ S_UnpackedWorld S_UnpackWorld(Arena *arena, String packed)
|
|||||||
|
|
||||||
if (!result.tiles)
|
if (!result.tiles)
|
||||||
{
|
{
|
||||||
result.tiles = PushStructs(arena, u8, S_TilesCount);
|
result.tiles = PushStructs(arena, u8, P_TilesCount);
|
||||||
}
|
}
|
||||||
|
|
||||||
EndScratch(scratch);
|
EndScratch(scratch);
|
||||||
30
src/pp/pp_transcode.h
Normal file
30
src/pp/pp_transcode.h
Normal file
@ -0,0 +1,30 @@
|
|||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Transcode types
|
||||||
|
|
||||||
|
Enum(P_Tv)
|
||||||
|
{
|
||||||
|
P_Tv_None = 0,
|
||||||
|
P_Tv_Initial = 1,
|
||||||
|
|
||||||
|
P_Tv_COUNT
|
||||||
|
};
|
||||||
|
|
||||||
|
#define P_Tv_Latest (P_Tv_COUNT - 1)
|
||||||
|
|
||||||
|
Struct(P_UnpackedWorld)
|
||||||
|
{
|
||||||
|
P_Tv version;
|
||||||
|
|
||||||
|
u64 seed;
|
||||||
|
i64 tick;
|
||||||
|
i64 time_ns;
|
||||||
|
|
||||||
|
P_EntList ents;
|
||||||
|
u8 *tiles;
|
||||||
|
};
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//~ Transcode
|
||||||
|
|
||||||
|
String P_PackWorld(Arena *arena, P_World *src_world);
|
||||||
|
P_UnpackedWorld P_UnpackWorld(Arena *arena, String packed);
|
||||||
@ -4,7 +4,6 @@
|
|||||||
//- Dependencies
|
//- Dependencies
|
||||||
|
|
||||||
@Dep pp
|
@Dep pp
|
||||||
@Dep pp_sim
|
|
||||||
@Dep sprite
|
@Dep sprite
|
||||||
@Dep gpu
|
@Dep gpu
|
||||||
@Dep glyph_cache
|
@Dep glyph_cache
|
||||||
|
|||||||
@ -41,10 +41,10 @@ V_Cmd *V_PushVisCmd(String name)
|
|||||||
return cmd;
|
return cmd;
|
||||||
}
|
}
|
||||||
|
|
||||||
S_Cmd *V_PushSimCmd(S_CmdKind kind)
|
P_Cmd *V_PushSimCmd(P_CmdKind kind)
|
||||||
{
|
{
|
||||||
V_Frame *frame = V_CurrentFrame();
|
V_Frame *frame = V_CurrentFrame();
|
||||||
S_CmdNode *n = PushStruct(frame->arena, S_CmdNode);
|
P_CmdNode *n = PushStruct(frame->arena, P_CmdNode);
|
||||||
n->cmd.kind = kind;
|
n->cmd.kind = kind;
|
||||||
SllQueuePush(frame->first_sim_cmd_node, frame->last_sim_cmd_node, n);
|
SllQueuePush(frame->first_sim_cmd_node, frame->last_sim_cmd_node, n);
|
||||||
++frame->sim_cmds_count;
|
++frame->sim_cmds_count;
|
||||||
@ -198,7 +198,7 @@ void V_DrawPoly(Vec2Array points, Vec4 srgb, V_DrawFlag flags)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void V_DrawShape(S_Shape shape, Vec4 srgb, i32 detail, V_DrawFlag flags)
|
void V_DrawShape(P_Shape shape, Vec4 srgb, i32 detail, V_DrawFlag flags)
|
||||||
{
|
{
|
||||||
if (shape.radius == 0)
|
if (shape.radius == 0)
|
||||||
{
|
{
|
||||||
@ -218,7 +218,7 @@ void V_DrawShape(S_Shape shape, Vec4 srgb, i32 detail, V_DrawFlag flags)
|
|||||||
{
|
{
|
||||||
f32 rad = ((f32)i / (f32)detail) * Tau;
|
f32 rad = ((f32)i / (f32)detail) * Tau;
|
||||||
Vec2 dir = Vec2FromAngle(rad);
|
Vec2 dir = Vec2FromAngle(rad);
|
||||||
Vec2 sp = S_SupportPointFromShape(shape, dir).p;
|
Vec2 sp = P_SupportPointFromShape(shape, dir).p;
|
||||||
draw_points.points[i] = sp;
|
draw_points.points[i] = sp;
|
||||||
}
|
}
|
||||||
V_DrawPoly(draw_points, srgb, flags);
|
V_DrawPoly(draw_points, srgb, flags);
|
||||||
@ -255,7 +255,7 @@ void V_DrawRect(Rng2 rect, Vec4 srgb, V_DrawFlag flags)
|
|||||||
|
|
||||||
void V_DrawPoint(Vec2 p, Vec4 srgb)
|
void V_DrawPoint(Vec2 p, Vec4 srgb)
|
||||||
{
|
{
|
||||||
S_Shape ui_shape = S_ShapeFromDesc(
|
P_Shape ui_shape = P_ShapeFromDesc(
|
||||||
.count = 1,
|
.count = 1,
|
||||||
.points = { p },
|
.points = { p },
|
||||||
.radius = 5
|
.radius = 5
|
||||||
@ -326,7 +326,7 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
Arena *perm = PermArena();
|
Arena *perm = PermArena();
|
||||||
G_ArenaHandle gpu_perm = G_PermArena();
|
G_ArenaHandle gpu_perm = G_PermArena();
|
||||||
|
|
||||||
const i32 world_pitch = S_WorldPitch;
|
const i32 world_pitch = P_WorldPitch;
|
||||||
const f32 zoom_rate = 1.50;
|
const f32 zoom_rate = 1.50;
|
||||||
const f32 min_zoom = 0.03;
|
const f32 min_zoom = 0.03;
|
||||||
const f32 max_zoom = 15.0;
|
const f32 max_zoom = 15.0;
|
||||||
@ -336,17 +336,17 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
//- Init vis state
|
//- Init vis state
|
||||||
|
|
||||||
Arena *sim_debug_arena = AcquireArena(Gibi(64));
|
Arena *sim_debug_arena = AcquireArena(Gibi(64));
|
||||||
u64 sim_debug_draw_descs_count = 0;
|
P_DebugDrawNode *first_sim_debug_draw_node = 0;
|
||||||
S_DebugDrawDesc *sim_debug_draw_descs = 0;
|
P_DebugDrawNode *last_sim_debug_draw_node = 0;
|
||||||
|
|
||||||
Arena *world_arena = AcquireArena(Gibi(64));
|
Arena *world_arena = AcquireArena(Gibi(64));
|
||||||
S_World *world = PushStruct(world_arena, S_World);
|
P_World *world = PushStruct(world_arena, P_World);
|
||||||
world->ent_bins_count = Kibi(16);
|
world->ent_bins_count = Kibi(16);
|
||||||
world->ent_bins = PushStructs(world_arena, S_EntBin, world->ent_bins_count);
|
world->ent_bins = PushStructs(world_arena, P_EntBin, world->ent_bins_count);
|
||||||
world->tiles = PushStructs(world_arena, u8, S_TilesCount);
|
world->tiles = PushStructs(world_arena, u8, P_TilesCount);
|
||||||
|
|
||||||
Vec2I32 tiles_dims = VEC2I32(S_TilesPitch, S_TilesPitch);
|
Vec2I32 tiles_dims = VEC2I32(P_TilesPitch, P_TilesPitch);
|
||||||
Vec2I32 cells_dims = VEC2I32(V_CellsPerMeter * S_WorldPitch, V_CellsPerMeter * S_WorldPitch);
|
Vec2I32 cells_dims = VEC2I32(V_CellsPerMeter * P_WorldPitch, V_CellsPerMeter * P_WorldPitch);
|
||||||
|
|
||||||
// Init gpu state
|
// Init gpu state
|
||||||
G_ResourceHandle gpu_state = Zi;
|
G_ResourceHandle gpu_state = Zi;
|
||||||
@ -489,6 +489,7 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
while (!shutdown)
|
while (!shutdown)
|
||||||
{
|
{
|
||||||
shutdown = Atomic32Fetch(&V.shutdown);
|
shutdown = Atomic32Fetch(&V.shutdown);
|
||||||
|
P_tl.debug_draw_enabled = 1;
|
||||||
|
|
||||||
//////////////////////////////
|
//////////////////////////////
|
||||||
//- Begin frame
|
//- Begin frame
|
||||||
@ -532,9 +533,9 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
frame->dt = SecondsFromNs(frame->dt_ns);
|
frame->dt = SecondsFromNs(frame->dt_ns);
|
||||||
frame->rand = last_frame->rand;
|
frame->rand = last_frame->rand;
|
||||||
|
|
||||||
if (S_IsKeyNil(V.player_key))
|
if (P_IsKeyNil(V.player_key))
|
||||||
{
|
{
|
||||||
V.player_key = S_RandKey();
|
V.player_key = P_RandKey();
|
||||||
}
|
}
|
||||||
|
|
||||||
//////////////////////////////
|
//////////////////////////////
|
||||||
@ -633,17 +634,17 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
//////////////////////////////
|
//////////////////////////////
|
||||||
//- Pop sim output
|
//- Pop sim output
|
||||||
|
|
||||||
S_OutputState *sim_output = 0;
|
P_OutputState *sim_output = 0;
|
||||||
LockTicketMutex(&S.output_back_tm);
|
LockTicketMutex(&P.sim_output_back_tm);
|
||||||
{
|
{
|
||||||
sim_output = &S.output_states[S.output_back_idx];
|
sim_output = &P.sim_output_states[P.sim_output_back_idx];
|
||||||
++S.output_back_idx;
|
++P.sim_output_back_idx;
|
||||||
if (S.output_back_idx >= countof(S.output_states))
|
if (P.sim_output_back_idx >= countof(P.sim_output_states))
|
||||||
{
|
{
|
||||||
S.output_back_idx = 0;
|
P.sim_output_back_idx = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
UnlockTicketMutex(&S.output_back_tm);
|
UnlockTicketMutex(&P.sim_output_back_tm);
|
||||||
|
|
||||||
//////////////////////////////
|
//////////////////////////////
|
||||||
//- Apply sim snapshots
|
//- Apply sim snapshots
|
||||||
@ -653,59 +654,45 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
b32 received_unseen_tick = 0;
|
b32 received_unseen_tick = 0;
|
||||||
b32 tiles_dirty = 0;
|
b32 tiles_dirty = 0;
|
||||||
b32 should_clear_particles = 0;
|
b32 should_clear_particles = 0;
|
||||||
for (S_SnapshotNode *n = sim_output->first_snapshot_node; n; n = n->next)
|
for (P_SnapshotNode *n = sim_output->first_snapshot_node; n; n = n->next)
|
||||||
{
|
{
|
||||||
S_Snapshot *snapshot = &n->snapshot;
|
P_Snapshot *snapshot = &n->snapshot;
|
||||||
if (snapshot->tick > world->tick)
|
if (snapshot->tick > world->tick)
|
||||||
{
|
{
|
||||||
world->seed = snapshot->seed;
|
world->seed = snapshot->seed;
|
||||||
world->tick = snapshot->tick;
|
world->tick = snapshot->tick;
|
||||||
world->time_ns = snapshot->time_ns;
|
world->time_ns = snapshot->time_ns;
|
||||||
for (S_DeltaNode *dn = snapshot->first_delta_node; dn; dn = dn->next)
|
for (P_DeltaNode *dn = snapshot->first_delta_node; dn; dn = dn->next)
|
||||||
{
|
{
|
||||||
S_Delta *delta = &dn->delta;
|
P_Delta *delta = &dn->delta;
|
||||||
if (delta->kind == S_DeltaKind_Reset)
|
if (delta->kind == P_DeltaKind_Reset)
|
||||||
{
|
{
|
||||||
tiles_dirty = 1;
|
tiles_dirty = 1;
|
||||||
should_clear_particles = 1;
|
should_clear_particles = 1;
|
||||||
}
|
}
|
||||||
if (delta->kind == S_DeltaKind_RawTiles || delta->kind == S_DeltaKind_Tile)
|
if (delta->kind == P_DeltaKind_RawTiles || delta->kind == P_DeltaKind_Tile)
|
||||||
{
|
{
|
||||||
tiles_dirty = 1;
|
tiles_dirty = 1;
|
||||||
}
|
}
|
||||||
S_UpdateWorldFromDelta(world_arena, world, delta);
|
P_UpdateWorldFromDelta(world_arena, world, delta);
|
||||||
}
|
}
|
||||||
received_unseen_tick = 1;
|
received_unseen_tick = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
//////////////////////////////
|
|
||||||
//- Copy sim debug info
|
|
||||||
|
|
||||||
if (received_unseen_tick)
|
|
||||||
{
|
|
||||||
ResetArena(sim_debug_arena);
|
|
||||||
|
|
||||||
// Copy sim debug info
|
|
||||||
sim_debug_draw_descs_count = sim_output->debug_draw_descs_count;
|
|
||||||
sim_debug_draw_descs = PushStructsNoZero(sim_debug_arena, S_DebugDrawDesc, sim_debug_draw_descs_count);
|
|
||||||
CopyStructs(sim_debug_draw_descs, sim_output->debug_draw_descs, sim_debug_draw_descs_count);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// //////////////////////////////
|
// //////////////////////////////
|
||||||
// //- Update tiles from sim
|
// //- Update tiles from sim
|
||||||
|
|
||||||
// {
|
// {
|
||||||
// for (S_SnapshotNode *n = sim_output->first_snapshot_node; n; n = n->next)
|
// for (P_SnapshotNode *n = sim_output->first_snapshot_node; n; n = n->next)
|
||||||
// {
|
// {
|
||||||
// S_Snapshot *snapshot = &n->snapshot;
|
// P_Snapshot *snapshot = &n->snapshot;
|
||||||
// if (snapshot->tick > world->tick)
|
// if (snapshot->tick > world->tick)
|
||||||
// {
|
// {
|
||||||
// for (u64 placement_idx = 0; placement_idx < snapshot->tile_placements_count; ++placement_idx)
|
// for (u64 placement_idx = 0; placement_idx < snapshot->tile_placements_count; ++placement_idx)
|
||||||
// {
|
// {
|
||||||
// S_TilePlacement placement = snapshot->tile_placements[placement_idx];
|
// P_TilePlacement placement = snapshot->tile_placements[placement_idx];
|
||||||
// Rng2I32 dirty_rect = S_UpdateTilesInPlaceFromPlacement(tiles, placement);
|
// Rng2I32 dirty_rect = P_UpdateTilesInPlaceFromPlacement(tiles, placement);
|
||||||
// G_CopyCpuToTexture(
|
// G_CopyCpuToTexture(
|
||||||
// frame->cl,
|
// frame->cl,
|
||||||
// gpu_tiles, VEC3I32(dirty_rect.p0.x, dirty_rect.p0.y, 0),
|
// gpu_tiles, VEC3I32(dirty_rect.p0.x, dirty_rect.p0.y, 0),
|
||||||
@ -723,12 +710,12 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
// if (sim_output->last_snapshot_node && sim_output->last_snapshot_node->snapshot.tick > world->tick)
|
// if (sim_output->last_snapshot_node && sim_output->last_snapshot_node->snapshot.tick > world->tick)
|
||||||
// {
|
// {
|
||||||
// ResetArena(world_arena);
|
// ResetArena(world_arena);
|
||||||
// world = S_WorldFromSnapshot(world_arena, &sim_output->last_snapshot_node->snapshot);
|
// world = P_WorldFromSnapshot(world_arena, &sim_output->last_snapshot_node->snapshot);
|
||||||
// V.lookup = S_LookupFromWorld(world_arena, world);
|
// V.lookup = P_LookupFromWorld(world_arena, world);
|
||||||
|
|
||||||
// // Copy sim debug info
|
// // Copy sim debug info
|
||||||
// sim_debug_draw_descs_count = sim_output->debug_draw_descs_count;
|
// sim_debug_draw_descs_count = sim_output->debug_draw_descs_count;
|
||||||
// sim_debug_draw_descs = PushStructsNoZero(world_arena, S_DebugDrawDesc, sim_debug_draw_descs_count);
|
// sim_debug_draw_descs = PushStructsNoZero(world_arena, P_DebugDrawDesc, sim_debug_draw_descs_count);
|
||||||
// CopyStructs(sim_debug_draw_descs, sim_output->debug_draw_descs, sim_debug_draw_descs_count);
|
// CopyStructs(sim_debug_draw_descs, sim_output->debug_draw_descs, sim_debug_draw_descs_count);
|
||||||
// }
|
// }
|
||||||
|
|
||||||
@ -860,8 +847,8 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
Vec2 look_ratio = Zi;
|
Vec2 look_ratio = Zi;
|
||||||
look_ratio.y = 0.25;
|
look_ratio.y = 0.25;
|
||||||
look_ratio.x = look_ratio.y / (16.0 / 9.0);
|
look_ratio.x = look_ratio.y / (16.0 / 9.0);
|
||||||
S_Ent *player = S_EntFromKey(world, V.player_key);
|
P_Ent *player = P_EntFromKey(world, V.player_key);
|
||||||
target_camera_pos = S_WorldShapeFromEnt(player).centroid;
|
target_camera_pos = P_WorldShapeFromEnt(player).centroid;
|
||||||
target_camera_pos = AddVec2(target_camera_pos, MulVec2Vec2(player->look, look_ratio));
|
target_camera_pos = AddVec2(target_camera_pos, MulVec2Vec2(player->look, look_ratio));
|
||||||
target_camera_zoom = 1;
|
target_camera_zoom = 1;
|
||||||
}
|
}
|
||||||
@ -929,7 +916,7 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
frame->xf.cell_to_world = XformIdentity;
|
frame->xf.cell_to_world = XformIdentity;
|
||||||
{
|
{
|
||||||
frame->xf.world_to_cell = ScaleXform(frame->xf.world_to_cell, VEC2(V_CellsPerMeter, V_CellsPerMeter));
|
frame->xf.world_to_cell = ScaleXform(frame->xf.world_to_cell, VEC2(V_CellsPerMeter, V_CellsPerMeter));
|
||||||
frame->xf.world_to_cell = TranslateXform(frame->xf.world_to_cell, VEC2((S_WorldPitch / 2.0), (S_WorldPitch / 2.0)));
|
frame->xf.world_to_cell = TranslateXform(frame->xf.world_to_cell, VEC2((P_WorldPitch / 2.0), (P_WorldPitch / 2.0)));
|
||||||
frame->xf.cell_to_world = InvertXform(frame->xf.world_to_cell);
|
frame->xf.cell_to_world = InvertXform(frame->xf.world_to_cell);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -938,8 +925,8 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
frame->xf.world_to_tile = XformIdentity;
|
frame->xf.world_to_tile = XformIdentity;
|
||||||
frame->xf.tile_to_world = XformIdentity;
|
frame->xf.tile_to_world = XformIdentity;
|
||||||
{
|
{
|
||||||
frame->xf.world_to_tile = ScaleXform(frame->xf.world_to_tile, VEC2(S_TilesPerMeter, S_TilesPerMeter));
|
frame->xf.world_to_tile = ScaleXform(frame->xf.world_to_tile, VEC2(P_TilesPerMeter, P_TilesPerMeter));
|
||||||
frame->xf.world_to_tile = TranslateXform(frame->xf.world_to_tile, VEC2((S_WorldPitch / 2.0), (S_WorldPitch / 2.0)));
|
frame->xf.world_to_tile = TranslateXform(frame->xf.world_to_tile, VEC2((P_WorldPitch / 2.0), (P_WorldPitch / 2.0)));
|
||||||
frame->xf.tile_to_world = InvertXform(frame->xf.world_to_tile);
|
frame->xf.tile_to_world = InvertXform(frame->xf.world_to_tile);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -964,12 +951,12 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
if (m1_held)
|
if (m1_held)
|
||||||
{
|
{
|
||||||
frame->is_selecting = 1;
|
frame->is_selecting = 1;
|
||||||
// frame->equipped_tile = S_TileKind_Floor;
|
// frame->equipped_tile = P_TileKind_Floor;
|
||||||
}
|
}
|
||||||
else if (m2_held)
|
else if (m2_held)
|
||||||
{
|
{
|
||||||
frame->is_selecting = 1;
|
frame->is_selecting = 1;
|
||||||
// frame->equipped_tile = S_TileKind_Empty;
|
// frame->equipped_tile = P_TileKind_Empty;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (frame->is_selecting && last_frame->is_selecting)
|
if (frame->is_selecting && last_frame->is_selecting)
|
||||||
@ -1003,8 +990,8 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
tile_range.p0 = Vec2I32FromVec(FloorVec2(MulXformV2(frame->xf.world_to_tile, last_frame->world_selection.p0)));
|
tile_range.p0 = Vec2I32FromVec(FloorVec2(MulXformV2(frame->xf.world_to_tile, last_frame->world_selection.p0)));
|
||||||
tile_range.p1 = Vec2I32FromVec(CeilVec2(MulXformV2(frame->xf.world_to_tile, last_frame->world_selection.p1)));
|
tile_range.p1 = Vec2I32FromVec(CeilVec2(MulXformV2(frame->xf.world_to_tile, last_frame->world_selection.p1)));
|
||||||
|
|
||||||
S_Cmd *cmd = V_PushSimCmd(S_CmdKind_Delta);
|
P_Cmd *cmd = V_PushSimCmd(P_CmdKind_Delta);
|
||||||
cmd->delta.kind = S_DeltaKind_Tile;
|
cmd->delta.kind = P_DeltaKind_Tile;
|
||||||
cmd->delta.tile_kind = last_frame->equipped_tile;
|
cmd->delta.tile_kind = last_frame->equipped_tile;
|
||||||
cmd->delta.tile_range = tile_range;
|
cmd->delta.tile_range = tile_range;
|
||||||
}
|
}
|
||||||
@ -1013,15 +1000,15 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
//////////////////////////////
|
//////////////////////////////
|
||||||
//- Query entities
|
//- Query entities
|
||||||
|
|
||||||
S_Ent *player = S_EntFromKey(world, V.player_key);
|
P_Ent *player = P_EntFromKey(world, V.player_key);
|
||||||
S_Ent *hovered_ent = &S_NilEnt;
|
P_Ent *hovered_ent = &P_NilEnt;
|
||||||
{
|
{
|
||||||
// TODO: Real world query
|
// TODO: Real world query
|
||||||
S_Shape cursor_shape = S_ShapeFromDesc(.count = 1, .points = { frame->world_cursor });
|
P_Shape cursor_shape = P_ShapeFromDesc(.count = 1, .points = { frame->world_cursor });
|
||||||
for (S_Ent *ent = S_FirstEnt(world); ent->valid; ent = S_NextEnt(ent))
|
for (P_Ent *ent = P_FirstEnt(world); ent->valid; ent = P_NextEnt(ent))
|
||||||
{
|
{
|
||||||
S_Shape ent_shape = S_WorldShapeFromEnt(ent);
|
P_Shape ent_shape = P_WorldShapeFromEnt(ent);
|
||||||
b32 is_hovered = S_CollisionResultFromShapes(ent_shape, cursor_shape).collision_points_count > 0;
|
b32 is_hovered = P_CollisionResultFromShapes(ent_shape, cursor_shape).collision_points_count > 0;
|
||||||
if (is_hovered)
|
if (is_hovered)
|
||||||
{
|
{
|
||||||
hovered_ent = ent;
|
hovered_ent = ent;
|
||||||
@ -1551,9 +1538,9 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
UI_Push(Tag, window->key.v);
|
UI_Push(Tag, window->key.v);
|
||||||
if (window->is_tile_window)
|
if (window->is_tile_window)
|
||||||
{
|
{
|
||||||
for (S_TileKind tile_kind = 0; tile_kind < S_TileKind_COUNT; ++tile_kind)
|
for (P_TileKind tile_kind = 0; tile_kind < P_TileKind_COUNT; ++tile_kind)
|
||||||
{
|
{
|
||||||
String name = S_NameFromTileKind(tile_kind);
|
String name = P_NameFromTileKind(tile_kind);
|
||||||
UI_Key key = UI_KeyF("Tile %F", FmtString(name));
|
UI_Key key = UI_KeyF("Tile %F", FmtString(name));
|
||||||
UI_BoxReport rep = UI_ReportsFromKey(key).draw;
|
UI_BoxReport rep = UI_ReportsFromKey(key).draw;
|
||||||
|
|
||||||
@ -2232,13 +2219,13 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
UI_BuildSpacer(UI_PIX(padding, 1), Axis_Y);
|
UI_BuildSpacer(UI_PIX(padding, 1), Axis_Y);
|
||||||
Vec2 tile_pos = MulXformV2(frame->xf.world_to_tile, frame->world_cursor);
|
Vec2 tile_pos = MulXformV2(frame->xf.world_to_tile, frame->world_cursor);
|
||||||
Vec2 cell_pos = MulXformV2(frame->xf.world_to_cell, frame->world_cursor);
|
Vec2 cell_pos = MulXformV2(frame->xf.world_to_cell, frame->world_cursor);
|
||||||
i32 tile_idx = S_TileIdxFromTilePos(tile_pos);
|
i32 tile_idx = P_TileIdxFromTilePos(tile_pos);
|
||||||
UI_BuildLabelF("Camera pos: %F", FmtFloat2(frame->camera_pos));
|
UI_BuildLabelF("Camera pos: %F", FmtFloat2(frame->camera_pos));
|
||||||
UI_BuildLabelF("Cursor world pos: %F", FmtFloat2(frame->world_cursor));
|
UI_BuildLabelF("Cursor world pos: %F", FmtFloat2(frame->world_cursor));
|
||||||
UI_BuildLabelF("Cursor tile pos: %F", FmtFloat2(tile_pos));
|
UI_BuildLabelF("Cursor tile pos: %F", FmtFloat2(tile_pos));
|
||||||
UI_BuildLabelF("Cursor tile idx: %F", FmtSint(tile_idx));
|
UI_BuildLabelF("Cursor tile idx: %F", FmtSint(tile_idx));
|
||||||
UI_BuildLabelF("Cursor cell pos: %F", FmtFloat2(cell_pos));
|
UI_BuildLabelF("Cursor cell pos: %F", FmtFloat2(cell_pos));
|
||||||
UI_BuildLabelF("Hovered ent: %F", S_FmtKey(hovered_ent->key));
|
UI_BuildLabelF("Hovered ent: %F", P_FmtKey(hovered_ent->key));
|
||||||
}
|
}
|
||||||
UI_BuildSpacer(UI_PIX(padding, 1), Axis_Y);
|
UI_BuildSpacer(UI_PIX(padding, 1), Axis_Y);
|
||||||
{
|
{
|
||||||
@ -2511,8 +2498,8 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
Vec2 player_pos = VEC2(5, 0);
|
Vec2 player_pos = VEC2(5, 0);
|
||||||
if (kind == V_CmdKind_reset_world)
|
if (kind == V_CmdKind_reset_world)
|
||||||
{
|
{
|
||||||
S_Cmd *cmd = V_PushSimCmd(S_CmdKind_Delta);
|
P_Cmd *cmd = V_PushSimCmd(P_CmdKind_Delta);
|
||||||
cmd->delta.kind = S_DeltaKind_Reset;
|
cmd->delta.kind = P_DeltaKind_Reset;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -2520,10 +2507,10 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
}
|
}
|
||||||
// Spawn player
|
// Spawn player
|
||||||
{
|
{
|
||||||
S_Cmd *cmd = V_PushSimCmd(S_CmdKind_Delta);
|
P_Cmd *cmd = V_PushSimCmd(P_CmdKind_Delta);
|
||||||
cmd->delta.kind = S_DeltaKind_RawEnt;
|
cmd->delta.kind = P_DeltaKind_RawEnt;
|
||||||
S_Ent *ent = &cmd->delta.ent;
|
P_Ent *ent = &cmd->delta.ent;
|
||||||
*ent = S_NilEnt;
|
*ent = P_NilEnt;
|
||||||
ent->key = V.player_key;
|
ent->key = V.player_key;
|
||||||
ent->xf = XformFromPos(player_pos);
|
ent->xf = XformFromPos(player_pos);
|
||||||
ent->is_player = 1;
|
ent->is_player = 1;
|
||||||
@ -2534,11 +2521,11 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
|
|
||||||
case V_CmdKind_spawn_dummy:
|
case V_CmdKind_spawn_dummy:
|
||||||
{
|
{
|
||||||
S_Cmd *cmd = V_PushSimCmd(S_CmdKind_Delta);
|
P_Cmd *cmd = V_PushSimCmd(P_CmdKind_Delta);
|
||||||
cmd->delta.kind = S_DeltaKind_RawEnt;
|
cmd->delta.kind = P_DeltaKind_RawEnt;
|
||||||
S_Ent *ent = &cmd->delta.ent;
|
P_Ent *ent = &cmd->delta.ent;
|
||||||
*ent = S_NilEnt;
|
*ent = P_NilEnt;
|
||||||
ent->key = S_RandKey();
|
ent->key = P_RandKey();
|
||||||
ent->xf = XformFromPos(frame->world_cursor);
|
ent->xf = XformFromPos(frame->world_cursor);
|
||||||
ent->is_player = 1;
|
ent->is_player = 1;
|
||||||
ent->has_weapon = 1;
|
ent->has_weapon = 1;
|
||||||
@ -2549,9 +2536,9 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
{
|
{
|
||||||
if (hovered_ent->valid)
|
if (hovered_ent->valid)
|
||||||
{
|
{
|
||||||
S_Cmd *cmd = V_PushSimCmd(S_CmdKind_Delta);
|
P_Cmd *cmd = V_PushSimCmd(P_CmdKind_Delta);
|
||||||
cmd->delta.kind = S_DeltaKind_RawEnt;
|
cmd->delta.kind = P_DeltaKind_RawEnt;
|
||||||
S_Ent *ent = &cmd->delta.ent;
|
P_Ent *ent = &cmd->delta.ent;
|
||||||
ent->key = hovered_ent->key;
|
ent->key = hovered_ent->key;
|
||||||
ent->exists = 0;
|
ent->exists = 0;
|
||||||
}
|
}
|
||||||
@ -2561,7 +2548,7 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
{
|
{
|
||||||
if (frame->is_editing)
|
if (frame->is_editing)
|
||||||
{
|
{
|
||||||
S_Cmd *cmd = V_PushSimCmd(S_CmdKind_Save);
|
P_Cmd *cmd = V_PushSimCmd(P_CmdKind_Save);
|
||||||
}
|
}
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
@ -2587,7 +2574,7 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
f32 fire_presses = fire_held && !last_frame->held_buttons[Button_M1];
|
f32 fire_presses = fire_held && !last_frame->held_buttons[Button_M1];
|
||||||
Vec2 look = Zi;
|
Vec2 look = Zi;
|
||||||
{
|
{
|
||||||
Vec2 center = S_WorldShapeFromEnt(player).centroid;
|
Vec2 center = P_WorldShapeFromEnt(player).centroid;
|
||||||
look = SubVec2(frame->world_cursor, center);
|
look = SubVec2(frame->world_cursor, center);
|
||||||
}
|
}
|
||||||
if (frame->is_editing)
|
if (frame->is_editing)
|
||||||
@ -2609,7 +2596,7 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
|
|
||||||
// Push control cmd
|
// Push control cmd
|
||||||
{
|
{
|
||||||
S_Cmd *cmd = V_PushSimCmd(S_CmdKind_Control);
|
P_Cmd *cmd = V_PushSimCmd(P_CmdKind_Control);
|
||||||
cmd->target = V.player_key;
|
cmd->target = V.player_key;
|
||||||
cmd->move = frame->move;
|
cmd->move = frame->move;
|
||||||
cmd->look = frame->look;
|
cmd->look = frame->look;
|
||||||
@ -2620,18 +2607,18 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
//////////////////////////////
|
//////////////////////////////
|
||||||
//- Submit sim commands
|
//- Submit sim commands
|
||||||
|
|
||||||
LockTicketMutex(&S.input_back_tm);
|
LockTicketMutex(&P.sim_input_back_tm);
|
||||||
{
|
{
|
||||||
S_InputState *v2s = &S.input_states[S.input_back_idx];
|
P_InputState *v2s = &P.sim_input_states[P.sim_input_back_idx];
|
||||||
for (S_CmdNode *src = frame->first_sim_cmd_node; src; src = src->next)
|
for (P_CmdNode *src = frame->first_sim_cmd_node; src; src = src->next)
|
||||||
{
|
{
|
||||||
S_CmdNode *cmd_node = PushStruct(v2s->arena, S_CmdNode);
|
P_CmdNode *cmd_node = PushStruct(v2s->arena, P_CmdNode);
|
||||||
cmd_node->cmd = src->cmd;
|
cmd_node->cmd = src->cmd;
|
||||||
SllQueuePush(v2s->first_cmd_node, v2s->last_cmd_node, cmd_node);
|
SllQueuePush(v2s->first_cmd_node, v2s->last_cmd_node, cmd_node);
|
||||||
++v2s->cmds_count;
|
++v2s->cmds_count;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
UnlockTicketMutex(&S.input_back_tm);
|
UnlockTicketMutex(&P.sim_input_back_tm);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@ -2648,7 +2635,7 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
for (S_Ent *bullet = S_FirstEnt(world); bullet->valid; bullet = S_NextEnt(bullet))
|
for (P_Ent *bullet = P_FirstEnt(world); bullet->valid; bullet = P_NextEnt(bullet))
|
||||||
{
|
{
|
||||||
if (bullet->is_bullet)
|
if (bullet->is_bullet)
|
||||||
{
|
{
|
||||||
@ -2828,7 +2815,7 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
|
|
||||||
if (0)
|
if (0)
|
||||||
{
|
{
|
||||||
for (S_Ent *bullet = S_FirstEnt(world); bullet->valid; bullet = S_NextEnt(bullet))
|
for (P_Ent *bullet = P_FirstEnt(world); bullet->valid; bullet = P_NextEnt(bullet))
|
||||||
{
|
{
|
||||||
if (bullet->is_bullet && bullet->has_hit)
|
if (bullet->is_bullet && bullet->has_hit)
|
||||||
{
|
{
|
||||||
@ -2905,29 +2892,29 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
|
|
||||||
|
|
||||||
// {
|
// {
|
||||||
// for (S_Ent *firer = S_FirstEnt(world); firer->valid; firer = S_NextEnt(firer))
|
// for (P_Ent *firer = P_FirstEnt(world); firer->valid; firer = P_NextEnt(firer))
|
||||||
// {
|
// {
|
||||||
// if (firer->fire_held)
|
// if (firer->fire_held)
|
||||||
// {
|
// {
|
||||||
// Xform firer_xf = firer->xf;
|
// Xform firer_xf = firer->xf;
|
||||||
// S_Shape firer_world_shape = S_MulXformShape(firer_xf, firer->local_shape);
|
// P_Shape firer_world_shape = P_MulXformShape(firer_xf, firer->local_shape);
|
||||||
|
|
||||||
// Vec2 ray_start = firer_world_shape.centroid;
|
// Vec2 ray_start = firer_world_shape.centroid;
|
||||||
// Vec2 ray_dir = firer->look;
|
// Vec2 ray_dir = firer->look;
|
||||||
|
|
||||||
// // TODO: Real raycast query
|
// // TODO: Real raycast query
|
||||||
// S_Ent *closest_victim = &S_NilEnt;
|
// P_Ent *closest_victim = &P_NilEnt;
|
||||||
// S_RaycastResult victim_raycast = Zi;
|
// P_RaycastResult victim_raycast = Zi;
|
||||||
// {
|
// {
|
||||||
// f32 closest_len_sq = Inf;
|
// f32 closest_len_sq = Inf;
|
||||||
// for (S_Ent *victim = S_FirstEnt(world); victim->valid; victim = S_NextEnt(victim))
|
// for (P_Ent *victim = P_FirstEnt(world); victim->valid; victim = P_NextEnt(victim))
|
||||||
// {
|
// {
|
||||||
// if (victim != firer)
|
// if (victim != firer)
|
||||||
// {
|
// {
|
||||||
// Xform victim_xf = victim->xf;
|
// Xform victim_xf = victim->xf;
|
||||||
// S_Shape victim_world_shape = S_MulXformShape(victim_xf, victim->local_shape);
|
// P_Shape victim_world_shape = P_MulXformShape(victim_xf, victim->local_shape);
|
||||||
|
|
||||||
// S_RaycastResult raycast = S_RaycastShape(victim_world_shape, ray_start, ray_dir);
|
// P_RaycastResult raycast = P_RaycastShape(victim_world_shape, ray_start, ray_dir);
|
||||||
// if (raycast.is_intersecting)
|
// if (raycast.is_intersecting)
|
||||||
// {
|
// {
|
||||||
// f32 len_sq = Vec2LenSq(SubVec2(raycast.p, ray_start));
|
// f32 len_sq = Vec2LenSq(SubVec2(raycast.p, ray_start));
|
||||||
@ -2990,8 +2977,8 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
// }
|
// }
|
||||||
|
|
||||||
|
|
||||||
// // for (S_QueryResult query = S_FirstRaycast(wrold, ray_start, ray_dir); query.
|
// // for (P_QueryResult query = P_FirstRaycast(wrold, ray_start, ray_dir); query.
|
||||||
// // S_RaycastWorldResult hits = S_RaycastWorld(world, ray_start, ray_dir)
|
// // P_RaycastWorldResult hits = P_RaycastWorld(world, ray_start, ray_dir)
|
||||||
// // {
|
// // {
|
||||||
// // }
|
// // }
|
||||||
// }
|
// }
|
||||||
@ -3027,14 +3014,98 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
V_PushParticles(emitter);
|
V_PushParticles(emitter);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//////////////////////////////
|
||||||
|
//- Debug draw
|
||||||
|
|
||||||
|
{
|
||||||
|
// Copy debug draw data from sim
|
||||||
|
if (received_unseen_tick)
|
||||||
|
{
|
||||||
|
ResetArena(sim_debug_arena);
|
||||||
|
first_sim_debug_draw_node = 0;
|
||||||
|
last_sim_debug_draw_node = 0;
|
||||||
|
{
|
||||||
|
i64 dst_idx = 0;
|
||||||
|
P_DebugDrawNode *dst_nodes = PushStructsNoZero(sim_debug_arena, P_DebugDrawNode, sim_output->debug_draw_nodes_count);
|
||||||
|
for (P_DebugDrawNode *src = sim_output->first_debug_draw_node; src; src = src->next)
|
||||||
|
{
|
||||||
|
P_DebugDrawNode *dst = &dst_nodes[dst_idx];
|
||||||
|
*dst = *src;
|
||||||
|
dst_idx += 1;
|
||||||
|
SllQueuePush(first_sim_debug_draw_node, last_sim_debug_draw_node, dst);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Merge vis debug draws with sim debug draws
|
||||||
|
P_DebugDrawNode *first_debug_draw_node = first_sim_debug_draw_node;
|
||||||
|
P_DebugDrawNode *last_debug_draw_node = last_sim_debug_draw_node;
|
||||||
|
if (P_tl.first_debug_draw_node)
|
||||||
|
{
|
||||||
|
if (last_debug_draw_node)
|
||||||
|
{
|
||||||
|
last_debug_draw_node->next = P_tl.first_debug_draw_node;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
first_debug_draw_node = P_tl.first_debug_draw_node;
|
||||||
|
}
|
||||||
|
last_debug_draw_node = P_tl.last_debug_draw_node;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (P_DebugDrawNode *n = first_debug_draw_node; n; n = n->next)
|
||||||
|
{
|
||||||
|
Vec4 color = Vec4FromU32(n->srgb32);
|
||||||
|
i32 detail = 24;
|
||||||
|
f32 radius = 5;
|
||||||
|
switch(n->kind)
|
||||||
|
{
|
||||||
|
case P_DebugDrawKind_Point:
|
||||||
|
{
|
||||||
|
Vec2 ui_p = MulXformV2(frame->xf.world_to_ui, n->point.p);
|
||||||
|
V_DrawPoint(ui_p, color);
|
||||||
|
} break;
|
||||||
|
|
||||||
|
case P_DebugDrawKind_Line:
|
||||||
|
{
|
||||||
|
Vec2 ui_p0 = MulXformV2(frame->xf.world_to_ui, n->line.p0);
|
||||||
|
Vec2 ui_p1 = MulXformV2(frame->xf.world_to_ui, n->line.p1);
|
||||||
|
V_DrawLine(ui_p0, ui_p1, color);
|
||||||
|
} break;
|
||||||
|
|
||||||
|
case P_DebugDrawKind_Rect:
|
||||||
|
{
|
||||||
|
Rng2 ui_rect = Zi;
|
||||||
|
ui_rect.p0 = MulXformV2(frame->xf.world_to_ui, n->rect.p0);
|
||||||
|
ui_rect.p1 = MulXformV2(frame->xf.world_to_ui, n->rect.p1);
|
||||||
|
V_DrawRect(ui_rect, color, V_DrawFlag_Line);
|
||||||
|
} break;
|
||||||
|
|
||||||
|
case P_DebugDrawKind_Shape:
|
||||||
|
{
|
||||||
|
P_Shape ui_shape = P_MulXformShape(frame->xf.world_to_ui, n->shape);
|
||||||
|
V_DrawShape(ui_shape, color, detail, V_DrawFlag_Line);
|
||||||
|
// V_DrawShape(ui_shape, color, detail, V_DrawFlag_None);
|
||||||
|
} break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Reset vis debug draws
|
||||||
|
ResetArena(P_tl.debug_arena);
|
||||||
|
P_tl.first_debug_draw_node = 0;
|
||||||
|
P_tl.last_debug_draw_node = 0;
|
||||||
|
P_tl.debug_draw_nodes_count = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
//////////////////////////////
|
//////////////////////////////
|
||||||
//- Draw entities
|
//- Draw entities
|
||||||
|
|
||||||
// for (S_Ent *ent = S_FirstEnt(world); ent->valid; ent = S_NextEnt(ent))
|
// for (P_Ent *ent = P_FirstEnt(world); ent->valid; ent = P_NextEnt(ent))
|
||||||
// {
|
// {
|
||||||
// Xform ent_to_world_xf = ent->xf;
|
// Xform ent_to_world_xf = ent->xf;
|
||||||
// Xform ent_to_draw_xf = MulXform(frame->xf.world_to_draw, ent_to_world_xf);
|
// Xform ent_to_draw_xf = MulXform(frame->xf.world_to_draw, ent_to_world_xf);
|
||||||
// S_Shape draw_shape = S_MulXformShape(ent_to_draw_xf, ent->local_shape);
|
// P_Shape draw_shape = P_MulXformShape(ent_to_draw_xf, ent->local_shape);
|
||||||
|
|
||||||
// f32 opacity = 0.5;
|
// f32 opacity = 0.5;
|
||||||
|
|
||||||
@ -3056,7 +3127,7 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
// // color.w *= opacity;
|
// // color.w *= opacity;
|
||||||
// // f32 width = 0.1;
|
// // f32 width = 0.1;
|
||||||
// // f32 height = 0.75;
|
// // f32 height = 0.75;
|
||||||
// // S_Shape local_shape = S_ShapeFromDesc(
|
// // P_Shape local_shape = P_ShapeFromDesc(
|
||||||
// // .count = 4,
|
// // .count = 4,
|
||||||
// // .points = {
|
// // .points = {
|
||||||
// // VEC2(-width / 2, -height), VEC2(width / 2, -height),
|
// // VEC2(-width / 2, -height), VEC2(width / 2, -height),
|
||||||
@ -3065,7 +3136,7 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
// // );
|
// // );
|
||||||
// // Xform local_xf = XformFromTrs(TRS(.t = { 0, 0 }, .r = Tau / 4));
|
// // Xform local_xf = XformFromTrs(TRS(.t = { 0, 0 }, .r = Tau / 4));
|
||||||
// // Xform xf = MulXform(ent_to_draw_xf, local_xf);
|
// // Xform xf = MulXform(ent_to_draw_xf, local_xf);
|
||||||
// // S_Shape shape = S_MulXformShape(xf, local_shape);
|
// // P_Shape shape = P_MulXformShape(xf, local_shape);
|
||||||
// // V_DrawShape(shape, color, 10, V_DrawFlag_Line);
|
// // V_DrawShape(shape, color, 10, V_DrawFlag_Line);
|
||||||
// // }
|
// // }
|
||||||
|
|
||||||
@ -3073,53 +3144,12 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
// // {
|
// // {
|
||||||
// // Vec4 color = Color_Orange;
|
// // Vec4 color = Color_Orange;
|
||||||
// // color.w *= opacity;
|
// // color.w *= opacity;
|
||||||
// // Rng2 bb = S_BoundingBoxFromShape(draw_shape);
|
// // Rng2 bb = P_BoundingBoxFromShape(draw_shape);
|
||||||
// // V_DrawRect(bb, color, V_DrawFlag_Line);
|
// // V_DrawRect(bb, color, V_DrawFlag_Line);
|
||||||
// // }
|
// // }
|
||||||
// }
|
// }
|
||||||
// }
|
// }
|
||||||
|
|
||||||
//////////////////////////////
|
|
||||||
//- Draw sim debug shapes
|
|
||||||
|
|
||||||
for (u64 desc_idx = 0; desc_idx < sim_debug_draw_descs_count; ++desc_idx)
|
|
||||||
{
|
|
||||||
S_DebugDrawDesc *desc = &sim_debug_draw_descs[desc_idx];
|
|
||||||
Vec4 color = Vec4FromU32(desc->srgb32);
|
|
||||||
i32 detail = 24;
|
|
||||||
f32 radius = 5;
|
|
||||||
switch(desc->kind)
|
|
||||||
{
|
|
||||||
case S_DebugDrawKind_Point:
|
|
||||||
{
|
|
||||||
Vec2 ui_p = MulXformV2(frame->xf.world_to_ui, desc->point.p);
|
|
||||||
V_DrawPoint(ui_p, color);
|
|
||||||
} break;
|
|
||||||
|
|
||||||
case S_DebugDrawKind_Line:
|
|
||||||
{
|
|
||||||
Vec2 ui_p0 = MulXformV2(frame->xf.world_to_ui, desc->line.p0);
|
|
||||||
Vec2 ui_p1 = MulXformV2(frame->xf.world_to_ui, desc->line.p1);
|
|
||||||
V_DrawLine(ui_p0, ui_p1, color);
|
|
||||||
} break;
|
|
||||||
|
|
||||||
case S_DebugDrawKind_Rect:
|
|
||||||
{
|
|
||||||
Rng2 ui_rect = Zi;
|
|
||||||
ui_rect.p0 = MulXformV2(frame->xf.world_to_ui, desc->rect.p0);
|
|
||||||
ui_rect.p1 = MulXformV2(frame->xf.world_to_ui, desc->rect.p1);
|
|
||||||
V_DrawRect(ui_rect, color, V_DrawFlag_Line);
|
|
||||||
} break;
|
|
||||||
|
|
||||||
case S_DebugDrawKind_Shape:
|
|
||||||
{
|
|
||||||
S_Shape ui_shape = S_MulXformShape(frame->xf.world_to_ui, desc->shape);
|
|
||||||
V_DrawShape(ui_shape, color, detail, V_DrawFlag_Line);
|
|
||||||
// V_DrawShape(ui_shape, color, detail, V_DrawFlag_None);
|
|
||||||
} break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//////////////////////////////
|
//////////////////////////////
|
||||||
//- Render
|
//- Render
|
||||||
|
|
||||||
@ -3207,9 +3237,9 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
|
|
||||||
// Fill tile textures
|
// Fill tile textures
|
||||||
{
|
{
|
||||||
for (S_TileKind tile_kind = 0; tile_kind < S_TileKind_COUNT; ++tile_kind)
|
for (P_TileKind tile_kind = 0; tile_kind < P_TileKind_COUNT; ++tile_kind)
|
||||||
{
|
{
|
||||||
String tile_name = S_TileNameFromKind(tile_kind);
|
String tile_name = P_TileNameFromKind(tile_kind);
|
||||||
String sheet_name = StringF(frame->arena, "tile/%F.ase", FmtString(tile_name));
|
String sheet_name = StringF(frame->arena, "tile/%F.ase", FmtString(tile_name));
|
||||||
ResourceKey sheet_resource = ResourceKeyFromStore(&P_Resources, sheet_name);
|
ResourceKey sheet_resource = ResourceKeyFromStore(&P_Resources, sheet_name);
|
||||||
SPR_SheetKey sheet = SPR_SheetKeyFromResource(sheet_resource);
|
SPR_SheetKey sheet = SPR_SheetKeyFromResource(sheet_resource);
|
||||||
@ -3343,8 +3373,8 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
|
|
||||||
{
|
{
|
||||||
i64 ents_to_prune_count = 0;
|
i64 ents_to_prune_count = 0;
|
||||||
S_Ent **ents_to_prune = PushStructsNoZero(frame->arena, S_Ent *, world->ents_count);
|
P_Ent **ents_to_prune = PushStructsNoZero(frame->arena, P_Ent *, world->ents_count);
|
||||||
for (S_Ent *ent = S_FirstEnt(world); ent->valid; ent = S_NextEnt(ent))
|
for (P_Ent *ent = P_FirstEnt(world); ent->valid; ent = P_NextEnt(ent))
|
||||||
{
|
{
|
||||||
if (ent->exists <= 0)
|
if (ent->exists <= 0)
|
||||||
{
|
{
|
||||||
@ -3356,8 +3386,8 @@ void V_TickForever(WaveLaneCtx *lane)
|
|||||||
for (i64 prune_idx = 0; prune_idx < ents_to_prune_count; ++prune_idx)
|
for (i64 prune_idx = 0; prune_idx < ents_to_prune_count; ++prune_idx)
|
||||||
{
|
{
|
||||||
// FIXME: Add to free list
|
// FIXME: Add to free list
|
||||||
S_Ent *ent = ents_to_prune[prune_idx];
|
P_Ent *ent = ents_to_prune[prune_idx];
|
||||||
S_EntBin *bin = &world->ent_bins[ent->key.v % world->ent_bins_count];
|
P_EntBin *bin = &world->ent_bins[ent->key.v % world->ent_bins_count];
|
||||||
DllQueueRemoveNP(bin->first, bin->last, ent, next_in_bin, prev_in_bin);
|
DllQueueRemoveNP(bin->first, bin->last, ent, next_in_bin, prev_in_bin);
|
||||||
DllQueueRemove(world->first_ent, world->last_ent, ent);
|
DllQueueRemove(world->first_ent, world->last_ent, ent);
|
||||||
world->ents_count -= 1;
|
world->ents_count -= 1;
|
||||||
|
|||||||
@ -234,7 +234,7 @@ Struct(V_Frame)
|
|||||||
|
|
||||||
// Editor state
|
// Editor state
|
||||||
V_EditMode edit_mode;
|
V_EditMode edit_mode;
|
||||||
S_TileKind equipped_tile;
|
P_TileKind equipped_tile;
|
||||||
|
|
||||||
// Editor
|
// Editor
|
||||||
b32 is_selecting;
|
b32 is_selecting;
|
||||||
@ -273,8 +273,8 @@ Struct(V_Frame)
|
|||||||
|
|
||||||
// Sim cmds
|
// Sim cmds
|
||||||
u64 sim_cmds_count;
|
u64 sim_cmds_count;
|
||||||
S_CmdNode *first_sim_cmd_node;
|
P_CmdNode *first_sim_cmd_node;
|
||||||
S_CmdNode *last_sim_cmd_node;
|
P_CmdNode *last_sim_cmd_node;
|
||||||
|
|
||||||
// Emitters
|
// Emitters
|
||||||
i64 emitters_count;
|
i64 emitters_count;
|
||||||
@ -284,7 +284,7 @@ Struct(V_Frame)
|
|||||||
|
|
||||||
Struct(V_Ctx)
|
Struct(V_Ctx)
|
||||||
{
|
{
|
||||||
S_Key player_key;
|
P_Key player_key;
|
||||||
|
|
||||||
i64 panels_count;
|
i64 panels_count;
|
||||||
i64 windows_count;
|
i64 windows_count;
|
||||||
@ -315,7 +315,7 @@ void V_Shutdown(void);
|
|||||||
V_Frame *V_CurrentFrame(void);
|
V_Frame *V_CurrentFrame(void);
|
||||||
V_Frame *V_LastFrame(void);
|
V_Frame *V_LastFrame(void);
|
||||||
V_Cmd *V_PushVisCmd(String name);
|
V_Cmd *V_PushVisCmd(String name);
|
||||||
S_Cmd *V_PushSimCmd(S_CmdKind kind);
|
P_Cmd *V_PushSimCmd(P_CmdKind kind);
|
||||||
String V_StringFromHotkey(Arena *arena, V_Hotkey hotkey);
|
String V_StringFromHotkey(Arena *arena, V_Hotkey hotkey);
|
||||||
void V_PushParticles(V_Emitter src);
|
void V_PushParticles(V_Emitter src);
|
||||||
|
|
||||||
@ -323,7 +323,7 @@ void V_PushParticles(V_Emitter src);
|
|||||||
//~ Draw helpers
|
//~ Draw helpers
|
||||||
|
|
||||||
void V_DrawPoly(Vec2Array points, Vec4 srgb, V_DrawFlag flags);
|
void V_DrawPoly(Vec2Array points, Vec4 srgb, V_DrawFlag flags);
|
||||||
void V_DrawShape(S_Shape shape, Vec4 srgb, i32 detail, V_DrawFlag flags);
|
void V_DrawShape(P_Shape shape, Vec4 srgb, i32 detail, V_DrawFlag flags);
|
||||||
void V_DrawLine(Vec2 p0, Vec2 p1, Vec4 srgb);
|
void V_DrawLine(Vec2 p0, Vec2 p1, Vec4 srgb);
|
||||||
void V_DrawRect(Rng2 rect, Vec4 srgb, V_DrawFlag flags);
|
void V_DrawRect(Rng2 rect, Vec4 srgb, V_DrawFlag flags);
|
||||||
void V_DrawPoint(Vec2 p, Vec4 srgb);
|
void V_DrawPoint(Vec2 p, Vec4 srgb);
|
||||||
|
|||||||
@ -69,7 +69,7 @@ ComputeShader2D(V_BackdropCS, 8, 8)
|
|||||||
{
|
{
|
||||||
V_GpuParams params = G_Dereference<V_GpuParams>(V_ShaderConst_Params)[0];
|
V_GpuParams params = G_Dereference<V_GpuParams>(V_ShaderConst_Params)[0];
|
||||||
RWTexture2D<Vec4> target = G_Dereference<Vec4>(params.target_rw);
|
RWTexture2D<Vec4> target = G_Dereference<Vec4>(params.target_rw);
|
||||||
Texture2D<S_TileKind> tiles = G_Dereference<S_TileKind>(params.tiles);
|
Texture2D<P_TileKind> tiles = G_Dereference<P_TileKind>(params.tiles);
|
||||||
|
|
||||||
const Vec4 background_color_a = LinearFromSrgb(Vec4(0.30, 0.30, 0.30, 1));
|
const Vec4 background_color_a = LinearFromSrgb(Vec4(0.30, 0.30, 0.30, 1));
|
||||||
const Vec4 background_color_b = LinearFromSrgb(Vec4(0.15, 0.15, 0.15, 1));
|
const Vec4 background_color_b = LinearFromSrgb(Vec4(0.15, 0.15, 0.15, 1));
|
||||||
@ -82,10 +82,10 @@ ComputeShader2D(V_BackdropCS, 8, 8)
|
|||||||
Vec2 cell_pos = floor(mul(params.xf.world_to_cell, Vec3(world_pos, 1)));
|
Vec2 cell_pos = floor(mul(params.xf.world_to_cell, Vec3(world_pos, 1)));
|
||||||
Vec2 tile_pos = mul(params.xf.world_to_tile, Vec3(world_pos, 1));
|
Vec2 tile_pos = mul(params.xf.world_to_tile, Vec3(world_pos, 1));
|
||||||
|
|
||||||
S_TileKind tile = tiles.Load(Vec3(tile_pos, 0));
|
P_TileKind tile = tiles.Load(Vec3(tile_pos, 0));
|
||||||
|
|
||||||
f32 half_thickness = 1;
|
f32 half_thickness = 1;
|
||||||
f32 half_bounds_size = S_WorldPitch * 0.5;
|
f32 half_bounds_size = P_WorldPitch * 0.5;
|
||||||
Vec2 bounds_screen_p0 = mul(params.xf.world_to_ui, Vec3(-half_bounds_size, -half_bounds_size, 1));
|
Vec2 bounds_screen_p0 = mul(params.xf.world_to_ui, Vec3(-half_bounds_size, -half_bounds_size, 1));
|
||||||
Vec2 bounds_screen_p1 = mul(params.xf.world_to_ui, Vec3(half_bounds_size, half_bounds_size, 1));
|
Vec2 bounds_screen_p1 = mul(params.xf.world_to_ui, Vec3(half_bounds_size, half_bounds_size, 1));
|
||||||
bool is_in_bounds = ui_pos.x > (bounds_screen_p0.x - half_thickness) &&
|
bool is_in_bounds = ui_pos.x > (bounds_screen_p0.x - half_thickness) &&
|
||||||
@ -125,17 +125,17 @@ ComputeShader2D(V_BackdropCS, 8, 8)
|
|||||||
// Tile test
|
// Tile test
|
||||||
// TODO: Remove this
|
// TODO: Remove this
|
||||||
{
|
{
|
||||||
S_TileKind tile_tl = tiles.Load(Vec3(tile_pos.x - 1, tile_pos.y - 1, 0));
|
P_TileKind tile_tl = tiles.Load(Vec3(tile_pos.x - 1, tile_pos.y - 1, 0));
|
||||||
S_TileKind tile_tr = tiles.Load(Vec3(tile_pos.x + 1, tile_pos.y - 1, 0));
|
P_TileKind tile_tr = tiles.Load(Vec3(tile_pos.x + 1, tile_pos.y - 1, 0));
|
||||||
S_TileKind tile_br = tiles.Load(Vec3(tile_pos.x + 1, tile_pos.y + 1, 0));
|
P_TileKind tile_br = tiles.Load(Vec3(tile_pos.x + 1, tile_pos.y + 1, 0));
|
||||||
S_TileKind tile_bl = tiles.Load(Vec3(tile_pos.x - 1, tile_pos.y + 1, 0));
|
P_TileKind tile_bl = tiles.Load(Vec3(tile_pos.x - 1, tile_pos.y + 1, 0));
|
||||||
S_TileKind tile_t = tiles.Load(Vec3(tile_pos.x, tile_pos.y - 1, 0));
|
P_TileKind tile_t = tiles.Load(Vec3(tile_pos.x, tile_pos.y - 1, 0));
|
||||||
S_TileKind tile_r = tiles.Load(Vec3(tile_pos.x + 1, tile_pos.y, 0));
|
P_TileKind tile_r = tiles.Load(Vec3(tile_pos.x + 1, tile_pos.y, 0));
|
||||||
S_TileKind tile_b = tiles.Load(Vec3(tile_pos.x, tile_pos.y + 1, 0));
|
P_TileKind tile_b = tiles.Load(Vec3(tile_pos.x, tile_pos.y + 1, 0));
|
||||||
S_TileKind tile_l = tiles.Load(Vec3(tile_pos.x - 1, tile_pos.y, 0));
|
P_TileKind tile_l = tiles.Load(Vec3(tile_pos.x - 1, tile_pos.y, 0));
|
||||||
|
|
||||||
f32 tile_edge_dist = Inf;
|
f32 tile_edge_dist = Inf;
|
||||||
S_TileKind edge_tile = tile;
|
P_TileKind edge_tile = tile;
|
||||||
if (tile_tl != tile) { edge_tile = tile_tl; tile_edge_dist = min(tile_edge_dist, length(tile_pos - Vec2(floor(tile_pos.x), floor(tile_pos.y)))); }
|
if (tile_tl != tile) { edge_tile = tile_tl; tile_edge_dist = min(tile_edge_dist, length(tile_pos - Vec2(floor(tile_pos.x), floor(tile_pos.y)))); }
|
||||||
if (tile_tr != tile) { edge_tile = tile_tr; tile_edge_dist = min(tile_edge_dist, length(tile_pos - Vec2(ceil(tile_pos.x), floor(tile_pos.y)))); }
|
if (tile_tr != tile) { edge_tile = tile_tr; tile_edge_dist = min(tile_edge_dist, length(tile_pos - Vec2(ceil(tile_pos.x), floor(tile_pos.y)))); }
|
||||||
if (tile_br != tile) { edge_tile = tile_br; tile_edge_dist = min(tile_edge_dist, length(tile_pos - Vec2(ceil(tile_pos.x), ceil(tile_pos.y)))); }
|
if (tile_br != tile) { edge_tile = tile_br; tile_edge_dist = min(tile_edge_dist, length(tile_pos - Vec2(ceil(tile_pos.x), ceil(tile_pos.y)))); }
|
||||||
@ -145,14 +145,14 @@ ComputeShader2D(V_BackdropCS, 8, 8)
|
|||||||
if (tile_t != tile) { edge_tile = tile_t; tile_edge_dist = min(tile_edge_dist, frac(tile_pos.y)); }
|
if (tile_t != tile) { edge_tile = tile_t; tile_edge_dist = min(tile_edge_dist, frac(tile_pos.y)); }
|
||||||
if (tile_b != tile) { edge_tile = tile_b; tile_edge_dist = min(tile_edge_dist, 1.0 - frac(tile_pos.y)); }
|
if (tile_b != tile) { edge_tile = tile_b; tile_edge_dist = min(tile_edge_dist, 1.0 - frac(tile_pos.y)); }
|
||||||
|
|
||||||
if (tile == S_TileKind_Wall)
|
if (tile == P_TileKind_Wall)
|
||||||
{
|
{
|
||||||
Vec4 outer = LinearFromSrgb(Vec4(0.05, 0.05, 0.05, 1));
|
Vec4 outer = LinearFromSrgb(Vec4(0.05, 0.05, 0.05, 1));
|
||||||
Vec4 inner = LinearFromSrgb(Vec4(0.10, 0.10, 0.10, 1));
|
Vec4 inner = LinearFromSrgb(Vec4(0.10, 0.10, 0.10, 1));
|
||||||
result = lerp(outer, inner, smoothstep(0, 1, tile_edge_dist / 0.375));
|
result = lerp(outer, inner, smoothstep(0, 1, tile_edge_dist / 0.375));
|
||||||
// result = lerp(outer, inner, smoothstep(0, 1, tile_edge_dist / 0.5));
|
// result = lerp(outer, inner, smoothstep(0, 1, tile_edge_dist / 0.5));
|
||||||
}
|
}
|
||||||
else if (tile != S_TileKind_Empty)
|
else if (tile != P_TileKind_Empty)
|
||||||
{
|
{
|
||||||
SamplerState wrap_sampler = G_Dereference(params.pt_wrap_sampler);
|
SamplerState wrap_sampler = G_Dereference(params.pt_wrap_sampler);
|
||||||
SPR_Slice slice = params.tile_slices[tile];
|
SPR_Slice slice = params.tile_slices[tile];
|
||||||
@ -166,12 +166,12 @@ ComputeShader2D(V_BackdropCS, 8, 8)
|
|||||||
// {
|
// {
|
||||||
// default: break;
|
// default: break;
|
||||||
|
|
||||||
// case S_TileKind_Floor:
|
// case P_TileKind_Floor:
|
||||||
// {
|
// {
|
||||||
// result = Color_Blue;
|
// result = Color_Blue;
|
||||||
// } break;
|
// } break;
|
||||||
|
|
||||||
// case S_TileKind_Wall:
|
// case P_TileKind_Wall:
|
||||||
// {
|
// {
|
||||||
// // result = Color_Red;
|
// // result = Color_Red;
|
||||||
// result = Color_Black;
|
// result = Color_Black;
|
||||||
@ -517,10 +517,10 @@ PixelShader(V_OverlayPS, V_OverlayPSOutput, V_OverlayPSInput input)
|
|||||||
|
|
||||||
Vec2 world_pos = mul(params.xf.ui_to_world, Vec3(ui_pos, 1));
|
Vec2 world_pos = mul(params.xf.ui_to_world, Vec3(ui_pos, 1));
|
||||||
Vec2 tile_pos = mul(params.xf.world_to_tile, Vec3(world_pos, 1));
|
Vec2 tile_pos = mul(params.xf.world_to_tile, Vec3(world_pos, 1));
|
||||||
S_TileKind equipped_tile = params.equipped_tile;
|
P_TileKind equipped_tile = params.equipped_tile;
|
||||||
|
|
||||||
f32 half_thickness = 1;
|
f32 half_thickness = 1;
|
||||||
f32 half_bounds_size = S_WorldPitch * 0.5;
|
f32 half_bounds_size = P_WorldPitch * 0.5;
|
||||||
Vec2 bounds_screen_p0 = mul(params.xf.world_to_ui, Vec3(-half_bounds_size, -half_bounds_size, 1));
|
Vec2 bounds_screen_p0 = mul(params.xf.world_to_ui, Vec3(-half_bounds_size, -half_bounds_size, 1));
|
||||||
Vec2 bounds_screen_p1 = mul(params.xf.world_to_ui, Vec3(half_bounds_size, half_bounds_size, 1));
|
Vec2 bounds_screen_p1 = mul(params.xf.world_to_ui, Vec3(half_bounds_size, half_bounds_size, 1));
|
||||||
bool is_in_bounds = ui_pos.x > (bounds_screen_p0.x - half_thickness) &&
|
bool is_in_bounds = ui_pos.x > (bounds_screen_p0.x - half_thickness) &&
|
||||||
@ -558,10 +558,10 @@ PixelShader(V_OverlayPS, V_OverlayPSOutput, V_OverlayPSInput input)
|
|||||||
// else
|
// else
|
||||||
{
|
{
|
||||||
if (
|
if (
|
||||||
world_pos.x > -(S_WorldPitch / 2) &&
|
world_pos.x > -(P_WorldPitch / 2) &&
|
||||||
world_pos.y > -(S_WorldPitch / 2) &&
|
world_pos.y > -(P_WorldPitch / 2) &&
|
||||||
world_pos.x < (S_WorldPitch / 2) &&
|
world_pos.x < (P_WorldPitch / 2) &&
|
||||||
world_pos.y < (S_WorldPitch / 2) &&
|
world_pos.y < (P_WorldPitch / 2) &&
|
||||||
tile_pos.x >= tile_selection.p0.x &&
|
tile_pos.x >= tile_selection.p0.x &&
|
||||||
tile_pos.x <= tile_selection.p1.x &&
|
tile_pos.x <= tile_selection.p1.x &&
|
||||||
tile_pos.y >= tile_selection.p0.y &&
|
tile_pos.y >= tile_selection.p0.y &&
|
||||||
|
|||||||
@ -71,7 +71,7 @@ Struct(V_GpuParams)
|
|||||||
G_SamplerStateRef pt_wrap_sampler;
|
G_SamplerStateRef pt_wrap_sampler;
|
||||||
|
|
||||||
V_SelectionMode selection_mode;
|
V_SelectionMode selection_mode;
|
||||||
S_TileKind equipped_tile;
|
P_TileKind equipped_tile;
|
||||||
|
|
||||||
b32 has_mouse_focus;
|
b32 has_mouse_focus;
|
||||||
b32 has_keyboard_focus;
|
b32 has_keyboard_focus;
|
||||||
@ -99,7 +99,7 @@ Struct(V_GpuParams)
|
|||||||
G_RWTexture2DRef stains;
|
G_RWTexture2DRef stains;
|
||||||
G_RWTexture2DRef drynesses;
|
G_RWTexture2DRef drynesses;
|
||||||
|
|
||||||
SPR_Slice tile_slices[S_TileKind_COUNT];
|
SPR_Slice tile_slices[P_TileKind_COUNT];
|
||||||
};
|
};
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
|
|||||||
@ -92,6 +92,7 @@ SPR_Slice SPR_SliceFromSheet(SPR_SheetKey sheet, String slice_name)
|
|||||||
SPR_CmdNode *n = SPR.submit.first_free;
|
SPR_CmdNode *n = SPR.submit.first_free;
|
||||||
if (n)
|
if (n)
|
||||||
{
|
{
|
||||||
|
SllStackPop(SPR.submit.first_free);
|
||||||
ZeroStruct(n);
|
ZeroStruct(n);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user