diff options
Diffstat (limited to 'source/blender/blenkernel/intern/constraint.c')
-rw-r--r-- | source/blender/blenkernel/intern/constraint.c | 134 |
1 files changed, 70 insertions, 64 deletions
diff --git a/source/blender/blenkernel/intern/constraint.c b/source/blender/blenkernel/intern/constraint.c index 8ba746e3493..3df1a84a0c9 100644 --- a/source/blender/blenkernel/intern/constraint.c +++ b/source/blender/blenkernel/intern/constraint.c @@ -368,7 +368,7 @@ static void contarget_get_mesh_mat(Object *ob, const char *substring, float mat[ /* when not in EditMode, use the 'final' evaluated mesh, depsgraph * ensures we build with CD_MDEFORMVERT layer */ - Mesh *me_eval = ob->runtime.mesh_eval; + Mesh *me_eval = BKE_object_get_evaluated_mesh(ob); BMEditMesh *em = BKE_editmesh_from_object(ob); float plane[3]; float imat[3][3], tmat[3][3]; @@ -860,94 +860,88 @@ static void childof_evaluate(bConstraint *con, bConstraintOb *cob, ListBase *tar } float parmat[4][4]; - - /* simple matrix parenting */ - if (data->flag == CHILDOF_ALL) { - - /* multiply target (parent matrix) by offset (parent inverse) to get - * the effect of the parent that will be exerted on the owner - */ - mul_m4_m4m4(parmat, ct->matrix, data->invmat); - - /* now multiply the parent matrix by the owner matrix to get the - * the effect of this constraint (i.e. owner is 'parented' to parent) - */ - mul_m4_m4m4(cob->matrix, parmat, cob->matrix); + /* Simple matrix parenting. */ + if ((data->flag & CHILDOF_ALL) == CHILDOF_ALL) { + copy_m4_m4(parmat, ct->matrix); } + /* Filter the parent matrix by channel. */ else { - float invmat[4][4], tempmat[4][4]; float loc[3], eul[3], size[3]; - float loco[3], eulo[3], sizo[3]; - - /* get offset (parent-inverse) matrix */ - copy_m4_m4(invmat, data->invmat); /* extract components of both matrices */ copy_v3_v3(loc, ct->matrix[3]); mat4_to_eulO(eul, ct->rotOrder, ct->matrix); mat4_to_size(size, ct->matrix); - copy_v3_v3(loco, invmat[3]); - mat4_to_eulO(eulo, cob->rotOrder, invmat); - mat4_to_size(sizo, invmat); - /* disable channels not enabled */ if (!(data->flag & CHILDOF_LOCX)) { - loc[0] = loco[0] = 0.0f; + loc[0] = 0.0f; } if (!(data->flag & CHILDOF_LOCY)) { - loc[1] = loco[1] = 0.0f; + loc[1] = 0.0f; } if (!(data->flag & CHILDOF_LOCZ)) { - loc[2] = loco[2] = 0.0f; + loc[2] = 0.0f; } if (!(data->flag & CHILDOF_ROTX)) { - eul[0] = eulo[0] = 0.0f; + eul[0] = 0.0f; } if (!(data->flag & CHILDOF_ROTY)) { - eul[1] = eulo[1] = 0.0f; + eul[1] = 0.0f; } if (!(data->flag & CHILDOF_ROTZ)) { - eul[2] = eulo[2] = 0.0f; + eul[2] = 0.0f; } if (!(data->flag & CHILDOF_SIZEX)) { - size[0] = sizo[0] = 1.0f; + size[0] = 1.0f; } if (!(data->flag & CHILDOF_SIZEY)) { - size[1] = sizo[1] = 1.0f; + size[1] = 1.0f; } if (!(data->flag & CHILDOF_SIZEZ)) { - size[2] = sizo[2] = 1.0f; + size[2] = 1.0f; } /* make new target mat and offset mat */ - loc_eulO_size_to_mat4(ct->matrix, loc, eul, size, ct->rotOrder); - loc_eulO_size_to_mat4(invmat, loco, eulo, sizo, cob->rotOrder); + loc_eulO_size_to_mat4(parmat, loc, eul, size, ct->rotOrder); + } - /* multiply target (parent matrix) by offset (parent inverse) to get - * the effect of the parent that will be exerted on the owner - */ - mul_m4_m4m4(parmat, ct->matrix, invmat); + /* Compute the inverse matrix if requested. */ + if (data->flag & CHILDOF_SET_INVERSE) { + invert_m4_m4(data->invmat, parmat); - /* now multiply the parent matrix by the owner matrix to get the - * the effect of this constraint (i.e. owner is 'parented' to parent) - */ - copy_m4_m4(tempmat, cob->matrix); - mul_m4_m4m4(cob->matrix, parmat, tempmat); + data->flag &= ~CHILDOF_SET_INVERSE; - /* without this, changes to scale and rotation can change location - * of a parentless bone or a disconnected bone. Even though its set - * to zero above. */ - if (!(data->flag & CHILDOF_LOCX)) { - cob->matrix[3][0] = tempmat[3][0]; - } - if (!(data->flag & CHILDOF_LOCY)) { - cob->matrix[3][1] = tempmat[3][1]; - } - if (!(data->flag & CHILDOF_LOCZ)) { - cob->matrix[3][2] = tempmat[3][2]; + /* Write the computed matrix back to the master copy if in COW evaluation. */ + bConstraint *orig_con = constraint_find_original_for_update(cob, con); + + if (orig_con != NULL) { + bChildOfConstraint *orig_data = orig_con->data; + + copy_m4_m4(orig_data->invmat, data->invmat); + orig_data->flag &= ~CHILDOF_SET_INVERSE; } } + + /* Multiply together the target (parent) matrix, parent inverse, + * and the owner transform matrixto get the effect of this constraint + * (i.e. owner is 'parented' to parent). */ + float orig_cob_matrix[4][4]; + copy_m4_m4(orig_cob_matrix, cob->matrix); + mul_m4_series(cob->matrix, parmat, data->invmat, orig_cob_matrix); + + /* Without this, changes to scale and rotation can change location + * of a parentless bone or a disconnected bone. Even though its set + * to zero above. */ + if (!(data->flag & CHILDOF_LOCX)) { + cob->matrix[3][0] = orig_cob_matrix[3][0]; + } + if (!(data->flag & CHILDOF_LOCY)) { + cob->matrix[3][1] = orig_cob_matrix[3][1]; + } + if (!(data->flag & CHILDOF_LOCZ)) { + cob->matrix[3][2] = orig_cob_matrix[3][2]; + } } /* XXX note, con->flag should be CONSTRAINT_SPACEONCE for bone-childof, patched in readfile.c */ @@ -3974,7 +3968,7 @@ static void shrinkwrap_get_tarmat(struct Depsgraph *UNUSED(depsgraph), float track_no[3] = {0.0f, 0.0f, 0.0f}; SpaceTransform transform; - Mesh *target_eval = ct->tar->runtime.mesh_eval; + Mesh *target_eval = BKE_object_get_evaluated_mesh(ct->tar); copy_m4_m4(ct->matrix, cob->matrix); @@ -4742,7 +4736,7 @@ static void followtrack_evaluate(bConstraint *con, bConstraintOb *cob, ListBase if (data->depth_ob) { Object *depth_ob = data->depth_ob; - Mesh *target_eval = depth_ob->runtime.mesh_eval; + Mesh *target_eval = BKE_object_get_evaluated_mesh(depth_ob); if (target_eval) { BVHTreeFromMesh treeData = NULL_BVHTreeFromMesh; BVHTreeRayHit hit; @@ -4891,23 +4885,35 @@ static void objectsolver_evaluate(bConstraint *con, bConstraintOb *cob, ListBase return; } - float mat[4][4], obmat[4][4], imat[4][4], cammat[4][4], camimat[4][4], parmat[4][4]; + float mat[4][4], obmat[4][4], imat[4][4], parmat[4][4]; float ctime = DEG_get_ctime(depsgraph); float framenr = BKE_movieclip_remap_scene_to_clip_frame(clip, ctime); - BKE_object_where_is_calc_mat4(camob, cammat); - BKE_tracking_camera_get_reconstructed_interpolate(tracking, object, framenr, mat); - invert_m4_m4(camimat, cammat); - mul_m4_m4m4(parmat, cammat, data->invmat); + invert_m4_m4(imat, mat); + mul_m4_m4m4(parmat, camob->obmat, imat); - copy_m4_m4(cammat, camob->obmat); copy_m4_m4(obmat, cob->matrix); - invert_m4_m4(imat, mat); + /* Recalculate the inverse matrix if requested. */ + if (data->flag & OBJECTSOLVER_SET_INVERSE) { + invert_m4_m4(data->invmat, parmat); + + data->flag &= ~OBJECTSOLVER_SET_INVERSE; + + /* Write the computed matrix back to the master copy if in COW evaluation. */ + bConstraint *orig_con = constraint_find_original_for_update(cob, con); + + if (orig_con != NULL) { + bObjectSolverConstraint *orig_data = orig_con->data; + + copy_m4_m4(orig_data->invmat, data->invmat); + orig_data->flag &= ~OBJECTSOLVER_SET_INVERSE; + } + } - mul_m4_series(cob->matrix, cammat, imat, camimat, parmat, obmat); + mul_m4_series(cob->matrix, parmat, data->invmat, obmat); } static bConstraintTypeInfo CTI_OBJECTSOLVER = { |