diff --git a/src/config.h b/src/config.h index 55e619fe..445355e9 100644 --- a/src/config.h +++ b/src/config.h @@ -55,6 +55,7 @@ #define USER_INTERP_ENABLED 1 #define COLLIDER_DEBUG RTC +#define COLLIDER_DEBUG_DETAILED 1 /* ========================== * * Settings diff --git a/src/phys.c b/src/phys.c index ab592b06..ed91b50a 100644 --- a/src/phys.c +++ b/src/phys.c @@ -228,7 +228,7 @@ struct phys_collision_data_array phys_create_contacts(struct arena *arena, struc } /* TODO: Remove this (debugging) */ -#if COLLIDER_DEBUG +#if COLLIDER_DEBUG && COLLIDER_DEBUG_DETAILED { struct entity *dbg_ent = entity_nil(); struct entity_lookup_entry *dbg_entry = entity_lookup_get(debug_lookup, key); @@ -275,6 +275,8 @@ struct phys_collision_data_array phys_create_contacts(struct arena *arena, struc dbg->closest1 = closest_points_res.p1; } } +#else + (UNUSED)debug_lookup; #endif } } @@ -376,7 +378,6 @@ void phys_prepare_contacts(struct phys_ctx *ctx) } } -#if COLLIDER_DEBUG for (u64 entity_index = 0; entity_index < store->reserved; ++entity_index) { struct entity *dbg_ent = &store->entities[entity_index]; if (!entity_is_valid_and_active(dbg_ent)) continue; @@ -412,7 +413,6 @@ void phys_prepare_contacts(struct phys_ctx *ctx) } } } -#endif } void phys_warm_start_contacts(struct phys_ctx *ctx) diff --git a/src/renderer_d3d11.c b/src/renderer_d3d11.c index bc1d6a7d..c13fccae 100644 --- a/src/renderer_d3d11.c +++ b/src/renderer_d3d11.c @@ -11,7 +11,6 @@ #pragma warning(push, 0) # define UNICODE -# define CINTERFACE # define COBJMACROS # include # include @@ -723,7 +722,6 @@ void renderer_canvas_ensure_texture_cmd(struct renderer_canvas *canvas, struct t canvas->cpu_cmd_store.cmd_last = cmd; } - } /* ========================== * diff --git a/src/user.c b/src/user.c index 2c848dfa..c19acfff 100644 --- a/src/user.c +++ b/src/user.c @@ -1086,14 +1086,86 @@ INTERNAL void user_update(void) #endif } - /* Draw constraint */ + /* Draw contact constraint */ + if (entity_has_prop(ent, ENTITY_PROP_CONTACT_CONSTRAINT)) { + struct phys_contact_constraint *data = &ent->contact_constraint_data; + struct entity *e0 = entity_from_handle(store, data->e0); + struct entity *e1 = entity_from_handle(store, data->e1); + (UNUSED)e0; + (UNUSED)e1; + +#if 1 + /* Draw contact points */ + { + f32 radius = 5; + for (u32 i = 0; i < data->num_points; ++i) { + struct phys_contact_point point = data->points[i]; +#if 0 + struct v2 p0 = xform_mul_v2(e0_xf, contact.point_local_e0); + struct v2 p1 = xform_mul_v2(e1_xf, contact.point_local_e1); + struct v2 point = v2_add(p0, v2_mul(v2_sub(p1, p0), 0.5f)); +#else + struct v2 dbg_pt = point.dbg_pt; +#endif + /* Draw point */ + { + //u32 color = contact.persisted ? RGBA_32_F(1, 1, 0, 0.50) : RGBA_32_F(1, 0, 0, 0.50); + u32 color = RGBA_32_F(1, 1, 0, 0.50); + //struct v2 point = xform_mul_v2(e0_xf, contact.p0_local); + //struct v2 point = contact.p0_initial_world; + draw_solid_circle(G.viewport_canvas, xform_mul_v2(G.world_view, dbg_pt), radius, color, 10); + } + /* Draw normal */ + { + u32 color = COLOR_WHITE; + f32 len = 0.1f; + f32 arrow_thickness = 2; + f32 arrow_height = 5; + struct v2 start = xform_mul_v2(G.world_view, dbg_pt); + struct v2 end = xform_mul_v2(G.world_view, v2_add(dbg_pt, v2_mul(v2_norm(data->normal), len))); + draw_solid_arrow_line(G.viewport_canvas, start, end, arrow_thickness, arrow_height, color); + } +#if 0 + /* Draw contact info */ + { + struct font *disp_font = font_load_async(STR("res/fonts/fixedsys.ttf"), 12.0f); + if (disp_font) { + f32 offset_px = 10; + + struct string fmt = STR( + "e0 index: %F\n" + "e1 index: %F\n" + "id: 0x%F\n" + "impulse (n): %F\n" + "impulse (t): %F\n" + "separation: %F\n" + "normal: (%F, %F)\n" + "num contacts: %F" + ); + struct string text = string_format(temp.arena, fmt, + FMT_UINT(e0->handle.idx), + FMT_UINT(e1->handle.idx), + FMT_HEX(point.id), + FMT_FLOAT_P(point.normal_impulse, 3), + FMT_FLOAT_P(point.tangent_impulse, 3), + FMT_FLOAT_P(point.starting_separation, 6), + FMT_FLOAT_P(data->normal.x, 6), FMT_FLOAT_P(data->normal.y, 6), + FMT_UINT(data->num_points)); + + + draw_text(G.viewport_canvas, disp_font, v2_add(v2_round(xform_mul_v2(G.world_view, dbg_pt)), V2(0, offset_px)), text); + } + } +#endif + } + } + } + + /* Draw collision debug */ #if COLLIDER_DEBUG if (entity_has_prop(ent, ENTITY_PROP_COLLISION_DEBUG)) { struct phys_collision_debug *data = &ent->collision_debug_data; struct collider_collision_points_result collider_res = data->res; - - //struct phys_contact_constraint *data = &entity_from_handle(store, data->contact_constraint_ent)->contact_constraint_data; - //struct phys_contact_constraint *data = &data->contact_constraint_data; struct entity *e0 = entity_from_handle(store, data->e0); struct entity *e1 = entity_from_handle(store, data->e1); struct collider_shape e0_collider = e0->local_collider; @@ -1101,6 +1173,39 @@ INTERNAL void user_update(void) (UNUSED)e0_collider; (UNUSED)e1_collider; + /* Draw closest points */ + { + f32 radius = 4; + u32 color = RGBA_32_F(1, 1, 0, 0.5); + struct v2 a = xform_mul_v2(G.world_view, data->closest0); + struct v2 b = xform_mul_v2(G.world_view, data->closest1); + draw_solid_circle(G.viewport_canvas, a, radius, color, 10); + draw_solid_circle(G.viewport_canvas, b, radius, color, 10); + } + + /* Draw clipping */ + { + f32 thickness = 2; + f32 radius = 4; + u32 color_line = RGBA_32_F(1, 0, 1, 0.5); + u32 color_a = RGBA_32_F(1, 0, 0, 0.5); + u32 color_b = RGBA_32_F(0, 1, 0, 0.5); + { + struct v2 a = xform_mul_v2(G.world_view, collider_res.a0); + struct v2 b = xform_mul_v2(G.world_view, collider_res.b0); + draw_solid_line(G.viewport_canvas, a, b, thickness, color_line); + draw_solid_circle(G.viewport_canvas, a, radius, color_a, 10); + draw_solid_circle(G.viewport_canvas, b, radius, color_b, 10); + } + { + struct v2 a = xform_mul_v2(G.world_view, collider_res.a1); + struct v2 b = xform_mul_v2(G.world_view, collider_res.b1); + draw_solid_line(G.viewport_canvas, a, b, thickness, color_line); + draw_solid_circle(G.viewport_canvas, a, radius, color_a, 10); + draw_solid_circle(G.viewport_canvas, b, radius, color_b, 10); + } + } + #if USER_DRAW_MENKOWSKI struct xform e0_xf = data->xf0; struct xform e1_xf = data->xf1; @@ -1227,120 +1332,6 @@ INTERNAL void user_update(void) } } #endif - -#if 1 - /* Draw contact points */ - { - f32 radius = 5; - for (u32 i = 0; i < data->num_points; ++i) { - struct phys_contact_point point = data->points[i]; -#if 0 - struct v2 p0 = xform_mul_v2(e0_xf, contact.point_local_e0); - struct v2 p1 = xform_mul_v2(e1_xf, contact.point_local_e1); - struct v2 point = v2_add(p0, v2_mul(v2_sub(p1, p0), 0.5f)); -#else - struct v2 dbg_pt = point.dbg_pt; -#endif - /* Draw point */ - { - //u32 color = contact.persisted ? RGBA_32_F(1, 1, 0, 0.50) : RGBA_32_F(1, 0, 0, 0.50); - u32 color = RGBA_32_F(1, 1, 0, 0.50); - //struct v2 point = xform_mul_v2(e0_xf, contact.p0_local); - //struct v2 point = contact.p0_initial_world; - draw_solid_circle(G.viewport_canvas, xform_mul_v2(G.world_view, dbg_pt), radius, color, 10); - } - /* Draw normal */ - { - u32 color = COLOR_WHITE; - f32 len = 0.1f; - f32 arrow_thickness = 2; - f32 arrow_height = 5; - struct v2 start = xform_mul_v2(G.world_view, dbg_pt); - struct v2 end = xform_mul_v2(G.world_view, v2_add(dbg_pt, v2_mul(v2_norm(collider_res.normal), len))); - draw_solid_arrow_line(G.viewport_canvas, start, end, arrow_thickness, arrow_height, color); - } -#if 0 - /* Draw contact info */ - { - struct font *disp_font = font_load_async(STR("res/fonts/fixedsys.ttf"), 12.0f); - if (disp_font) { - f32 offset_px = 10; - -#if 1 - struct string fmt = STR( - "path: %F\n" - "e0 index: %F\n" - "e1 index: %F\n" - "id: 0x%F\n" - "impulse (n): %F\n" - "impulse (t): %F\n" - "separation: %F\n" - "normal: (%F, %F)\n" - "num contacts: %F" - ); - struct string text = string_format(temp.arena, fmt, - FMT_SINT(collider_res.path), - FMT_UINT(e0->handle.idx), - FMT_UINT(e1->handle.idx), - FMT_HEX(point.id), - FMT_FLOAT_P(point.normal_impulse, 3), - FMT_FLOAT_P(point.tangent_impulse, 3), - FMT_FLOAT_P(point.starting_separation, 6), - FMT_FLOAT_P(data->normal.x, 6), FMT_FLOAT_P(data->normal.y, 6), - FMT_UINT(data->num_points)); - - - draw_text(G.viewport_canvas, disp_font, v2_add(v2_round(xform_mul_v2(G.world_view, dbg_pt)), V2(0, offset_px)), text); -#else - struct string fmt = STR( - "e0 index: %F\n" - "e1 index: %F\n" - ); - struct string text = string_format(temp.arena, fmt, - FMT_UINT(e0->handle.idx), - FMT_UINT(e1->handle.idx)); - - - draw_text(G.viewport_canvas, disp_font, v2_add(v2_round(xform_mul_v2(G.world_view, point)), V2(0, offset_px)), text); -#endif - } - } -#endif - } - } - - /* Draw clipping */ - { - f32 thickness = 2; - f32 radius = 4; - u32 color_line = RGBA_32_F(1, 0, 1, 0.5); - u32 color_a = RGBA_32_F(1, 0, 0, 0.5); - u32 color_b = RGBA_32_F(0, 1, 0, 0.5); - { - struct v2 a = xform_mul_v2(G.world_view, collider_res.a0); - struct v2 b = xform_mul_v2(G.world_view, collider_res.b0); - draw_solid_line(G.viewport_canvas, a, b, thickness, color_line); - draw_solid_circle(G.viewport_canvas, a, radius, color_a, 10); - draw_solid_circle(G.viewport_canvas, b, radius, color_b, 10); - } - { - struct v2 a = xform_mul_v2(G.world_view, collider_res.a1); - struct v2 b = xform_mul_v2(G.world_view, collider_res.b1); - draw_solid_line(G.viewport_canvas, a, b, thickness, color_line); - draw_solid_circle(G.viewport_canvas, a, radius, color_a, 10); - draw_solid_circle(G.viewport_canvas, b, radius, color_b, 10); - } - } - - /* Draw closest points */ - { - f32 radius = 4; - u32 color = RGBA_32_F(1, 1, 0, 0.5); - struct v2 a = xform_mul_v2(G.world_view, data->closest0); - struct v2 b = xform_mul_v2(G.world_view, data->closest1); - draw_solid_circle(G.viewport_canvas, a, radius, color, 10); - draw_solid_circle(G.viewport_canvas, b, radius, color, 10); - } #endif } #endif