summaryrefslogtreecommitdiff
path: root/libphysics/tick.c
diff options
context:
space:
mode:
authoresquizo <esquizo+noreply@esquizo.net>2026-05-17 12:02:56 -0300
committeresquizo <esquizo+noreply@esquizo.net>2026-05-17 12:02:56 -0300
commit97702f11ea016ca2e395f71f03c3fc3a2ee929ca (patch)
tree20380f895ee422c48b970c7da5b921e046e35da4 /libphysics/tick.c
parent5c6b3c19172948cf2e1800a9333cfcd858ee829c (diff)
adicionado libphysics
Diffstat (limited to 'libphysics/tick.c')
-rw-r--r--libphysics/tick.c138
1 files changed, 138 insertions, 0 deletions
diff --git a/libphysics/tick.c b/libphysics/tick.c
new file mode 100644
index 0000000..c6399ab
--- /dev/null
+++ b/libphysics/tick.c
@@ -0,0 +1,138 @@
+#include <vecmath.h>
+#include <physics.h>
+#include <stdlib.h>
+
+#include "dat.h"
+
+#define PHX_TICK_TIME (1.0 / 480.0)
+
+static void tick(void);
+static void mapcollision(Body *);
+static void bodycollision(Body *);
+
+#define TILE_SIZE 16
+
+void
+phxtick(float delta)
+{
+ static float time;
+
+ time += delta;
+ if(time >= PHX_TICK_TIME > 0) {
+ while(time >= PHX_TICK_TIME) {
+ tick();
+ time -= PHX_TICK_TIME;
+ }
+ for(int i = 0; i < phxbodypoolsize; i++) {
+ Body *b = phxbodypool + i;
+ if(!b->active)
+ continue;
+
+ b->accel[0] = 0.0;
+ b->accel[1] = 0.0;
+ }
+ }
+}
+
+void
+tick(void)
+{
+ for(int i = 0; i < phxbodypoolsize; i++) {
+ Body *b = phxbodypool + i;
+ if(!b->active)
+ continue;
+
+ vec2_add_scaled(b->vel, b->vel, b->accel, PHX_TICK_TIME);
+ }
+
+ for(int i = 0; i < phxbodypoolsize; i++) {
+ Body *b = phxbodypool + i;
+ if(!b->active)
+ continue;
+
+ mapcollision(b);
+ bodycollision(b);
+ }
+
+ for(int i = 0; i < phxbodypoolsize; i++) {
+ Body *b = phxbodypool + i;
+ if(!b->active)
+ continue;
+
+ vec2_add_scaled(b->pos, b->pos, b->vel, PHX_TICK_TIME);
+ }
+}
+
+void
+mapcollision(Body *a)
+{
+ int minx, miny, maxx, maxy;
+
+ minx = ((int)(a->pos[0] - a->size[0]) / TILE_SIZE) * TILE_SIZE;
+ maxx = ((int)(a->pos[0] + a->size[0]) / TILE_SIZE) * TILE_SIZE;
+ miny = ((int)(a->pos[1] - a->size[1]) / TILE_SIZE) * TILE_SIZE;
+ maxy = ((int)(a->pos[1] + a->size[1]) / TILE_SIZE) * TILE_SIZE;
+
+ for(int y = miny; y <= maxy + TILE_SIZE; y += TILE_SIZE)
+ for(int x = minx; x <= maxx + TILE_SIZE; x += TILE_SIZE) {
+ int tilex = x / (2 * TILE_SIZE);
+ int tiley = y / (2 * TILE_SIZE);
+
+ if(tilex < 0 || tilex >= phxmapwidth)
+ continue;
+ if(tiley < 0 || tiley >= phxmapheight)
+ continue;
+
+ if(!phxmapbuffer[tilex + tiley * phxmapwidth])
+ continue;
+
+ Body b = {
+ .pos = {
+ tilex * TILE_SIZE * 2.0,
+ tiley * TILE_SIZE * 2.0,
+ },
+ .size = { TILE_SIZE, TILE_SIZE },
+ };
+
+ if(phxaabbcheck(a, &b)) {
+ float p[2], n[2];
+ phxaabbresolv(a, &b, p, n);
+
+ vec2_sub(a->pos, a->pos, p);
+
+ if(p[0] != 0.0) {
+ a->vel[0] = 0;
+ } else {
+ a->vel[1] = 0;
+ }
+ }
+ }
+}
+
+void
+bodycollision(Body *a)
+{
+ CollisionEvent event;
+ for(Body *b = a + 1; b < (a + phxbodypoolsize); b++) {
+ if(!b->active)
+ continue;
+
+ if(phxaabbcheck(a, b)) {
+ float p[2], n[2], rvel[2], j;
+ phxaabbresolv(a, b, p, n);
+
+ vec2_sub(rvel, a->vel, b->vel);
+ j = vec2_dot(rvel, n);
+
+ vec2_sub_scaled(a->vel, a->vel, n, 0.5);
+ vec2_sub_scaled(b->vel, b->vel, n, -0.5);
+
+ vec2_sub_scaled(a->pos, a->pos, p, 0.5);
+ vec2_sub_scaled(b->pos, b->pos, p, -0.5);
+
+ event.body1 = a;
+ event.body2 = b;
+ phxenqevent(&event);
+ }
+ }
+}