diff options
author | Bastien Montagne <montagne29@wanadoo.fr> | 2016-05-13 12:05:12 +0300 |
---|---|---|
committer | Bastien Montagne <montagne29@wanadoo.fr> | 2016-05-13 13:06:15 +0300 |
commit | 029ccca0feb2d74180aa7693f9118b781bad29a7 (patch) | |
tree | 670567f9fc96aa24556be9d706f6d3657e01d803 /source | |
parent | 868cfc5a4a04f3f22f891ad3213cee5ceddea009 (diff) |
Armature meshdeform evaluation: parallelize computation of bbones deform matrices.
On big and complex rigs like blendrig or koro, it can give up to ~10% more FPS in best cases.
Hard to tackle all cases in tests though, so please report any unexpected slowdown
in armature animation playback!
Diffstat (limited to 'source')
-rw-r--r-- | source/blender/blenkernel/intern/armature.c | 45 |
1 files changed, 32 insertions, 13 deletions
diff --git a/source/blender/blenkernel/intern/armature.c b/source/blender/blenkernel/intern/armature.c index 564c670fb3a..1a3afbb876e 100644 --- a/source/blender/blenkernel/intern/armature.c +++ b/source/blender/blenkernel/intern/armature.c @@ -41,6 +41,7 @@ #include "BLI_listbase.h" #include "BLI_string.h" #include "BLI_ghash.h" +#include "BLI_task.h" #include "BLI_utildefines.h" #include "DNA_anim_types.h" @@ -48,6 +49,7 @@ #include "DNA_constraint_types.h" #include "DNA_mesh_types.h" #include "DNA_lattice_types.h" +#include "DNA_listBase.h" #include "DNA_meshdata_types.h" #include "DNA_scene_types.h" #include "DNA_object_types.h" @@ -854,6 +856,32 @@ static void pchan_bone_deform(bPoseChannel *pchan, bPoseChanDeform *pdef_info, f (*contrib) += weight; } +typedef struct ArmatureBBoneDefmatsData { + bPoseChanDeform *pdef_info_array; + DualQuat *dualquats; + bool use_quaternion; +} ArmatureBBoneDefmatsData; + +static void armature_bbone_defmats_cb(void *userdata, Link *iter, int index) +{ + ArmatureBBoneDefmatsData *data = userdata; + bPoseChannel *pchan = (bPoseChannel *)iter; + + if (!(pchan->bone->flag & BONE_NO_DEFORM)) { + bPoseChanDeform *pdef_info = &data->pdef_info_array[index]; + const bool use_quaternion = data->use_quaternion; + + if (pchan->bone->segments > 1) { + pchan_b_bone_defmats(pchan, pdef_info, use_quaternion); + } + + if (use_quaternion) { + pdef_info->dual_quat = &data->dualquats[index]; + mat4_to_dquat(pdef_info->dual_quat, pchan->bone->arm_mat, pchan->chan_mat); + } + } +} + void armature_deform_verts(Object *armOb, Object *target, DerivedMesh *dm, float (*vertexCos)[3], float (*defMats)[3][3], int numVerts, int deformflag, float (*prevCos)[3], const char *defgrp_name) @@ -897,19 +925,10 @@ void armature_deform_verts(Object *armOb, Object *target, DerivedMesh *dm, float pdef_info_array = MEM_callocN(sizeof(bPoseChanDeform) * totchan, "bPoseChanDeform"); - totchan = 0; - pdef_info = pdef_info_array; - for (pchan = armOb->pose->chanbase.first; pchan; pchan = pchan->next, pdef_info++) { - if (!(pchan->bone->flag & BONE_NO_DEFORM)) { - if (pchan->bone->segments > 1) - pchan_b_bone_defmats(pchan, pdef_info, use_quaternion); - - if (use_quaternion) { - pdef_info->dual_quat = &dualquats[totchan++]; - mat4_to_dquat(pdef_info->dual_quat, pchan->bone->arm_mat, pchan->chan_mat); - } - } - } + ArmatureBBoneDefmatsData data = { + .pdef_info_array = pdef_info_array, .dualquats = dualquats, .use_quaternion = use_quaternion + }; + BLI_task_parallel_listbase(&armOb->pose->chanbase, &data, armature_bbone_defmats_cb, totchan > 512); /* get the def_nr for the overall armature vertex group if present */ armature_def_nr = defgroup_name_index(target, defgrp_name); |