store and calculate mass from unscaled mass instead of density
This commit is contained in:
parent
c461956fb0
commit
c4dd372041
@ -17,7 +17,7 @@ READONLY struct entity _g_entity_nil = {
|
|||||||
.cached_global_xform = XFORM_IDENT_NOCAST,
|
.cached_global_xform = XFORM_IDENT_NOCAST,
|
||||||
.cached_global_xform_dirty = false,
|
.cached_global_xform_dirty = false,
|
||||||
.verlet_xform = XFORM_IDENT_NOCAST,
|
.verlet_xform = XFORM_IDENT_NOCAST,
|
||||||
.density = 1,
|
.mass_unscaled = 1,
|
||||||
.sprite_local_xform = XFORM_IDENT_NOCAST,
|
.sprite_local_xform = XFORM_IDENT_NOCAST,
|
||||||
.sprite_tint = COLOR_WHITE
|
.sprite_tint = COLOR_WHITE
|
||||||
};
|
};
|
||||||
@ -28,7 +28,7 @@ GLOBAL READONLY struct entity g_entity_default = {
|
|||||||
.cached_global_xform = XFORM_IDENT_NOCAST,
|
.cached_global_xform = XFORM_IDENT_NOCAST,
|
||||||
.cached_global_xform_dirty = true,
|
.cached_global_xform_dirty = true,
|
||||||
.verlet_xform = XFORM_IDENT_NOCAST,
|
.verlet_xform = XFORM_IDENT_NOCAST,
|
||||||
.density = 1,
|
.mass_unscaled = 1,
|
||||||
.sprite_local_xform = XFORM_IDENT_NOCAST,
|
.sprite_local_xform = XFORM_IDENT_NOCAST,
|
||||||
.sprite_tint = COLOR_WHITE
|
.sprite_tint = COLOR_WHITE
|
||||||
};
|
};
|
||||||
|
|||||||
@ -101,7 +101,7 @@ struct entity {
|
|||||||
|
|
||||||
/* ENTITY_PROP_PHYSICAL */
|
/* ENTITY_PROP_PHYSICAL */
|
||||||
|
|
||||||
f32 density;
|
f32 mass_unscaled; /* Mass of entity in kg before any transformations */
|
||||||
f32 ground_friction;
|
f32 ground_friction;
|
||||||
|
|
||||||
/* Xform of the entity from the previous frame (used to calculate velocity) */
|
/* Xform of the entity from the previous frame (used to calculate velocity) */
|
||||||
|
|||||||
30
src/game.c
30
src/game.c
@ -124,14 +124,14 @@ INTERNAL void spawn_test_entities(void)
|
|||||||
e->sprite_span_name = STR("idle.two_handed");
|
e->sprite_span_name = STR("idle.two_handed");
|
||||||
|
|
||||||
entity_enable_prop(e, ENTITY_PROP_PLAYER_CONTROLLED);
|
entity_enable_prop(e, ENTITY_PROP_PLAYER_CONTROLLED);
|
||||||
e->control_move_force = 50;
|
e->control_move_force = 4500;
|
||||||
e->control.focus = V2(0, -1);
|
e->control.focus = V2(0, -1);
|
||||||
e->ground_friction = 12;
|
|
||||||
e->density = 1.0;
|
|
||||||
|
|
||||||
player_ent = e;
|
|
||||||
|
|
||||||
entity_enable_prop(e, ENTITY_PROP_PHYSICAL);
|
entity_enable_prop(e, ENTITY_PROP_PHYSICAL);
|
||||||
|
e->mass_unscaled = 70;
|
||||||
|
e->ground_friction = 1000;
|
||||||
|
|
||||||
|
player_ent = e;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Weapon */
|
/* Weapon */
|
||||||
@ -156,6 +156,18 @@ INTERNAL void spawn_test_entities(void)
|
|||||||
player_ent->equipped = e->handle;
|
player_ent->equipped = e->handle;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Box */
|
||||||
|
{
|
||||||
|
struct v2 pos = V2(1, -1);
|
||||||
|
struct v2 size = V2(1, 1);
|
||||||
|
f32 rot = 0;
|
||||||
|
struct entity *e = entity_alloc(root);
|
||||||
|
|
||||||
|
e->sprite = sprite_tag_from_path(STR("res/graphics/box.ase"));
|
||||||
|
|
||||||
|
entity_set_xform(e, XFORM_TRS(.t = pos, .s = size, .r = rot));
|
||||||
|
}
|
||||||
|
|
||||||
/* Camera */
|
/* Camera */
|
||||||
{
|
{
|
||||||
struct entity *e = entity_alloc(root);
|
struct entity *e = entity_alloc(root);
|
||||||
@ -512,7 +524,8 @@ INTERNAL void game_update(struct game_cmd_array game_cmds)
|
|||||||
bullet->bullet_src = ent->handle;
|
bullet->bullet_src = ent->handle;
|
||||||
bullet->bullet_src_pos = rel_pos;
|
bullet->bullet_src_pos = rel_pos;
|
||||||
bullet->bullet_src_dir = rel_dir;
|
bullet->bullet_src_dir = rel_dir;
|
||||||
bullet->bullet_impulse = 5;
|
bullet->bullet_impulse = 0.25;
|
||||||
|
bullet->mass_unscaled = 0.04;
|
||||||
|
|
||||||
entity_enable_prop(bullet, ENTITY_PROP_BULLET);
|
entity_enable_prop(bullet, ENTITY_PROP_BULLET);
|
||||||
}
|
}
|
||||||
@ -581,8 +594,8 @@ INTERNAL void game_update(struct game_cmd_array game_cmds)
|
|||||||
struct entity *ent = &store->entities[entity_index];
|
struct entity *ent = &store->entities[entity_index];
|
||||||
if (!(ent->valid && entity_has_prop(ent, ENTITY_PROP_ACTIVE))) continue;
|
if (!(ent->valid && entity_has_prop(ent, ENTITY_PROP_ACTIVE))) continue;
|
||||||
if (entity_has_prop(ent, ENTITY_PROP_PHYSICAL)) {
|
if (entity_has_prop(ent, ENTITY_PROP_PHYSICAL)) {
|
||||||
f32 density = ent->density;
|
struct xform xf = entity_get_xform(ent);
|
||||||
f32 mass = density; /* TODO: Real mass calculation */
|
f32 mass = ent->mass_unscaled * xform_get_determinant(xf);
|
||||||
|
|
||||||
struct v2 acceleration = V2(0, 0);
|
struct v2 acceleration = V2(0, 0);
|
||||||
|
|
||||||
@ -605,7 +618,6 @@ INTERNAL void game_update(struct game_cmd_array game_cmds)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Verlet integration */
|
/* Verlet integration */
|
||||||
struct xform xf = entity_get_xform(ent);
|
|
||||||
struct v2 tick_velocity = v2_sub(xf.og, ent->verlet_xform.og);
|
struct v2 tick_velocity = v2_sub(xf.og, ent->verlet_xform.og);
|
||||||
ent->verlet_xform = xf;
|
ent->verlet_xform = xf;
|
||||||
xf.og = v2_add(xf.og, v2_add(tick_velocity, v2_mul(acceleration, dt)));
|
xf.og = v2_add(xf.og, v2_add(tick_velocity, v2_mul(acceleration, dt)));
|
||||||
|
|||||||
20
src/math.h
20
src/math.h
@ -907,6 +907,16 @@ INLINE struct v2 xform_invert_mul_v2(struct xform xf, struct v2 v)
|
|||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
INLINE struct quad xform_mul_quad(struct xform xf, struct quad quad)
|
||||||
|
{
|
||||||
|
return (struct quad) {
|
||||||
|
xform_mul_v2(xf, quad.p1),
|
||||||
|
xform_mul_v2(xf, quad.p2),
|
||||||
|
xform_mul_v2(xf, quad.p3),
|
||||||
|
xform_mul_v2(xf, quad.p4)
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
INLINE f32 xform_get_determinant(struct xform xf)
|
INLINE f32 xform_get_determinant(struct xform xf)
|
||||||
{
|
{
|
||||||
return v2_wedge(xf.bx, xf.by);
|
return v2_wedge(xf.bx, xf.by);
|
||||||
@ -1027,16 +1037,6 @@ INLINE struct quad quad_scale(struct quad q, f32 s)
|
|||||||
return q;
|
return q;
|
||||||
}
|
}
|
||||||
|
|
||||||
INLINE struct quad quad_mul_xform(struct quad quad, struct xform m)
|
|
||||||
{
|
|
||||||
return (struct quad) {
|
|
||||||
xform_mul_v2(m, quad.p1),
|
|
||||||
xform_mul_v2(m, quad.p2),
|
|
||||||
xform_mul_v2(m, quad.p3),
|
|
||||||
xform_mul_v2(m, quad.p4)
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
INLINE struct quad quad_round(struct quad quad)
|
INLINE struct quad quad_round(struct quad quad)
|
||||||
{
|
{
|
||||||
return (struct quad) {
|
return (struct quad) {
|
||||||
|
|||||||
14
src/user.c
14
src/user.c
@ -367,7 +367,7 @@ INTERNAL void debug_draw_xform(struct xform xf)
|
|||||||
y_ray = v2_mul(y_ray, ray_scale);
|
y_ray = v2_mul(y_ray, ray_scale);
|
||||||
|
|
||||||
struct quad quad = quad_from_rect(RECT(0, 0, 1, -1));
|
struct quad quad = quad_from_rect(RECT(0, 0, 1, -1));
|
||||||
quad = quad_mul_xform(quad_scale(quad, 0.075f), xf);
|
quad = xform_mul_quad(xf, quad_scale(quad, 0.075f));
|
||||||
|
|
||||||
draw_solid_arrow_ray(G.viewport_canvas, pos, x_ray, thickness, arrowhead_len, color_x);
|
draw_solid_arrow_ray(G.viewport_canvas, pos, x_ray, thickness, arrowhead_len, color_x);
|
||||||
draw_solid_arrow_ray(G.viewport_canvas, pos, y_ray, thickness, arrowhead_len, color_y);
|
draw_solid_arrow_ray(G.viewport_canvas, pos, y_ray, thickness, arrowhead_len, color_y);
|
||||||
@ -842,7 +842,7 @@ INTERNAL void user_update(void)
|
|||||||
/* TODO: Fade in placeholder if texture isn't loaded */
|
/* TODO: Fade in placeholder if texture isn't loaded */
|
||||||
if (sheet->loaded) {
|
if (sheet->loaded) {
|
||||||
struct sprite_sheet_frame frame = sprite_sheet_get_frame(sheet, ent->animation_frame);
|
struct sprite_sheet_frame frame = sprite_sheet_get_frame(sheet, ent->animation_frame);
|
||||||
struct quad quad = quad_mul_xform(QUAD_UNIT_SQUARE_CENTERED, sprite_xform);
|
struct quad quad = xform_mul_quad(sprite_xform, QUAD_UNIT_SQUARE_CENTERED);
|
||||||
struct draw_sprite_params params = DRAW_SPRITE_PARAMS(.sprite = sprite, .tint = ent->sprite_tint, .clip = frame.clip);
|
struct draw_sprite_params params = DRAW_SPRITE_PARAMS(.sprite = sprite, .tint = ent->sprite_tint, .clip = frame.clip);
|
||||||
draw_sprite_quad(G.world_canvas, params, quad);
|
draw_sprite_quad(G.world_canvas, params, quad);
|
||||||
}
|
}
|
||||||
@ -924,8 +924,8 @@ INTERNAL void user_update(void)
|
|||||||
|
|
||||||
if (!slice.has_ray) {
|
if (!slice.has_ray) {
|
||||||
struct quad quad = quad_from_rect(slice.rect);
|
struct quad quad = quad_from_rect(slice.rect);
|
||||||
quad = quad_mul_xform(quad, sprite_xform);
|
quad = xform_mul_quad(sprite_xform, quad);
|
||||||
quad = quad_mul_xform(quad, G.world_view);
|
quad = xform_mul_quad(G.world_view, quad);
|
||||||
draw_solid_quad_line(G.viewport_canvas, quad, 2, RGBA_32_F(1, 0, 0.5, 1));
|
draw_solid_quad_line(G.viewport_canvas, quad, 2, RGBA_32_F(1, 0, 0.5, 1));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -959,8 +959,8 @@ INTERNAL void user_update(void)
|
|||||||
|
|
||||||
|
|
||||||
struct xform quad_xf = xform_mul(xf, ent->camera_quad_xform);
|
struct xform quad_xf = xform_mul(xf, ent->camera_quad_xform);
|
||||||
struct quad quad = quad_mul_xform(QUAD_UNIT_SQUARE_CENTERED, quad_xf);
|
struct quad quad = xform_mul_quad(quad_xf, QUAD_UNIT_SQUARE_CENTERED);
|
||||||
quad = quad_mul_xform(quad, G.world_view);
|
quad = xform_mul_quad(G.world_view, quad);
|
||||||
|
|
||||||
draw_solid_quad_line(G.viewport_canvas, quad, thickness, color);
|
draw_solid_quad_line(G.viewport_canvas, quad, thickness, color);
|
||||||
}
|
}
|
||||||
@ -979,7 +979,7 @@ INTERNAL void user_update(void)
|
|||||||
|
|
||||||
struct v2 size = V2(t->width, t->height);
|
struct v2 size = V2(t->width, t->height);
|
||||||
struct xform xf = XFORM_TRS(.t = crosshair_pos, .s = size);
|
struct xform xf = XFORM_TRS(.t = crosshair_pos, .s = size);
|
||||||
struct quad quad = quad_mul_xform(QUAD_UNIT_SQUARE_CENTERED, xf);
|
struct quad quad = xform_mul_quad(xf, QUAD_UNIT_SQUARE_CENTERED);
|
||||||
draw_sprite_quad(G.viewport_canvas, DRAW_SPRITE_PARAMS(.sprite = crosshair_tag, .tint = tint), quad);
|
draw_sprite_quad(G.viewport_canvas, DRAW_SPRITE_PARAMS(.sprite = crosshair_tag, .tint = tint), quad);
|
||||||
|
|
||||||
struct rect cursor_clip = RECT_FROM_V2(G.viewport_screen_offset, G.viewport_size);
|
struct rect cursor_clip = RECT_FROM_V2(G.viewport_screen_offset, G.viewport_size);
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user