1
1
Fork 0
Browse Source

mega bugfix

thread-physics
alistair 4 years ago
parent
commit
9a31a5a9d1
  1. 6
      controlscheme.h
  2. 21
      draw.c
  3. 21
      draw.h
  4. 18
      environment.c
  5. 27
      environment.h
  6. 150
      game.c
  7. 196
      game.h
  8. 6
      garbo.h
  9. 2
      vect.h

6
controlscheme.h

@ -1,5 +1,8 @@ @@ -1,5 +1,8 @@
#include <SDL2/SDL.h>
#ifndef CRTL_H
#define CRTL_H
enum Game_Interaction {
PLAYER_UP,
PLAYER_DOWN,
@ -20,6 +23,5 @@ extern struct InputMap input_map; @@ -20,6 +23,5 @@ extern struct InputMap input_map;
void get_input_map(void);
#endif

21
draw.c

@ -1,6 +1,4 @@ @@ -1,6 +1,4 @@
#include "draw.h"
#include "vect.h"
#include "environment.h"
Vect viewport_pos;
int width, height;
@ -63,9 +61,10 @@ void draw_player(SDL_Renderer * ren, int x, int y, bool red) { @@ -63,9 +61,10 @@ void draw_player(SDL_Renderer * ren, int x, int y, bool red) {
if (red) {
SDL_SetRenderDrawColor(ren, 255, 0, 0, 255);
} else {
SDL_SetRenderDrawColor(ren, 120, 85, 188, 255);
}
struct colour c = get_scene_at(viewport_pos, level).colours.bg;
SDL_SetRenderDrawColor(ren, c.r, c.g, c.b, 255);
}
SDL_RenderDrawRect(ren, &player_rect);
SDL_RenderFillRect(ren, &player_rect);
@ -401,32 +400,32 @@ void redraw_buffer(SDL_Renderer * ren) { @@ -401,32 +400,32 @@ void redraw_buffer(SDL_Renderer * ren) {
struct environment scene = get_scene_at(viewport_pos, level);
draw_environment(ren, &scene);
for (int i=0; i<world.size; i++) {
for (int i=0; i < world.items.size; i++) {
world_thing thing;
thing = world.things[i];
thing = world.get(i);
switch (thing.kind) {
case PLAYER:
draw_player(ren, (*thing.player).physics->position.x, (*thing.player).physics->position.y, thing.player->colliding);
draw_collision_poly(ren, thing.player->physics);
draw_forces(ren, thing.player->physics);
break;
continue;
case STATIC_WALL_W:
draw_wall(ren, thing.wall);
draw_collision_poly(ren, thing.wall->physics);
break;
continue;
case FLOOR:
for (int i = 0; i < thing.floor->numPolys; i++) {
draw_floor(ren, &thing.floor->polys[i], true);
draw_collision_poly(ren, thing.floor->polys[i].physics);
}
break;
continue;
case CEILING:
for (int i = 0; i < thing.floor->numPolys; i++) {
draw_floor(ren, &thing.floor->polys[i], false);
draw_collision_poly(ren, thing.floor->polys[i].physics);
}
break;
continue;
case ROOM_W:
for (int i = 0; i < thing.room->ceil.numItems; i++) {
draw_collision_poly(ren, thing.room->ceil.items[i]);
@ -434,6 +433,8 @@ void redraw_buffer(SDL_Renderer * ren) { @@ -434,6 +433,8 @@ void redraw_buffer(SDL_Renderer * ren) {
for (int i = 0; i < thing.room->floor.numItems; i++) {
draw_collision_poly(ren, thing.room->floor.items[i]);
}
default:
continue;
}
}

21
draw.h

@ -1,16 +1,17 @@ @@ -1,16 +1,17 @@
#include <SDL2/SDL.h>
#include <SDL2/SDL_image.h>
#ifndef _DEFDRAW
#define _DEFDRAW
#define SHOWCOLLISION 1
#define SHOWFORCES 1
#include <SDL2/SDL.h>
#include <SDL2/SDL_image.h>
#include "garbo.h"
#include "game.h"
#include "c-colours/colours.h"
#include "vect.h"
#include "game.h"
#include "environment.h"
#define SHOWCOLLISION 0
#define SHOWFORCES 0
typedef enum {
PLAYER
@ -34,12 +35,6 @@ extern Vect viewport_pos; @@ -34,12 +35,6 @@ extern Vect viewport_pos;
extern int width, height;
struct colour_pallete {
struct colour bg;
struct colour fg1;
struct colour fg2;
struct colour fg3;
};
#endif

18
environment.c

@ -1,10 +1,26 @@ @@ -1,10 +1,26 @@
#include "environment.h"
#include "draw.h"
double linear_interpolate(double a0, double a1, double w) {
return (1.0f - w) * a0 + w * a1;
}
int destroy_environment(struct environment *e) {
/*Vect position;*/
/*ArrayList ceil; // doubles*/
/*ArrayList floor; // doubles*/
/*ArrayList bg1; // doubles*/
/*ArrayList bg2; // doubles*/
/*struct colour_pallete colours;*/
/*struct physics_collection physics;*/
arlst_destroy(&e->ceil);
arlst_destroy(&e->floor);
arlst_destroy(&e->bg1);
arlst_destroy(&e->bg2);
return 0;
}
double perlin(Vect coordinate) {
Vect a = coordinate;
Vect b = coordinate;

27
environment.h

@ -1,23 +1,10 @@ @@ -1,23 +1,10 @@
#include "c-colours/colours.h"
#include "datastructures/datatypes.h"
#include "vect.h"
#include "draw.h"
enum {
E_ROOM_WIDTH = 10000,
E_ROOM_RES = 500,
E_ROOM_TILES = E_ROOM_WIDTH / E_ROOM_RES,
};
#ifndef ENVIRO_H
#define ENVIRO_H
struct environment {
int level;
Vect position;
ArrayList ceil;
ArrayList floor;
ArrayList bg1;
ArrayList bg2;
struct colour_pallete colours;
struct physics_collection physics;
};
#include "vect.h"
#include "types.h"
struct environment get_scene_at(Vect coordinate, int seed);
int destroy_environment(struct environment *e);
#endif

150
game.c

@ -1,9 +1,10 @@ @@ -1,9 +1,10 @@
#include "game.h"
#include "environment.h"
#define FLOOR_THICKNESS 200
#define BREAKPOINT *(int *)0 = 1;
#define MAX_ROPE_GRAB_LEN 800
#define BREAKPOINT *(int *)0 = 1;
GlobWorld world;
player_st *glob_player;
@ -80,6 +81,11 @@ void default_motor_curve(Motor *motor) { @@ -80,6 +81,11 @@ void default_motor_curve(Motor *motor) {
return;
}
world_thing world_getter(int i) {
world_thing *item = arlst_get(&world.items, i);
return *item;
}
FloorPoly* generate_floor_simple(int num_polys, bool extend_down, int st_height) {
FloorPoly *floor = calloc(num_polys, sizeof(FloorPoly));
@ -504,9 +510,25 @@ bool check_collision(Body *one, Body *two, Vect *translation) { @@ -504,9 +510,25 @@ bool check_collision(Body *one, Body *two, Vect *translation) {
}
}
void destroy_physics_body(Body *b) {
// collisions
Vect *collision_poly;
Vect *collision_shape;
int collision_poly_size;
int collision_shape_size;
void (*updateCollisionPoly)(struct BodyStruct *);
// applying forces
int num_strings;
int max_strings;
String *strings;
}
void destroy_physics_collection(struct physics_collection *s) {
for (int i = 0; i < s->numItems; i++) {
free(s->items[i]);
if (s->items[i]) {
//free(s->items[i]);
}
}
free(s->items);
@ -519,19 +541,33 @@ void next_level() { @@ -519,19 +541,33 @@ void next_level() {
v.y = 0;
player.physics->vel = v;
player.physics->acc = v;
player.physics->position.x = 0;
player.physics->position.y = 0;
player.physics->position = v;
player.physics->next_position = v;
// destroy_physics_collection(&world.uniques_index[ROOM_W]->room->ceil);
// destroy_physics_collection(&world.uniques_index[ROOM_W]->room->floor);
int d = -1;
for (int i = 0; i < world.items.size; i++) {
if (world.get(i).kind == ROOM_W) {
d = i;
break;
}
}
// still need to free world object
if (d != -1) {
world_thing *w = arlst_del(&world.items, d);
}
destroy_physics_collection(&world.uniques_index[ROOM_W]->room->ceil);
destroy_physics_collection(&world.uniques_index[ROOM_W]->room->floor);
destroy_environment(&world.uniques_index[ROOM_W]->room->env);
level++;
get_floor_ceiling();
v = world.uniques_index[ROOM_W]->room->ceil.items[2]->collision_poly[0];
v.y -= 30;
player.physics->position = v;
player.physics->next_position = v;
}
int get_floor_ceiling() {
@ -613,6 +649,7 @@ int get_floor_ceiling() { @@ -613,6 +649,7 @@ int get_floor_ceiling() {
room_world.room = room;
add_to_world(room_world);
world.uniques_index[ROOM_W]->room->env = e;
return 0;
}
@ -884,37 +921,37 @@ int process_collisions(Body *thing, Vect *trans) { @@ -884,37 +921,37 @@ int process_collisions(Body *thing, Vect *trans) {
int num_cols = 0;
int num = 0;
for (int k = 0; k < world.size; k++) {
if (world.things[k].kind == STATIC_WALL_W
&& world.things[k].wall->physics->uid != thing->uid) {
if ((world.things[k].wall->physics->position.x - viewport_pos.x) > (width * 2)
|| world.things[k].wall->physics->position.x - viewport_pos.x < 0) {
for (int k = 0; k < world.items.size; k++) {
if (world.get(k).kind == STATIC_WALL_W
&& world.get(k).wall->physics->uid != thing->uid) {
if ((world.get(k).wall->physics->position.x - viewport_pos.x) > (width * 2)
|| world.get(k).wall->physics->position.x - viewport_pos.x < 0) {
continue;
} else {
num++;
}
if (check_collision(world.things[k].wall->physics, thing, &temptrans)) {
if (check_collision(world.get(k).wall->physics, thing, &temptrans)) {
num++;
thing->colliding = true;
translation = vect_add(translation, temptrans);
}
} else if (world.things[k].kind == FLOOR || world.things[k].kind == CEILING) {
for (int i = 0; i < world.things[k].floor->numPolys; i++) {
if ((world.things[k].floor->polys[i].physics->position.x - viewport_pos.x) > (2 *width)
|| (world.things[k].floor->polys[i].physics->position.x - viewport_pos.x) < -width) {
} else if (world.get(k).kind == FLOOR || world.get(k).kind == CEILING) {
for (int i = 0; i < world.get(k).floor->numPolys; i++) {
if ((world.get(k).floor->polys[i].physics->position.x - viewport_pos.x) > (2 *width)
|| (world.get(k).floor->polys[i].physics->position.x - viewport_pos.x) < -width) {
continue;
} else {
num++;
}
if (check_collision(world.things[k].floor->polys[i].physics, thing, &temptrans)) {
if (check_collision(world.get(k).floor->polys[i].physics, thing, &temptrans)) {
num_cols++;
thing->colliding = true;
translation = vect_add(translation, temptrans);
}
}
} else if (world.things[k].kind == ROOM_W) {
for (int i = 0; i < world.things[k].room->floor.numItems; i++) {
Body *s = world.things[k].room->floor.items[i];
} else if (world.get(k).kind == ROOM_W) {
for (int i = 0; i < world.get(k).room->floor.numItems; i++) {
Body *s = world.get(k).room->floor.items[i];
if (s->position.x + E_ROOM_RES < viewport_pos.x) {
continue;
} else if (s->position.x > viewport_pos.x + width) {
@ -930,8 +967,8 @@ int process_collisions(Body *thing, Vect *trans) { @@ -930,8 +967,8 @@ int process_collisions(Body *thing, Vect *trans) {
}
}
for (int i = 0; i < world.things[k].room->ceil.numItems; i++) {
Body *s = world.things[k].room->ceil.items[i];
for (int i = 0; i < world.get(k).room->ceil.numItems; i++) {
Body *s = world.get(k).room->ceil.items[i];
if (s->position.x + E_ROOM_RES < viewport_pos.x) {
continue;
} else if (s->position.x > viewport_pos.x + width) {
@ -1249,32 +1286,35 @@ void get_projectile(Projectile** proj) { @@ -1249,32 +1286,35 @@ void get_projectile(Projectile** proj) {
void advance_things(void) {
int numcols;
Vect translation;
for (int i = 0; i < world.size; i++) {
switch (world.things[i].kind) {
for (int i = 0; i < world.items.size; i++) {
switch (world.get(i).kind) {
case PLAYER_W :
advance_thing((world.things[i].player->physics));
break;
advance_thing((world.get(i).player->physics));
continue;
case STATIC_WALL_W:
advance_thing(world.things[i].wall->physics);
break;
advance_thing(world.get(i).wall->physics);
continue;
case FLOOR:
break;
/*for (int k = 0; k < world.things[i].floor->numPolys; k++) {*/
/*advance_thing(world.things[i].floor->polys[k].physics);*/
continue;
/*for (int k = 0; k < world.get(i).floor->numPolys; k++) {*/
/*advance_thing(world.get(i).floor->polys[k].physics);*/
/*}*/
/*break;*/
case CEILING:
break;
/*for (int k = 0; k < world.things[i].floor->numPolys; k++) {*/
/*advance_thing(world.things[i].floor->polys[k].physics);*/
continue;
/*for (int k = 0; k < world.get(i).floor->numPolys; k++) {*/
/*advance_thing(world.get(i).floor->polys[k].physics);*/
/*}*/
/*break;*/
case PROJECTILE:
if ((numcols = process_collisions(world.things[i].projectile->physics,
if ((numcols = process_collisions(world.get(i).projectile->physics,
&translation))) {
world.things[i].projectile->on_collision(world.things[i].projectile);
world.get(i).projectile->on_collision(world.get(i).projectile);
}
world.things[i].projectile->on_step(world.things[i].projectile);
world.get(i).projectile->on_step(world.get(i).projectile);
continue;
default:
continue;
}
}
}
@ -1293,20 +1333,18 @@ bool unique_world_kind(enum world_thing_kind k) { @@ -1293,20 +1333,18 @@ bool unique_world_kind(enum world_thing_kind k) {
// grow array of world things if needed
void add_to_world(world_thing thing) {
if (world.size == world.capacity) {
logwrite(INFO, "Increased world size.");
world.things = realloc(world.things, sizeof(world_thing) * (world.size*=2));
// man dodgy and unfinished
if (unique_world_kind(thing.kind)) {
}
}
thing.nid = world.items.size;
world_thing *t = calloc(1, sizeof(world_thing));
memcpy(t, &thing, sizeof(world_thing));
thing.nid = world.size;
memcpy(world.things + world.size, &thing, sizeof(world_thing));
world.uniques_index[thing.kind] = world.things + world.size;
arlst_add(&world.items, t);
if (unique_world_kind(thing.kind)) {
void *ref = arlst_get(&world.items, world.items.size - 1);
world.uniques_index[thing.kind] = ref;
}
world.size++;
//printf("Added to world: %d\n", thing.kind);
printf("Added to world: %d\n", thing.kind);
}
/* Send a projectile from body in direction dir (in degrees) with the force of
@ -1355,11 +1393,9 @@ void get_room(void) { @@ -1355,11 +1393,9 @@ void get_room(void) {
GlobWorld create_world() {
GlobWorld c;
c.things = malloc(sizeof(world_thing) * 100);
memset(c.things, 0, sizeof(world_thing) * 100);
c.capacity = 100;
c.size = 0;
c.items = new_arlst(100);
c.uniques_index = calloc(10, sizeof(world_thing*));
c.get = world_getter; // gross
return c;
}

196
game.h

@ -1,200 +1,14 @@ @@ -1,200 +1,14 @@
#include <SDL2/SDL.h>
#include <SDL2/SDL_image.h>
#include <stdbool.h>
#include <stdint.h>
#include <math.h>
#include <time.h>
#ifndef _DEFGAME
#define _DEFGAME
#include "environment.h"
#include "datastructures/datatypes.h"
#include "vect.h"
#include "garbo.h"
#include "draw.h"
#include "controlscheme.h"
enum motors {
M_GRAVITY = 0,
M_FRICTION = 1,
M_PLAYER_WALK = 2,
M_WINCH = 3
};
enum world_thing_kind {
PLAYER_W = 0,
FLOOR = 1,
CEILING = 2,
ROOM_W,
STATIC_WALL_W,
PROJECTILE
};
// used to exert a force on an object
typedef struct motorstruct {
double x; // positive is right
double y; // positive is down
double torque; // positive is anticlockwise
double max_velocity; // max motor output velocity
// does not apply force if the velocity in the
// direction of the motor vector is greater than
// max_velocity
struct timespec timeout;// absolute time (in ns, from when the program starts)
// for how long the motor runs before stopping
// automatically
// set to -1 for infinity
bool stop; // turn the motor off or on
void (*update_motor)(struct motorstruct *motor); // function pointer for generating
// the motor's output curve
struct BodyStruct *end_object;
} Motor;
typedef struct {
int x;
int y;
} Point;
/* String structure, used as a sub-element of a Body, compressible, but not
* stretchable. */
struct String {
bool attached;
double max_length;
Vect end_point;
int (*update_end_point)(struct String*); // method to update the end pt
// say if string is attached
// to another object
int (*set_end_point)(struct String*, Vect *); // manually set the end point of
// string
};
typedef struct String String;
typedef struct BodyStruct{
// turn on dynamic physics
// For moving objects.
// eg. on for payer, off for walls
bool dynamics;
// unique identifier
int uid;
bool colliding;
// position in viewport (pixels)
SDL_Point screen_pos;
// SI Unit kinematics
/*------------------*/
Vect position;
Vect next_position; // used for casting collision
Vect vel;
Vect acc;
// properties
double obj_mass; // kgs
double obj_elasticity; // rho
double obj_friction; // between 0 and 1 (fraction of lateral velocity
// that is removed)
//float x_vel;
//float y_vel;
//float x_acc;
//float y_acc;
/*------------------*/
// collisions
Vect *collision_poly;
Vect *collision_shape;
int collision_poly_size;
int collision_shape_size;
void (*updateCollisionPoly)(struct BodyStruct *);
// fields
double glob_friction;
bool glob_gravity; // t/f
// uint32_t last_advance_time;
struct timespec last_advance_time;
// applying forces
int num_motors;
int max_motors;
Motor *motors;
int num_strings;
int max_strings;
String *strings;
} Body;
typedef struct {
bool has_physics;
Body *physics;
int max_walking_speed;
int colliding;
} player_st;
typedef struct {
int numNodes;
SDL_Point *nodes;
Body *physics;
} Wall;
typedef struct {
Vect left;
Vect right;
Body *physics;
} FloorPoly;
typedef struct {
FloorPoly *polys;
int numPolys;
} Floor;
struct physics_collection {
int numItems;
Body **items;
};
typedef struct Projectile {
Body *physics;
void*(*on_collision)(struct Projectile*);
void*(*on_step)(struct Projectile*);
} Projectile;
struct room {
struct physics_collection ceil;
struct physics_collection floor;
struct environment *env; // TODO
};
typedef struct {
enum world_thing_kind kind;
int nid;
bool collisions;
bool physics;
union {
player_st *player;
Wall *wall;
Floor *floor;
Projectile *projectile;
struct room *room;
};
} world_thing;
struct world {
world_thing * things;
int size;
int capacity;
int modified;
world_thing** uniques_index;
};
typedef struct world GlobWorld;
#include "c-colours/colours.h"
#include "types.h"
#include "draw.h"
extern GlobWorld world;
extern int level;

6
garbo.h

@ -1,3 +1,7 @@ @@ -1,3 +1,7 @@
#ifndef _DEFGARBO
#define _DEFGARBO
#include <stdlib.h>
#include <string.h>
#include <SDL2/SDL.h>
@ -6,8 +10,6 @@ @@ -6,8 +10,6 @@
#include "logger.h"
#include <stdbool.h>
#ifndef _DEFGARBO
#define _DEFGARBO
/* Type definition for object cleanups */
typedef enum {

2
vect.h

@ -1,7 +1,7 @@ @@ -1,7 +1,7 @@
#include <math.h>
#ifndef VECT_H
#define VECT_H
#include <math.h>
// origin-centred vector
typedef struct {

Loading…
Cancel
Save