skeleton animation
This commit is contained in:
parent
f5a89915eb
commit
a29ce7e8d0
|
@ -1933,7 +1933,6 @@ JSC_CCALL(transform_rotate,
|
||||||
transform *t = js2transform(self);
|
transform *t = js2transform(self);
|
||||||
HMM_Quat rot = HMM_QFromAxisAngle_LH(axis, js2angle(argv[1]));
|
HMM_Quat rot = HMM_QFromAxisAngle_LH(axis, js2angle(argv[1]));
|
||||||
t->rotation = HMM_MulQ(t->rotation,rot);
|
t->rotation = HMM_MulQ(t->rotation,rot);
|
||||||
printf("rotation is now %g,%g,%g,%g\n", t->rotation.e[0], t->rotation.e[1], t->rotation.e[2], t->rotation.e[3]);
|
|
||||||
t->dirty = true;
|
t->dirty = true;
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -2960,7 +2959,7 @@ JSC_SCALL(os_gltf_skin,
|
||||||
goto CLEANUP;
|
goto CLEANUP;
|
||||||
}
|
}
|
||||||
|
|
||||||
ret = skin2js(make_gltf_skin(data->skins+0));
|
ret = skin2js(make_gltf_skin(data->skins+0, data));
|
||||||
|
|
||||||
CLEANUP:
|
CLEANUP:
|
||||||
cgltf_free(data);
|
cgltf_free(data);
|
||||||
|
|
|
@ -164,7 +164,14 @@ void packFloats(float *src, float *dest, int srcLength) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
animation *gltf_anim(cgltf_animation *anim)
|
static md5joint *node2joint(skin *sk, cgltf_node *n, cgltf_skin *skin)
|
||||||
|
{
|
||||||
|
int k = 0;
|
||||||
|
while (skin->joints[k] != n && k < skin->joints_count) k++;
|
||||||
|
return sk->joints+k;
|
||||||
|
}
|
||||||
|
|
||||||
|
animation *gltf_anim(cgltf_animation *anim, skin *sk, cgltf_skin *skin)
|
||||||
{
|
{
|
||||||
animation *ret = calloc(sizeof(*ret), 1);
|
animation *ret = calloc(sizeof(*ret), 1);
|
||||||
animation an = *ret;
|
animation an = *ret;
|
||||||
|
@ -200,7 +207,7 @@ animation *gltf_anim(cgltf_animation *anim)
|
||||||
for (int i = 0; i < anim->channels_count; i++) {
|
for (int i = 0; i < anim->channels_count; i++) {
|
||||||
cgltf_animation_channel ch = anim->channels[i];
|
cgltf_animation_channel ch = anim->channels[i];
|
||||||
struct anim_channel ach = (struct anim_channel){0};
|
struct anim_channel ach = (struct anim_channel){0};
|
||||||
md5joint *md = NULL;
|
md5joint *md = node2joint(sk, ch.target_node, skin);
|
||||||
switch(ch.target_path) {
|
switch(ch.target_path) {
|
||||||
case cgltf_animation_path_type_translation:
|
case cgltf_animation_path_type_translation:
|
||||||
ach.target = &md->pos;
|
ach.target = &md->pos;
|
||||||
|
@ -218,10 +225,13 @@ animation *gltf_anim(cgltf_animation *anim)
|
||||||
arrput(an.channels, ach);
|
arrput(an.channels, ach);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
an.time = 0;
|
||||||
|
|
||||||
*ret = an;
|
*ret = an;
|
||||||
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
skin *make_gltf_skin(cgltf_skin *skin)
|
skin *make_gltf_skin(cgltf_skin *skin, cgltf_data *data)
|
||||||
{
|
{
|
||||||
int n = cgltf_accessor_unpack_floats(skin->inverse_bind_matrices, NULL, 0);
|
int n = cgltf_accessor_unpack_floats(skin->inverse_bind_matrices, NULL, 0);
|
||||||
struct skin *sk = NULL;
|
struct skin *sk = NULL;
|
||||||
|
@ -236,10 +246,13 @@ skin *make_gltf_skin(cgltf_skin *skin)
|
||||||
|
|
||||||
for (int i = 0; i < skin->joints_count; i++) {
|
for (int i = 0; i < skin->joints_count; i++) {
|
||||||
cgltf_node *n = skin->joints[i];
|
cgltf_node *n = skin->joints[i];
|
||||||
int idx = n-skin->skeleton;
|
md5joint *j = sk->joints+i;
|
||||||
int parent_idx = n->parent-skin->skeleton;
|
|
||||||
md5joint *j = sk->joints+idx;
|
if (n == skin->skeleton)
|
||||||
j->parent = sk->joints+parent_idx;
|
j->parent = NULL;
|
||||||
|
else
|
||||||
|
j->parent = node2joint(sk, n->parent, skin);
|
||||||
|
|
||||||
for (int i = 0; i < 3; i++) {
|
for (int i = 0; i < 3; i++) {
|
||||||
j->pos.e[i] = n->translation[i];
|
j->pos.e[i] = n->translation[i];
|
||||||
j->scale.e[i] = n->scale[i];
|
j->scale.e[i] = n->scale[i];
|
||||||
|
@ -248,17 +261,20 @@ skin *make_gltf_skin(cgltf_skin *skin)
|
||||||
j->rot.e[i] = n->rotation[i];
|
j->rot.e[i] = n->rotation[i];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
sk->anim = gltf_anim(data->animations+0, sk, skin);
|
||||||
|
|
||||||
return sk;
|
return sk;
|
||||||
}
|
}
|
||||||
|
|
||||||
void skin_calculate(skin *sk)
|
void skin_calculate(skin *sk)
|
||||||
{
|
{
|
||||||
|
animation_run(sk->anim, apptime());
|
||||||
for (int i = 0; i < arrlen(sk->joints); i++) {
|
for (int i = 0; i < arrlen(sk->joints); i++) {
|
||||||
md5joint *md = sk->joints+i;
|
md5joint *md = sk->joints+i;
|
||||||
HMM_Mat4 local = HMM_M4TRS(md->pos.xyz, md->rot, md->scale.xyz);
|
md->t = HMM_M4TRS(md->pos.xyz, md->rot, md->scale.xyz);
|
||||||
if (md->parent)
|
if (md->parent)
|
||||||
local = HMM_MulM4(md->parent->t, local);
|
md->t = HMM_MulM4(md->parent->t, md->t);
|
||||||
md->t = local;
|
|
||||||
sk->binds[i] = HMM_MulM4(md->t, sk->invbind[i]);
|
sk->binds[i] = HMM_MulM4(md->t, sk->invbind[i]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -35,10 +35,11 @@ typedef struct skin {
|
||||||
md5joint *joints;
|
md5joint *joints;
|
||||||
HMM_Mat4 *invbind;
|
HMM_Mat4 *invbind;
|
||||||
HMM_Mat4 binds[50]; /* binds = joint * invbind */
|
HMM_Mat4 binds[50]; /* binds = joint * invbind */
|
||||||
|
animation *anim;
|
||||||
} skin;
|
} skin;
|
||||||
|
|
||||||
sg_buffer accessor2buffer(cgltf_accessor *a, int type);
|
sg_buffer accessor2buffer(cgltf_accessor *a, int type);
|
||||||
skin *make_gltf_skin(cgltf_skin *skin);
|
skin *make_gltf_skin(cgltf_skin *skin, cgltf_data *data);
|
||||||
void skin_calculate(skin *sk);
|
void skin_calculate(skin *sk);
|
||||||
|
|
||||||
sg_buffer float_buffer(float *f, int v);
|
sg_buffer float_buffer(float *f, int v);
|
||||||
|
|
Loading…
Reference in a new issue