{
u32 bone_id;
v3f offset;
- rigidbody rb;
+
+ u32 use_limits;
+ v3f limits[2];
+
+ rigidbody rb;
+ u32 parent;
}
*ragdoll;
u32 ragdoll_count;
v3_add( bone->co, rp->offset, rp->rb.co );
rp->rb.type = k_rb_shape_box;
rp->rb.is_world = 0;
+ rp->parent = 0xffffffff;
+
+ if( bone->parent )
+ {
+ for( u32 j=0; j<ch->ragdoll_count; j++ )
+ {
+ if( ch->ragdoll[ j ].bone_id == bone->parent )
+ {
+ rp->parent = j;
+ break;
+ }
+ }
+ }
+
+ /* TODO: refactor to use this style elswhere */
+ struct mdl_node *pnode = mdl_node_from_id( src, bone->orig_node );
+ struct classtype_bone *bone_inf = mdl_get_entdata( src, pnode );
+
+ rp->use_limits = bone_inf->use_limits;
+ v3_copy( bone_inf->angle_limits[0], rp->limits[0] );
+ v3_copy( bone_inf->angle_limits[1], rp->limits[1] );
rb_init( &rp->rb );
}
static void character_init_ragdoll_joints( struct character *ch ){}
static void character_init_ragdoll( struct character *ch ){}
static void character_ragdoll_go( struct character *ch, v3f pos ){}
+
+static void character_mimic_ragdoll( struct character *ch )
+{
+ for( int i=0; i<ch->ragdoll_count; i++ )
+ {
+ struct ragdoll_part *part = &ch->ragdoll[i];
+ m4x3f offset;
+ m3x3_identity(offset);
+ v3_negate( part->offset, offset[3] );
+ m4x3_mul( part->rb.to_world, offset, ch->sk.final_mtx[part->bone_id] );
+ }
+
+ skeleton_apply_inverses( &ch->sk );
+}
+
static void character_ragdoll_copypose( struct character *ch, v3f v )
{
for( int i=0; i<ch->ragdoll_count; i++ )
if( ch->shoes[i] )
shoe_vel[i] = v3_length( ch->ragdoll[i].rb.v );
+ for( int j=0; j<ch->ragdoll_count; j++ )
+ {
+ struct ragdoll_part *pj = &ch->ragdoll[j];
+ struct skeleton_bone *bj = &ch->sk.bones[pj->bone_id];
+
+ if( pj->parent != 0xffffffff )
+ {
+ struct ragdoll_part *pp = &ch->ragdoll[pj->parent];
+ struct skeleton_bone *bp = &ch->sk.bones[pp->bone_id];
+
+ v3f lca, lcb;
+ v3_negate( pj->offset, lca );
+ v3_add( bp->co, pp->offset, lcb );
+ v3_sub( bj->co, lcb, lcb );
+
+ rb_debug_constraint_position( &pj->rb, lca, &pp->rb, lcb );
+
+ if( pj->use_limits )
+ {
+ rb_debug_constraint_limits( &pj->rb, &pp->rb, lca, pj->limits );
+ }
+ }
+ }
+
/* CONSTRAINTS */
- for( int i=0; i<5; i++ )
+ for( int i=0; i<10; i++ )
{
rb_solve_contacts( rb_contact_buffer, rb_contact_count );
+
+ for( int j=0; j<ch->ragdoll_count; j++ )
+ {
+ struct ragdoll_part *pj = &ch->ragdoll[j];
+ struct skeleton_bone *bj = &ch->sk.bones[pj->bone_id];
+
+ if( pj->parent != 0xffffffff && pj->use_limits )
+ {
+ struct ragdoll_part *pp = &ch->ragdoll[pj->parent];
+ struct skeleton_bone *bp = &ch->sk.bones[pp->bone_id];
+
+ v3f lca, lcb;
+ v3_negate( pj->offset, lca );
+ v3_add( bp->co, pp->offset, lcb );
+ v3_sub( bj->co, lcb, lcb );
+
+ rb_constraint_position( &pj->rb, lca, &pp->rb, lcb );
+
+ rb_constraint_limits( &pj->rb, lca, &pp->rb, lcb, pj->limits );
+ }
+ }
}
/* INTEGRATION */