Physics edges
This commit is contained in:
parent
9303fb63cf
commit
68850b558a
2
Makefile
2
Makefile
|
@ -73,7 +73,7 @@ SEM = 0.0.1
|
|||
COM != git rev-parse --short HEAD
|
||||
VER = $(SEM)-$(COM)
|
||||
|
||||
COMPILER_FLAGS = $(includeflag) $(QFLAGS) -MD $(WARNING_FLAGS) -DVER=\"$(VER)\" -DINFO=\"$(INFO)\" -c $< -o $@
|
||||
COMPILER_FLAGS = $(includeflag) $(QFLAGS) -MD $(WARNING_FLAGS) -DCP_USE_DOUBLES=0 -DVER=\"$(VER)\" -DINFO=\"$(INFO)\" -c $< -o $@
|
||||
|
||||
LIBPATH = -L$(BIN)
|
||||
|
||||
|
|
|
@ -10,6 +10,7 @@
|
|||
#include <math.h>
|
||||
#include <chipmunk/chipmunk_unsafe.h>
|
||||
#include "stb_ds.h"
|
||||
#include <assert.h>
|
||||
|
||||
#include "script.h"
|
||||
|
||||
|
@ -158,40 +159,19 @@ void phys2d_dbgdrawcircle(struct phys2d_circle *circle)
|
|||
phys2d_dbgdrawcpcirc((cpCircleShape *)circle->shape.shape);
|
||||
}
|
||||
|
||||
|
||||
/*********** SEGMENT2D **************/
|
||||
|
||||
struct phys2d_segment *Make2DSegment(int go)
|
||||
void phys2d_applycircle(struct phys2d_circle *circle)
|
||||
{
|
||||
struct phys2d_segment *new = malloc(sizeof(struct phys2d_segment));
|
||||
struct gameobject *go = id2go(circle->shape.go);
|
||||
|
||||
new->thickness = 1.f;
|
||||
new->a[0] = 0.f;
|
||||
new->a[1] = 0.f;
|
||||
new->b[0] = 0.f;
|
||||
new->b[1] = 0.f;
|
||||
float radius = circle->radius * go->scale;
|
||||
float s = go->scale;
|
||||
cpVect offset = { circle->offset.x * s, circle->offset.y * s };
|
||||
|
||||
new->shape.shape = cpSpaceAddShape(space, cpSegmentShapeNew(id2go(go)->body, cpvzero, cpvzero, new->thickness));
|
||||
new->shape.debugdraw = phys2d_dbgdrawseg;
|
||||
init_phys2dshape(&new->shape, go, new);
|
||||
|
||||
return new;
|
||||
cpCircleShapeSetRadius(circle->shape.shape, radius);
|
||||
cpCircleShapeSetOffset(circle->shape.shape, offset);
|
||||
//cpBodySetMoment(go->body, cpMomentForCircle(go->mass, 0, radius, offset));
|
||||
}
|
||||
|
||||
void phys2d_segdel(struct phys2d_segment *seg)
|
||||
{
|
||||
phys2d_shape_del(&seg->shape);
|
||||
}
|
||||
|
||||
void segment_gui(struct phys2d_segment *seg)
|
||||
{
|
||||
nuke_property_float2("a", 0.f, seg->a, 1.f, 0.01f, 0.01f);
|
||||
nuke_property_float2("b", 0.f, seg->b, 1.f, 0.01f, 0.01f);
|
||||
|
||||
phys2d_applyseg(seg);
|
||||
}
|
||||
|
||||
|
||||
/************* BOX2D ************/
|
||||
|
||||
struct phys2d_box *Make2DBox(int go)
|
||||
|
@ -230,209 +210,18 @@ void phys2d_applybox(struct phys2d_box *box)
|
|||
{
|
||||
float s = id2go(box->shape.go)->scale;
|
||||
cpTransform T = { 0 };
|
||||
T.a = s;
|
||||
T.d = s;
|
||||
T.a = s * cos(box->rotation);
|
||||
T.b = -sin(box->rotation);
|
||||
T.c = sin(box->rotation);
|
||||
T.d = s * cos(box->rotation);
|
||||
T.tx = box->offset[0] * s;
|
||||
T.ty = box->offset[1] * s;
|
||||
float hh = box->h / 2.f;
|
||||
float hw = box->w / 2.f;
|
||||
cpVect verts[4] =
|
||||
{ { -hw, -hh }, { hw, -hh }, { hw, hh }, { -hw, hh } };
|
||||
cpVect verts[4] = { { -hw, -hh }, { hw, -hh }, { hw, hh }, { -hw, hh } };
|
||||
cpPolyShapeSetVerts(box->shape.shape, 4, verts, T);
|
||||
cpPolyShapeSetRadius(box->shape.shape, box->r);
|
||||
}
|
||||
|
||||
/************** POLYGON ************/
|
||||
|
||||
struct phys2d_poly *Make2DPoly(int go)
|
||||
{
|
||||
struct phys2d_poly *new = malloc(sizeof(struct phys2d_poly));
|
||||
|
||||
new->n = 0;
|
||||
new->points = NULL;
|
||||
new->radius = 0.f;
|
||||
|
||||
cpTransform T = { 0 };
|
||||
new->shape.shape = cpSpaceAddShape(space, cpPolyShapeNew(id2go(go)->body, 0, NULL, T, new->radius));
|
||||
init_phys2dshape(&new->shape, go, new);
|
||||
new->shape.debugdraw = phys2d_dbgdrawpoly;
|
||||
phys2d_applypoly(new);
|
||||
|
||||
return new;
|
||||
}
|
||||
|
||||
void phys2d_polydel(struct phys2d_poly *poly)
|
||||
{
|
||||
phys2d_shape_del(&poly->shape);
|
||||
}
|
||||
|
||||
void phys2d_polyaddvert(struct phys2d_poly *poly)
|
||||
{
|
||||
poly->n++;
|
||||
float *oldpoints = poly->points;
|
||||
poly->points = calloc(2 * poly->n, sizeof(float));
|
||||
memcpy(poly->points, oldpoints, sizeof(float) * 2 * (poly->n - 1));
|
||||
free(oldpoints);
|
||||
}
|
||||
|
||||
void poly_gui(struct phys2d_poly *poly)
|
||||
{
|
||||
|
||||
if (nuke_btn("Add Poly Vertex")) phys2d_polyaddvert(poly);
|
||||
|
||||
for (int i = 0; i < poly->n; i++) {
|
||||
nuke_property_float2("#P", 0.f, &poly->points[i*2], 1.f, 0.1f, 0.1f);
|
||||
}
|
||||
|
||||
nuke_property_float("Radius", 0.01f, &poly->radius, 1000.f, 1.f, 0.1f);
|
||||
|
||||
phys2d_applypoly(poly);
|
||||
}
|
||||
|
||||
|
||||
|
||||
/****************** EDGE 2D**************/
|
||||
|
||||
struct phys2d_edge *Make2DEdge(int go)
|
||||
{
|
||||
struct phys2d_edge *new = malloc(sizeof(struct phys2d_edge));
|
||||
|
||||
new->n = 2;
|
||||
new->points = calloc(2 * 2, sizeof(float));
|
||||
new->thickness = 0.f;
|
||||
new->shapes = malloc(sizeof(cpShape *));
|
||||
|
||||
new->shapes[0] = cpSpaceAddShape(space, cpSegmentShapeNew(id2go(go)->body, cpvzero, cpvzero, new->thickness));
|
||||
new->shape.go = go;
|
||||
phys2d_edgeshapeapply(&new->shape, new->shapes[0]);
|
||||
|
||||
phys2d_applyedge(new);
|
||||
|
||||
return new;
|
||||
}
|
||||
|
||||
void phys2d_edgedel(struct phys2d_edge *edge)
|
||||
{
|
||||
phys2d_shape_del(&edge->shape);
|
||||
}
|
||||
|
||||
void phys2d_edgeshapeapply(struct phys2d_shape *mshape, cpShape * shape)
|
||||
{
|
||||
cpShapeSetFriction(shape, id2go(mshape->go)->f);
|
||||
cpShapeSetElasticity(shape, id2go(mshape->go)->e);
|
||||
}
|
||||
|
||||
void phys2d_edgeaddvert(struct phys2d_edge *edge)
|
||||
{
|
||||
edge->n++;
|
||||
float *oldp = edge->points;
|
||||
edge->points = calloc(edge->n * 2, sizeof(float));
|
||||
memcpy(edge->points, oldp, sizeof(float) * 2 * (edge->n - 1));
|
||||
|
||||
cpShape **oldshapes = edge->shapes;
|
||||
edge->shapes = malloc(sizeof(cpShape *) * (edge->n - 1));
|
||||
memcpy(edge->shapes, oldshapes, sizeof(cpShape *) * (edge->n - 2));
|
||||
cpVect a =
|
||||
{ edge->points[(edge->n - 2) * 2],
|
||||
edge->points[(edge->n - 2) * 2 + 1] };
|
||||
cpVect b =
|
||||
{ edge->points[(edge->n - 1) * 2],
|
||||
edge->points[(edge->n - 1) * 2 + 1] };
|
||||
edge->shapes[edge->n - 2] = cpSpaceAddShape(space, cpSegmentShapeNew(id2go(edge->shape.go)->body, a, b, edge->thickness));
|
||||
phys2d_edgeshapeapply(&edge->shape, edge->shapes[edge->n - 2]);
|
||||
|
||||
free(oldp);
|
||||
free(oldshapes);
|
||||
}
|
||||
|
||||
void edge_gui(struct phys2d_edge *edge)
|
||||
{
|
||||
if (nuke_btn("Add Edge Vertex")) phys2d_edgeaddvert(edge);
|
||||
|
||||
for (int i = 0; i < edge->n; i++)
|
||||
nuke_property_float2("E", 0.f, &edge->points[i*2], 1.f, 0.01f, 0.01f);
|
||||
|
||||
nuke_property_float("Thickness", 0.01f, &edge->thickness, 1.f, 0.01f, 0.01f);
|
||||
|
||||
phys2d_applyedge(edge);
|
||||
}
|
||||
|
||||
|
||||
|
||||
void phys2d_applycircle(struct phys2d_circle *circle)
|
||||
{
|
||||
struct gameobject *go = id2go(circle->shape.go);
|
||||
|
||||
float radius = circle->radius * go->scale;
|
||||
float s = go->scale;
|
||||
cpVect offset = { circle->offset.x * s, circle->offset.y * s };
|
||||
|
||||
cpCircleShapeSetRadius(circle->shape.shape, radius);
|
||||
cpCircleShapeSetOffset(circle->shape.shape, offset);
|
||||
cpBodySetMoment(go->body, cpMomentForCircle(go->mass, 0, radius, offset));
|
||||
}
|
||||
|
||||
void phys2d_applyseg(struct phys2d_segment *seg)
|
||||
{
|
||||
float s = id2go(seg->shape.go)->scale;
|
||||
cpVect a = { seg->a[0] * s, seg->a[1] * s };
|
||||
cpVect b = { seg->b[0] * s, seg->b[1] * s };
|
||||
cpSegmentShapeSetEndpoints(seg->shape.shape, a, b);
|
||||
cpSegmentShapeSetRadius(seg->shape.shape, seg->thickness * s);
|
||||
}
|
||||
|
||||
|
||||
|
||||
void phys2d_applypoly(struct phys2d_poly *poly)
|
||||
{
|
||||
cpVect verts[poly->n];
|
||||
|
||||
for (int i = 0; i < poly->n; i++) {
|
||||
verts[i].x = poly->points[i * 2];
|
||||
verts[i].y = poly->points[i * 2 + 1];
|
||||
}
|
||||
|
||||
CP_CONVEX_HULL(poly->n, verts, hullCount, hullVerts);
|
||||
|
||||
float s = id2go(poly->shape.go)->scale;
|
||||
cpTransform T = { 0 };
|
||||
T.a = s;
|
||||
T.d = s;
|
||||
|
||||
cpPolyShapeSetVerts(poly->shape.shape, hullCount, hullVerts, T);
|
||||
cpPolyShapeSetRadius(poly->shape.shape, poly->radius);
|
||||
}
|
||||
|
||||
void phys2d_applyedge(struct phys2d_edge *edge)
|
||||
{
|
||||
float s = id2go(edge->shape.go)->scale;
|
||||
|
||||
for (int i = 0; i < edge->n - 1; i++) {
|
||||
cpVect a =
|
||||
{ edge->points[i * 2] * s, edge->points[i * 2 + 1] * s };
|
||||
cpVect b =
|
||||
{ edge->points[i * 2 + 2] * s, edge->points[i * 2 + 3] * s };
|
||||
cpSegmentShapeSetEndpoints(edge->shapes[i], a, b);
|
||||
cpSegmentShapeSetRadius(edge->shapes[i], edge->thickness);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
void phys2d_dbgdrawseg(struct phys2d_segment *seg)
|
||||
{
|
||||
cpVect p = cpBodyGetPosition(cpShapeGetBody(seg->shape.shape));
|
||||
cpVect a = cpSegmentShapeGetA(seg->shape.shape);
|
||||
cpVect b = cpSegmentShapeGetB(seg->shape.shape);
|
||||
|
||||
float angle = cpBodyGetAngle(cpShapeGetBody(seg->shape.shape));
|
||||
float ad = sqrt(pow(a.x, 2.f) + pow(a.y, 2.f));
|
||||
float bd = sqrt(pow(b.x, 2.f) + pow(b.y, 2.f));
|
||||
float aa = atan2(a.y, a.x) + angle;
|
||||
float ba = atan2(b.y, b.x) + angle;
|
||||
draw_line(ad * cos(aa) + p.x, ad * sin(aa) + p.y, bd * cos(ba) + p.x, bd * sin(ba) + p.y, shape_color(seg->shape.shape));
|
||||
}
|
||||
|
||||
void phys2d_dbgdrawbox(struct phys2d_box *box)
|
||||
{
|
||||
int n = cpPolyShapeGetCount(box->shape.shape);
|
||||
|
@ -450,22 +239,70 @@ void phys2d_dbgdrawbox(struct phys2d_box *box)
|
|||
|
||||
draw_poly(points, n, shape_color(box->shape.shape));
|
||||
}
|
||||
/************** POLYGON ************/
|
||||
|
||||
struct phys2d_poly *Make2DPoly(int go)
|
||||
{
|
||||
struct phys2d_poly *new = malloc(sizeof(struct phys2d_poly));
|
||||
|
||||
arrsetlen(new->points, 0);
|
||||
new->radius = 0.f;
|
||||
|
||||
new->shape.shape = cpSpaceAddShape(space, cpPolyShapeNewRaw(id2go(go)->body, 0, new->points, new->radius));
|
||||
new->shape.debugdraw = phys2d_dbgdrawpoly;
|
||||
init_phys2dshape(&new->shape, go, new);
|
||||
return new;
|
||||
}
|
||||
|
||||
void phys2d_polydel(struct phys2d_poly *poly)
|
||||
{
|
||||
arrfree(poly->points);
|
||||
phys2d_shape_del(&poly->shape);
|
||||
}
|
||||
|
||||
void phys2d_polyaddvert(struct phys2d_poly *poly)
|
||||
{
|
||||
arrput(poly->points, cpvzero);
|
||||
}
|
||||
|
||||
void poly_gui(struct phys2d_poly *poly)
|
||||
{
|
||||
}
|
||||
|
||||
void phys2d_poly_setverts(struct phys2d_poly *poly, cpVect *verts)
|
||||
{
|
||||
arrfree(poly->points);
|
||||
poly->points = verts;
|
||||
phys2d_applypoly(poly);
|
||||
}
|
||||
|
||||
void phys2d_applypoly(struct phys2d_poly *poly)
|
||||
{
|
||||
if (arrlen(poly->points) <= 0) return;
|
||||
float s = id2go(poly->shape.go)->scale;
|
||||
cpTransform T = { 0 };
|
||||
T.a = s;
|
||||
T.d = s;
|
||||
|
||||
cpPolyShapeSetVerts(poly->shape.shape, arrlen(poly->points), poly->points, T);
|
||||
cpPolyShapeSetRadius(poly->shape.shape, poly->radius);
|
||||
}
|
||||
void phys2d_dbgdrawpoly(struct phys2d_poly *poly)
|
||||
{
|
||||
float *color = shape_color(poly->shape.shape);
|
||||
int n = arrlen(poly->points);
|
||||
|
||||
cpVect b = cpBodyGetPosition(cpShapeGetBody(poly->shape.shape));
|
||||
float angle = cpBodyGetAngle(cpShapeGetBody(poly->shape.shape));
|
||||
|
||||
float s = id2go(poly->shape.go)->scale;
|
||||
for (int i = 0; i < poly->n; i++) {
|
||||
float d = sqrt(pow(poly->points[i * 2] * s, 2.f) + pow(poly->points[i * 2 + 1] * s, 2.f));
|
||||
float a = atan2(poly->points[i * 2 + 1], poly->points[i * 2]) + angle;
|
||||
for (int i = 0; i < n; i++) {
|
||||
float d = sqrt(pow(poly->points[i * 2].x * s, 2.f) + pow(poly->points[i * 2].y* s, 2.f));
|
||||
float a = atan2(poly->points[i * 2].y, poly->points[i * 2].x) + angle;
|
||||
draw_point(b.x + d * cos(a), b.y + d * sin(a), 3, color);
|
||||
}
|
||||
|
||||
if (poly->n >= 3) {
|
||||
if (arrlen(poly->points) >= 3) {
|
||||
int n = cpPolyShapeGetCount(poly->shape.shape);
|
||||
float points[n * 2];
|
||||
|
||||
|
@ -481,32 +318,111 @@ void phys2d_dbgdrawpoly(struct phys2d_poly *poly)
|
|||
}
|
||||
|
||||
}
|
||||
/****************** EDGE 2D**************/
|
||||
|
||||
struct phys2d_edge *Make2DEdge(int go)
|
||||
{
|
||||
struct phys2d_edge *new = malloc(sizeof(struct phys2d_edge));
|
||||
new->points = NULL;
|
||||
arrsetlen(new->points, 0);
|
||||
new->thickness = 0.f;
|
||||
new->shapes = NULL;
|
||||
arrsetlen(new->shapes, 0);
|
||||
new->shape.go = go;
|
||||
new->shape.data = new;
|
||||
new->shape.debugdraw = phys2d_dbgdrawedge;
|
||||
phys2d_applyedge(new);
|
||||
|
||||
return new;
|
||||
}
|
||||
|
||||
void phys2d_edgedel(struct phys2d_edge *edge)
|
||||
{
|
||||
phys2d_shape_del(&edge->shape);
|
||||
}
|
||||
|
||||
void phys2d_edgeaddvert(struct phys2d_edge *edge)
|
||||
{
|
||||
arrput(edge->points, cpvzero);
|
||||
if (arrlen(edge->points) > 1)
|
||||
arrput(edge->shapes, cpSpaceAddShape(space, cpSegmentShapeNew(id2go(edge->shape.go)->body, cpvzero, cpvzero, edge->thickness)));
|
||||
|
||||
phys2d_applyedge(edge);
|
||||
}
|
||||
|
||||
void phys2d_edge_rmvert(struct phys2d_edge *edge, int index)
|
||||
{
|
||||
assert(arrlen(edge->points) > index && index >= 0);
|
||||
|
||||
arrdel(edge->points, index);
|
||||
cpSegmentShapeSetEndpoints(edge->shapes[index-1], edge->points[index-1], edge->points[index]);
|
||||
cpSpaceRemoveShape(space, edge->shapes[index-1]);
|
||||
arrdel(edge->shapes, index-1);
|
||||
|
||||
phys2d_applyedge(edge);
|
||||
}
|
||||
|
||||
phys2d_edge_setvert(struct phys2d_edge *edge, int index, cpVect val)
|
||||
{
|
||||
assert(arrlen(edge->points) > index && index >= 0);
|
||||
edge->points[index] = val;
|
||||
|
||||
phys2d_applyedge(edge);
|
||||
}
|
||||
|
||||
void phys2d_applyedge(struct phys2d_edge *edge)
|
||||
{
|
||||
float s = id2go(edge->shape.go)->scale;
|
||||
|
||||
for (int i = 0; i < arrlen(edge->shapes); i++) {
|
||||
cpVect a = edge->points[i];
|
||||
cpVect b = edge->points[i+1];
|
||||
a.x *= s;
|
||||
a.y *= s;
|
||||
b.x *= s;
|
||||
b.y *= s;
|
||||
cpSegmentShapeSetEndpoints(edge->shapes[i], a, b);
|
||||
cpSegmentShapeSetRadius(edge->shapes[i], edge->thickness);
|
||||
cpShapeSetUserData(edge->shapes[i], &edge->shape);
|
||||
cpShapeSetCollisionType(edge->shapes[i], edge->shape.go);
|
||||
cpShapeSetFriction(edge->shapes[i], id2go(edge->shape.go)->f);
|
||||
cpShapeSetElasticity(edge->shapes[i], id2go(edge->shape.go)->e);
|
||||
}
|
||||
|
||||
cpSpaceReindexShapesForBody(space, id2go(edge->shape.go)->body);
|
||||
}
|
||||
|
||||
void phys2d_dbgdrawedge(struct phys2d_edge *edge)
|
||||
{
|
||||
float *color =shape_color(edge->shape.shape);
|
||||
edge->draws++;
|
||||
if (edge->draws > 1) {
|
||||
if (edge->draws >= arrlen(edge->shapes))
|
||||
edge->draws = 0;
|
||||
|
||||
cpVect p = cpBodyGetPosition(cpShapeGetBody(edge->shape.shape));
|
||||
return;
|
||||
}
|
||||
|
||||
if (arrlen(edge->shapes) < 1) return;
|
||||
|
||||
cpVect p = cpBodyGetPosition(cpShapeGetBody(edge->shapes[0]));
|
||||
float s = id2go(edge->shape.go)->scale;
|
||||
float angle = cpBodyGetAngle(cpShapeGetBody(edge->shape.shape));
|
||||
float angle = cpBodyGetAngle(cpShapeGetBody(edge->shapes[0]));
|
||||
|
||||
for (int i = 0; i < edge->n; i++) {
|
||||
float d = sqrt(pow(edge->points[i * 2] * s, 2.f) + pow(edge->points[i * 2 + 1] * s, 2.f));
|
||||
float a = atan2(edge->points[i * 2 + 1], edge->points[i * 2]) + angle;
|
||||
draw_point(p.x + d * cos(a), p.y + d * sin(a), 3, color);
|
||||
cpVect drawpoints[arrlen(edge->points)];
|
||||
|
||||
for (int i = 0; i < arrlen(edge->points); i++) {
|
||||
float d = sqrt(pow(edge->points[i].x*s, 2.f) + pow(edge->points[i].y*s, 2.f));
|
||||
float a = atan2(edge->points[i].y, edge->points[i].x) + angle;
|
||||
drawpoints[i].x = p.x + d*cos(a);
|
||||
drawpoints[i].y = p.y + d*sin(a);
|
||||
}
|
||||
|
||||
for (int i = 0; i < edge->n - 1; i++) {
|
||||
cpVect a = cpSegmentShapeGetA(edge->shapes[i]);
|
||||
cpVect b = cpSegmentShapeGetB(edge->shapes[i]);
|
||||
float ad = sqrt(pow(a.x, 2.f) + pow(a.y, 2.f));
|
||||
float bd = sqrt(pow(b.x, 2.f) + pow(b.y, 2.f));
|
||||
float aa = atan2(a.y, a.x) + angle;
|
||||
float ba = atan2(b.y, b.x) + angle;
|
||||
draw_line(ad * cos(aa) + p.x, ad * sin(aa) + p.y, bd * cos(ba) + p.x, bd * sin(ba) + p.y, color);
|
||||
}
|
||||
draw_edge(drawpoints, arrlen(edge->points), trigger_color);
|
||||
draw_points(drawpoints, arrlen(edge->points), 2, kinematic_color);
|
||||
}
|
||||
|
||||
|
||||
/************ COLLIDER ****************/
|
||||
void shape_enabled(struct phys2d_shape *shape, int enabled)
|
||||
{
|
||||
if (enabled)
|
||||
|
|
|
@ -23,12 +23,14 @@ struct phys2d_shape {
|
|||
void (*debugdraw)(void *data);
|
||||
};
|
||||
|
||||
/* Circles are the fastest collier type */
|
||||
struct phys2d_circle {
|
||||
float radius;
|
||||
cpVect offset;
|
||||
struct phys2d_shape shape;
|
||||
};
|
||||
|
||||
/* A single segment */
|
||||
struct phys2d_segment {
|
||||
float a[2];
|
||||
float b[2];
|
||||
|
@ -36,27 +38,31 @@ struct phys2d_segment {
|
|||
struct phys2d_shape shape;
|
||||
};
|
||||
|
||||
/* A convex polygon; defined as the convex hull around the given set of points */
|
||||
struct phys2d_poly {
|
||||
cpVect *points;
|
||||
float radius;
|
||||
struct phys2d_shape shape;
|
||||
};
|
||||
|
||||
/* A box shape; a type of a polygon collider */
|
||||
struct phys2d_box {
|
||||
float w;
|
||||
float h;
|
||||
float offset[2];
|
||||
float rotation;
|
||||
float r;
|
||||
struct phys2d_shape shape;
|
||||
};
|
||||
|
||||
/* An edge with no volume. Cannot collide with each other. Join to make levels. */
|
||||
struct phys2d_edge {
|
||||
int n;
|
||||
float *points;
|
||||
cpVect *points;
|
||||
float thickness;
|
||||
cpShape **shapes;
|
||||
int closed; /* True if the first and last points should be connected */
|
||||
struct phys2d_shape shape;
|
||||
};
|
||||
|
||||
struct phys2d_poly {
|
||||
int n;
|
||||
float *points;
|
||||
float radius;
|
||||
struct phys2d_shape shape;
|
||||
int draws;
|
||||
};
|
||||
|
||||
struct phys2d_circle *Make2DCircle(int go);
|
||||
|
@ -65,12 +71,6 @@ void phys2d_applycircle(struct phys2d_circle *circle);
|
|||
void phys2d_dbgdrawcircle(struct phys2d_circle *circle);
|
||||
void circle_gui(struct phys2d_circle *circle);
|
||||
|
||||
struct phys2d_segment *Make2DSegment(int go);
|
||||
void phys2d_segdel(struct phys2d_segment *seg);
|
||||
void phys2d_applyseg(struct phys2d_segment *seg);
|
||||
void phys2d_dbgdrawseg(struct phys2d_segment *seg);
|
||||
void segment_gui(struct phys2d_segment *seg);
|
||||
|
||||
struct phys2d_box *Make2DBox(int go);
|
||||
void phys2d_boxdel(struct phys2d_box *box);
|
||||
void phys2d_applybox(struct phys2d_box *box);
|
||||
|
@ -82,14 +82,15 @@ void phys2d_polydel(struct phys2d_poly *poly);
|
|||
void phys2d_applypoly(struct phys2d_poly *poly);
|
||||
void phys2d_dbgdrawpoly(struct phys2d_poly *poly);
|
||||
void phys2d_polyaddvert(struct phys2d_poly *poly);
|
||||
void phys2d_poly_setverts(struct phys2d_poly *poly, cpVect *verts);
|
||||
void poly_gui(struct phys2d_poly *poly);
|
||||
|
||||
struct phys2d_edge *Make2DEdge(int go);
|
||||
void phys2d_edgedel(struct phys2d_edge *edge);
|
||||
void phys2d_applyedge(struct phys2d_edge *edge);
|
||||
void phys2d_edgeshapeapply(struct phys2d_shape *mshape, cpShape * shape);
|
||||
void phys2d_dbgdrawedge(struct phys2d_edge *edge);
|
||||
void phys2d_edgeaddvert(struct phys2d_edge *edge);
|
||||
void phys2d_edge_rmvert(struct phys2d_edge *edge, int index);
|
||||
void edge_gui(struct phys2d_edge *edge);
|
||||
|
||||
|
||||
|
|
|
@ -1,6 +1,8 @@
|
|||
#ifndef DEBUG_GUI_H
|
||||
#define DEBUG_GUI_H
|
||||
|
||||
#define static_assert(pred) switch(0){case 0:case pred:;}
|
||||
|
||||
extern unsigned long long triCount;
|
||||
|
||||
void resetTriangles();
|
||||
|
|
|
@ -4,6 +4,10 @@
|
|||
|
||||
#include "shader.h"
|
||||
#include "log.h"
|
||||
#include <assert.h>
|
||||
#include "debug.h"
|
||||
|
||||
#include "stb_ds.h"
|
||||
|
||||
static uint32_t circleVBO;
|
||||
static uint32_t circleVAO;
|
||||
|
@ -59,9 +63,20 @@ void draw_line(int x1, int y1, int x2, int y2, float *color)
|
|||
draw_poly(verts, 2, color);
|
||||
}
|
||||
|
||||
void draw_edge(float *points, int n, float *color)
|
||||
void draw_edge(cpVect *points, int n, float *color)
|
||||
{
|
||||
draw_poly(points, n, color);
|
||||
static_assert(sizeof(cpVect) == 2*sizeof(float));
|
||||
|
||||
shader_use(rectShader);
|
||||
shader_setvec3(rectShader, "linecolor", color);
|
||||
glBindBuffer(GL_ARRAY_BUFFER, rectVBO);
|
||||
glBufferData(GL_ARRAY_BUFFER, sizeof(float) * n * 2, points, GL_DYNAMIC_DRAW);
|
||||
glBindVertexArray(rectVAO);
|
||||
glEnableVertexAttribArray(0);
|
||||
glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, 0, NULL);
|
||||
|
||||
shader_setfloat(rectShader, "alpha", 1.f);
|
||||
glDrawArrays(GL_LINE_STRIP, 0, n);
|
||||
}
|
||||
|
||||
void draw_circle(int x, int y, float radius, int pixels, float *color, int fill)
|
||||
|
@ -120,6 +135,12 @@ void draw_point(int x, int y, float r, float *color)
|
|||
draw_circle(x, y, r, r, color, 0);
|
||||
}
|
||||
|
||||
void draw_points(struct cpVect *points, int n, float size, float *color)
|
||||
{
|
||||
for (int i = 0; i < n; i++)
|
||||
draw_point(points[i].x, points[i].y, size, color);
|
||||
}
|
||||
|
||||
void draw_poly(float *points, int n, float *color)
|
||||
{
|
||||
shader_use(rectShader);
|
||||
|
@ -138,6 +159,17 @@ void draw_poly(float *points, int n, float *color)
|
|||
glDrawArrays(GL_LINE_LOOP, 0, n);
|
||||
}
|
||||
|
||||
void draw_polyvec(cpVect *points, int n, float *color)
|
||||
{
|
||||
float drawvec[n*2];
|
||||
for (int i = 0; i < n; i++) {
|
||||
drawvec[i*2] = points[i].x;
|
||||
drawvec[i*2+1] = points[i].y;
|
||||
}
|
||||
|
||||
draw_poly(drawvec, n, color);
|
||||
}
|
||||
|
||||
void debugdraw_flush()
|
||||
{
|
||||
|
||||
|
|
|
@ -1,15 +1,19 @@
|
|||
#ifndef DEBUGDRAW_H
|
||||
#define DEBUGDRAW_H
|
||||
|
||||
struct cpVect;
|
||||
|
||||
void debugdraw_init();
|
||||
void draw_line(int x1, int y1, int x2, int y2, float *color);
|
||||
void draw_edge(float *points, int n, float *color);
|
||||
void draw_edge(struct cpVect *points, int n, float *color);
|
||||
void draw_points(struct cpVect *points, int n, float size, float *color);
|
||||
void draw_circle(int x, int y, float radius, int pixels, float *color, int fill);
|
||||
void draw_grid(int width, int span);
|
||||
void draw_rect(int x, int y, int w, int h, float *color);
|
||||
void draw_point(int x, int y, float r, float *color);
|
||||
void draw_poly(float *points, int n, float *color);
|
||||
|
||||
|
||||
void debugdraw_flush(); /* This is called once per frame to draw all queued elements */
|
||||
|
||||
|
||||
|
|
|
@ -64,5 +64,5 @@ void engine_init()
|
|||
phys2d_init();
|
||||
|
||||
YughInfo("Starting sound ...");
|
||||
sound_init();
|
||||
//sound_init();
|
||||
}
|
||||
|
|
|
@ -21,6 +21,12 @@
|
|||
#include "music.h"
|
||||
#include "level.h"
|
||||
|
||||
void duk_dump_stack(duk_context *duk)
|
||||
{
|
||||
duk_push_context_dump(duk);
|
||||
YughInfo("DUK STACK\n%s", duk_to_string(duk, -1));
|
||||
}
|
||||
|
||||
struct color duk2color(duk_context *duk, int p)
|
||||
{
|
||||
struct color color;
|
||||
|
@ -37,6 +43,8 @@ struct color duk2color(duk_context *duk, int p)
|
|||
|
||||
cpVect duk2vec2(duk_context *duk, int p) {
|
||||
cpVect pos;
|
||||
if (p < 0) p = duk_get_top_index(duk) + p + 1;
|
||||
|
||||
duk_get_prop_index(duk, p, 0);
|
||||
pos.x = duk_to_number(duk, -1);
|
||||
duk_get_prop_index(duk, p, 1);
|
||||
|
@ -125,7 +133,6 @@ duk_ret_t duk_cmd(duk_context *duk) {
|
|||
case 0:
|
||||
duk_push_int(duk, script_dofile(duk_to_string(duk, 1)));
|
||||
return 1;
|
||||
break;
|
||||
|
||||
case 1:
|
||||
set_pawn(duk_get_heapptr(duk, 1));
|
||||
|
@ -270,12 +277,21 @@ duk_ret_t duk_cmd(duk_context *duk) {
|
|||
|
||||
case 36:
|
||||
id2go(duk_to_int(duk, 1))->scale = duk_to_number(duk, 2);
|
||||
cpSpaceReindexShapesForBody(space, id2go(duk_to_int(duk, 1))->body);
|
||||
return 0;
|
||||
|
||||
case 37:
|
||||
if (!id2sprite(duk_to_int(duk, 1))) return 0;
|
||||
vec2float(duk2vec2(duk, 2), id2sprite(duk_to_int(duk, 1))->pos);
|
||||
break;
|
||||
|
||||
case 38:
|
||||
duk_push_string(duk, slurp_text(duk_to_string(duk, 1)));
|
||||
return 1;
|
||||
|
||||
case 39:
|
||||
duk_push_int(duk, slurp_write(duk_to_string(duk, 1), duk_to_string(duk, 2)));
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
@ -331,6 +347,7 @@ duk_ret_t duk_sys_cmd(duk_context *duk) {
|
|||
|
||||
case 1:
|
||||
sim_start();
|
||||
cpSpaceReindexStatic(space);
|
||||
break;
|
||||
|
||||
case 2:
|
||||
|
@ -410,7 +427,6 @@ duk_ret_t duk_set_body(duk_context *duk) {
|
|||
switch (cmd) {
|
||||
case 0:
|
||||
gameobject_setangle(go, duk_to_number(duk, 2));
|
||||
cpSpaceReindexShapesForBody(space, go->body);
|
||||
break;
|
||||
|
||||
case 1:
|
||||
|
@ -419,7 +435,6 @@ duk_ret_t duk_set_body(duk_context *duk) {
|
|||
|
||||
case 2:
|
||||
cpBodySetPosition(go->body, duk2vec2(duk, 2));
|
||||
cpSpaceReindexShapesForBody(space, go->body);
|
||||
break;
|
||||
|
||||
case 3:
|
||||
|
@ -452,6 +467,8 @@ duk_ret_t duk_set_body(duk_context *duk) {
|
|||
|
||||
}
|
||||
|
||||
cpSpaceReindexShapesForBody(space, go->body);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -543,20 +560,26 @@ duk_ret_t duk_cmd_box2d(duk_context *duk)
|
|||
{
|
||||
int cmd = duk_to_int(duk, 0);
|
||||
struct phys2d_box *box = duk_to_pointer(duk, 1);
|
||||
cpVect arg = duk2vec2(duk, 2);
|
||||
cpVect arg;
|
||||
|
||||
if (!box) return 0;
|
||||
|
||||
switch(cmd) {
|
||||
case 0:
|
||||
arg = duk2vec2(duk, 2);
|
||||
box->w = arg.x;
|
||||
box->h = arg.y;
|
||||
break;
|
||||
|
||||
case 1:
|
||||
arg = duk2vec2(duk, 2);
|
||||
box->offset[0] = arg.x;
|
||||
box->offset[1] = arg.y;
|
||||
break;
|
||||
|
||||
case 2:
|
||||
box->rotation = duk_to_number(duk, 2);
|
||||
break;
|
||||
}
|
||||
|
||||
phys2d_applybox(box);
|
||||
|
@ -603,6 +626,54 @@ duk_ret_t duk_cmd_circle2d(duk_context *duk)
|
|||
return 0;
|
||||
}
|
||||
|
||||
duk_ret_t duk_make_poly2d(duk_context *duk)
|
||||
{
|
||||
int go = duk_to_int(duk, 0);
|
||||
struct phys2d_poly *poly = Make2DPoly(go);
|
||||
|
||||
YughInfo("Making polygon.");
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
duk_ret_t duk_cmd_poly2d(duk_context *duk)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
duk_ret_t duk_make_edge2d(duk_context *duk)
|
||||
{
|
||||
int go = duk_to_int(duk, 0);
|
||||
struct phys2d_edge *edge = Make2DEdge(go);
|
||||
|
||||
int arridx = 1;
|
||||
|
||||
int n = duk_get_length(duk, arridx);
|
||||
cpVect points[n];
|
||||
|
||||
for (int i = 0; i < n; i++) {
|
||||
duk_get_prop_index(duk, arridx, i);
|
||||
|
||||
points[i] = duk2vec2(duk, -1);
|
||||
|
||||
phys2d_edgeaddvert(edge);
|
||||
phys2d_edge_setvert(edge, i, points[i]);
|
||||
}
|
||||
|
||||
int idx = duk_push_object(duk);
|
||||
duk_push_pointer(duk, &edge->shape);
|
||||
duk_put_prop_string(duk, idx, "id");
|
||||
duk_push_pointer(duk, edge);
|
||||
duk_put_prop_string(duk, idx, "shape");
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
duk_ret_t duk_cmd_edge2d(duk_context *duk)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
/* These are anims for controlling properties on an object */
|
||||
duk_ret_t duk_anim(duk_context *duk) {
|
||||
void *prop = duk_get_heapptr(duk, 0);
|
||||
|
@ -663,6 +734,10 @@ void ffi_load()
|
|||
DUK_FUNC(cmd_box2d, DUK_VARARGS);
|
||||
DUK_FUNC(make_circle2d, 3);
|
||||
DUK_FUNC(cmd_circle2d, DUK_VARARGS);
|
||||
DUK_FUNC(make_poly2d, 2);
|
||||
DUK_FUNC(cmd_poly2d, DUK_VARARGS);
|
||||
DUK_FUNC(make_edge2d, 3);
|
||||
DUK_FUNC(cmd_edge2d, DUK_VARARGS);
|
||||
DUK_FUNC(make_timer, 3);
|
||||
|
||||
DUK_FUNC(cmd, DUK_VARARGS);
|
||||
|
|
|
@ -54,6 +54,16 @@ unsigned char *slurp_text(const char *filename) {
|
|||
return buf;
|
||||
}
|
||||
|
||||
int slurp_write(const char *txt, const char *filename)
|
||||
{
|
||||
FILE *f = fopen(filename, "w");
|
||||
if (!f) return 1;
|
||||
|
||||
fputs(txt, f);
|
||||
fclose(f);
|
||||
return 0;
|
||||
}
|
||||
|
||||
void font_init(struct shader *textshader) {
|
||||
shader = textshader;
|
||||
|
||||
|
|
|
@ -34,4 +34,6 @@ void renderText(const char *text, mfloat_t pos[2], float scale, mfloat_t color[3
|
|||
unsigned char *slurp_file(const char *filename);
|
||||
unsigned char *slurp_text(const char *filename);
|
||||
|
||||
int slurp_write(const char *txt, const char *filename);
|
||||
|
||||
#endif
|
||||
|
|
|
@ -6,6 +6,8 @@
|
|||
#include <string.h>
|
||||
#include "log.h"
|
||||
|
||||
#include <assert.h>
|
||||
|
||||
static struct bus bus[256];
|
||||
static int first = 0; /* First bus available */
|
||||
//static struct bus *first_on = NULL;
|
||||
|
@ -35,10 +37,8 @@ void mixer_init() {
|
|||
}
|
||||
|
||||
struct bus *first_free_bus(struct dsp_filter in) {
|
||||
if (!initted) {
|
||||
YughError("Tried to use a mixing bus without calling mixer_init().");
|
||||
return NULL;
|
||||
}
|
||||
if (!initted) return;
|
||||
assert(initted);
|
||||
|
||||
if (first == -1) return NULL;
|
||||
int ret = first;
|
||||
|
|
Loading…
Reference in a new issue