spline and edge commands
This commit is contained in:
parent
4d7d665a5e
commit
99e9807552
|
@ -61,7 +61,16 @@ int *qhits;
|
||||||
|
|
||||||
void querylist(cpShape *shape, cpContactPointSet *points, void *data)
|
void querylist(cpShape *shape, cpContactPointSet *points, void *data)
|
||||||
{
|
{
|
||||||
arrput(qhits, shape2gameobject(shape));
|
int go = shape2gameobject(shape);
|
||||||
|
int in = 0;
|
||||||
|
for (int i = 0; i < arrlen(qhits); i++) {
|
||||||
|
if (qhits[i] == go) {
|
||||||
|
in = 1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!in) arrput(qhits, go);
|
||||||
}
|
}
|
||||||
|
|
||||||
void querylistbodies(cpBody *body, void *data)
|
void querylistbodies(cpBody *body, void *data)
|
||||||
|
@ -412,7 +421,21 @@ void phys2d_edge_rmvert(struct phys2d_edge *edge, int index)
|
||||||
assert(arrlen(edge->points) > index && index >= 0);
|
assert(arrlen(edge->points) > index && index >= 0);
|
||||||
|
|
||||||
arrdel(edge->points, index);
|
arrdel(edge->points, index);
|
||||||
cpSegmentShapeSetEndpoints(edge->shapes[index-1], edge->points[index-1], edge->points[index]);
|
|
||||||
|
if (arrlen(edge->points) == 0) return;
|
||||||
|
|
||||||
|
|
||||||
|
if (index == 0) {
|
||||||
|
cpSpaceRemoveShape(space, edge->shapes[index]);
|
||||||
|
arrdel(edge->shapes, index);
|
||||||
|
phys2d_applyedge(edge);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (index != arrlen(edge->points)) {
|
||||||
|
cpSegmentShapeSetEndpoints(edge->shapes[index-1], edge->points[index-1], edge->points[index]);
|
||||||
|
}
|
||||||
|
|
||||||
cpSpaceRemoveShape(space, edge->shapes[index-1]);
|
cpSpaceRemoveShape(space, edge->shapes[index-1]);
|
||||||
arrdel(edge->shapes, index-1);
|
arrdel(edge->shapes, index-1);
|
||||||
|
|
||||||
|
@ -427,6 +450,21 @@ void phys2d_edge_setvert(struct phys2d_edge *edge, int index, cpVect val)
|
||||||
phys2d_applyedge(edge);
|
phys2d_applyedge(edge);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void phys2d_edge_clearverts(struct phys2d_edge *edge)
|
||||||
|
{
|
||||||
|
for (int i = arrlen(edge->points)-1; i>=0; i--) {
|
||||||
|
phys2d_edge_rmvert(edge, i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void phys2d_edge_addverts(struct phys2d_edge *edge, cpVect *verts)
|
||||||
|
{
|
||||||
|
for (int i = 0; i < arrlen(verts); i++) {
|
||||||
|
phys2d_edgeaddvert(edge);
|
||||||
|
phys2d_edge_setvert(edge, i, verts[i]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void phys2d_applyedge(struct phys2d_edge *edge)
|
void phys2d_applyedge(struct phys2d_edge *edge)
|
||||||
{
|
{
|
||||||
float s = id2go(edge->shape.go)->scale;
|
float s = id2go(edge->shape.go)->scale;
|
||||||
|
|
|
@ -90,8 +90,11 @@ void phys2d_applyedge(struct phys2d_edge *edge);
|
||||||
void phys2d_dbgdrawedge(struct phys2d_edge *edge);
|
void phys2d_dbgdrawedge(struct phys2d_edge *edge);
|
||||||
void phys2d_edgeaddvert(struct phys2d_edge *edge);
|
void phys2d_edgeaddvert(struct phys2d_edge *edge);
|
||||||
void phys2d_edge_rmvert(struct phys2d_edge *edge, int index);
|
void phys2d_edge_rmvert(struct phys2d_edge *edge, int index);
|
||||||
|
|
||||||
void edge_gui(struct phys2d_edge *edge);
|
void edge_gui(struct phys2d_edge *edge);
|
||||||
void phys2d_edge_setvert(struct phys2d_edge *edge, int index, cpVect val);
|
void phys2d_edge_setvert(struct phys2d_edge *edge, int index, cpVect val);
|
||||||
|
void phys2d_edge_clearverts(struct phys2d_edge *edge);
|
||||||
|
void phys2d_edge_addverts(struct phys2d_edge *edge, cpVect *verts);
|
||||||
|
|
||||||
void phys2d_init();
|
void phys2d_init();
|
||||||
void phys2d_update(float deltaT);
|
void phys2d_update(float deltaT);
|
||||||
|
|
|
@ -96,6 +96,20 @@ cpBitmask duk2bitmask(duk_context *duk, int p)
|
||||||
return mask;
|
return mask;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
cpVect *duk2cpvec2arr(duk_context *duk, int p)
|
||||||
|
{
|
||||||
|
int n = duk_get_length(duk, p);
|
||||||
|
cpVect *points = NULL;
|
||||||
|
|
||||||
|
for (int i = 0; i < n; i++) {
|
||||||
|
duk_get_prop_index(duk, p, i);
|
||||||
|
|
||||||
|
arrput(points, duk2vec2(duk, -1));
|
||||||
|
}
|
||||||
|
|
||||||
|
return points;
|
||||||
|
}
|
||||||
|
|
||||||
void bitmask2duk(duk_context *duk, cpBitmask mask)
|
void bitmask2duk(duk_context *duk, cpBitmask mask)
|
||||||
{
|
{
|
||||||
int arr = duk_push_array(duk);
|
int arr = duk_push_array(duk);
|
||||||
|
@ -244,8 +258,6 @@ duk_ret_t duk_spline_cmd(duk_context *duk)
|
||||||
|
|
||||||
ts_bspline_new(n, d, duk_to_int(duk, 1), duk_to_int(duk, 3), &spline, NULL);
|
ts_bspline_new(n, d, duk_to_int(duk, 1), duk_to_int(duk, 3), &spline, NULL);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
for (int i = 0; i < n; i++) {
|
for (int i = 0; i < n; i++) {
|
||||||
duk_get_prop_index(duk, 4, i);
|
duk_get_prop_index(duk, 4, i);
|
||||||
|
|
||||||
|
@ -268,8 +280,6 @@ duk_ret_t duk_spline_cmd(duk_context *duk)
|
||||||
|
|
||||||
for (int i = 0; i < nsamples; i++) {
|
for (int i = 0; i < nsamples; i++) {
|
||||||
int pidx = duk_push_array(duk);
|
int pidx = duk_push_array(duk);
|
||||||
|
|
||||||
|
|
||||||
duk_push_number(duk, samples[i].x);
|
duk_push_number(duk, samples[i].x);
|
||||||
duk_put_prop_index(duk, pidx, 0);
|
duk_put_prop_index(duk, pidx, 0);
|
||||||
duk_push_number(duk, samples[i].y);
|
duk_push_number(duk, samples[i].y);
|
||||||
|
@ -292,6 +302,48 @@ void ints2duk(int *ints)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int point2segindex(cpVect p, cpVect *segs, double slop)
|
||||||
|
{
|
||||||
|
float shortest = slop;
|
||||||
|
int best = -1;
|
||||||
|
|
||||||
|
for (int i = 0; i < arrlen(segs)-1; i++)
|
||||||
|
{
|
||||||
|
float a = (segs[i+1].y - segs[i].y) / (segs[i+1].x - segs[i].x);
|
||||||
|
float c = segs[i].y - (a * segs[i].x);
|
||||||
|
float b = -1;
|
||||||
|
|
||||||
|
float dist = abs(a*p.x + b*p.y + c) / sqrt(pow(a,2) + 1);
|
||||||
|
|
||||||
|
if (dist < shortest) {
|
||||||
|
shortest = dist;
|
||||||
|
best = i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (best == 0) {
|
||||||
|
cpVect n;
|
||||||
|
n.x = segs[1].x-segs[0].x;
|
||||||
|
n.y = segs[1].y-segs[0].y;
|
||||||
|
n = cpvnormalize(n);
|
||||||
|
if (cpvdot(n, cpvsub(p, segs[0])) < 0 && cpvdist(p, segs[0]) >= slop)
|
||||||
|
best = -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (best == arrlen(segs)-1) {
|
||||||
|
cpVect n;
|
||||||
|
n.x = segs[best-1].x-segs[best].x;
|
||||||
|
n.y = segs[best-1].y-segs[best-1].y;
|
||||||
|
n = cpvnormalize(n);
|
||||||
|
|
||||||
|
if (cpvdot(n, cpvsub(p, segs[best])) < 0 && cpvdist(p, segs[best]) >= slop)
|
||||||
|
best = -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
return best;
|
||||||
|
}
|
||||||
|
|
||||||
duk_ret_t duk_cmd(duk_context *duk) {
|
duk_ret_t duk_cmd(duk_context *duk) {
|
||||||
int cmd = duk_to_int(duk, 0);
|
int cmd = duk_to_int(duk, 0);
|
||||||
|
|
||||||
|
@ -538,6 +590,10 @@ duk_ret_t duk_cmd(duk_context *duk) {
|
||||||
case 58:
|
case 58:
|
||||||
duk_push_boolean(duk, duk2go(duk, 1)->flipy == -1 ? 1 : 0);
|
duk_push_boolean(duk, duk2go(duk, 1)->flipy == -1 ? 1 : 0);
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
|
case 59:
|
||||||
|
duk_push_int(duk, point2segindex(duk2vec2(duk, 1), duk2cpvec2arr(duk, 2), duk_to_number(duk, 3)));
|
||||||
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
@ -917,6 +973,16 @@ duk_ret_t duk_make_edge2d(duk_context *duk)
|
||||||
|
|
||||||
duk_ret_t duk_cmd_edge2d(duk_context *duk)
|
duk_ret_t duk_cmd_edge2d(duk_context *duk)
|
||||||
{
|
{
|
||||||
|
int cmd = duk_to_int(duk, 0);
|
||||||
|
struct phys2d_edge *edge = duk_to_pointer(duk, 1);
|
||||||
|
|
||||||
|
switch(cmd) {
|
||||||
|
case 0:
|
||||||
|
phys2d_edge_clearverts(edge);
|
||||||
|
phys2d_edge_addverts(edge, duk2cpvec2arr(duk, 2));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -81,6 +81,7 @@ static void mb_cb(GLFWwindow *w, int button, int action, int mods)
|
||||||
case GLFW_RELEASE:
|
case GLFW_RELEASE:
|
||||||
act = "released";
|
act = "released";
|
||||||
rm_downkey(button);
|
rm_downkey(button);
|
||||||
|
call_input_signal("input_any_released");
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case GLFW_REPEAT:
|
case GLFW_REPEAT:
|
||||||
|
@ -124,9 +125,7 @@ void call_input_signal(char *signal) {
|
||||||
|
|
||||||
const char *keyname_extd(int key, int scancode) {
|
const char *keyname_extd(int key, int scancode) {
|
||||||
char keybuf[50];
|
char keybuf[50];
|
||||||
const char *kkey = glfwGetKeyName(key, scancode);
|
const char *kkey = NULL;
|
||||||
|
|
||||||
if (kkey) return kkey;
|
|
||||||
|
|
||||||
if (key > 289 && key < 302) {
|
if (key > 289 && key < 302) {
|
||||||
sprintf(keybuf, "f%d", key-289);
|
sprintf(keybuf, "f%d", key-289);
|
||||||
|
@ -208,12 +207,24 @@ const char *keyname_extd(int key, int scancode) {
|
||||||
case GLFW_MOUSE_BUTTON_MIDDLE:
|
case GLFW_MOUSE_BUTTON_MIDDLE:
|
||||||
kkey = "mmouse";
|
kkey = "mmouse";
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case GLFW_KEY_KP_ADD:
|
||||||
|
kkey = "plus";
|
||||||
|
break;
|
||||||
|
|
||||||
|
case GLFW_KEY_KP_SUBTRACT:
|
||||||
|
kkey = "minus";
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (kkey) return kkey;
|
if (kkey) return kkey;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
kkey = glfwGetKeyName(key, scancode);
|
||||||
|
|
||||||
|
if (kkey) return kkey;
|
||||||
|
|
||||||
return "NULL";
|
return "NULL";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -251,6 +262,7 @@ void win_key_callback(GLFWwindow *w, int key, int scancode, int action, int mods
|
||||||
case GLFW_RELEASE:
|
case GLFW_RELEASE:
|
||||||
snprintf(keystr, 50, "input_%s_released", kkey);
|
snprintf(keystr, 50, "input_%s_released", kkey);
|
||||||
rm_downkey(key);
|
rm_downkey(key);
|
||||||
|
call_input_signal("input_any_released");
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case GLFW_REPEAT:
|
case GLFW_REPEAT:
|
||||||
|
|
|
@ -17,10 +17,10 @@ static struct {
|
||||||
} *texhash = NULL;
|
} *texhash = NULL;
|
||||||
|
|
||||||
struct Texture *tex_default;
|
struct Texture *tex_default;
|
||||||
|
/* If an empty string or null is put for path, loads default texture */
|
||||||
struct Texture *texture_pullfromfile(const char *path)
|
struct Texture *texture_pullfromfile(const char *path)
|
||||||
{
|
{
|
||||||
if (!path) { YughError("Tried to pull a texture with a NULL path."); return NULL; }
|
if (!path || path[0] == '\0') { return NULL; }
|
||||||
|
|
||||||
int index = shgeti(texhash, path);
|
int index = shgeti(texhash, path);
|
||||||
if (index != -1)
|
if (index != -1)
|
||||||
|
@ -47,7 +47,7 @@ struct Texture *texture_pullfromfile(const char *path)
|
||||||
|
|
||||||
unsigned char *data = stbi_load(path, &tex->width, &tex->height, &n, 4);
|
unsigned char *data = stbi_load(path, &tex->width, &tex->height, &n, 4);
|
||||||
|
|
||||||
while (data == NULL) {
|
if (data == NULL) {
|
||||||
YughError("STBI failed to load file %s with message: %s", path, stbi_failure_reason());
|
YughError("STBI failed to load file %s with message: %s", path, stbi_failure_reason());
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
@ -120,10 +120,7 @@ struct Texture *texture_loadfromfile(const char *path)
|
||||||
{
|
{
|
||||||
struct Texture *new = texture_pullfromfile(path);
|
struct Texture *new = texture_pullfromfile(path);
|
||||||
|
|
||||||
if (new == NULL) {
|
if (new == NULL) { new = texture_pullfromfile("./ph.png"); }
|
||||||
YughError("Texture %s not loaded! Loading the default instead ...", path);
|
|
||||||
new = texture_pullfromfile("./ph.png");
|
|
||||||
}
|
|
||||||
|
|
||||||
if (new->id == 0) {
|
if (new->id == 0) {
|
||||||
glGenTextures(1, &new->id);
|
glGenTextures(1, &new->id);
|
||||||
|
@ -188,7 +185,9 @@ struct TexAnim *anim2d_from_tex(const char *path, int frames, int fps)
|
||||||
|
|
||||||
void texanim_fromframes(struct TexAnim *anim, int frames)
|
void texanim_fromframes(struct TexAnim *anim, int frames)
|
||||||
{
|
{
|
||||||
if (anim->st_frames) free(anim->st_frames);
|
if (anim->st_frames) {
|
||||||
|
free(anim->st_frames);
|
||||||
|
}
|
||||||
|
|
||||||
arrsetlen(anim->st_frames, frames);
|
arrsetlen(anim->st_frames, frames);
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue