[Bf-blender-cvs] [c1f6a49ae4c] master: Fix snapping pose mode bugs

Campbell Barton noreply at git.blender.org
Tue Dec 24 06:11:49 CET 2019


Commit: c1f6a49ae4cc01dff68a8d5fba01ab518bba67aa
Author: Campbell Barton
Date:   Tue Dec 24 15:55:35 2019 +1100
Branches: master
https://developer.blender.org/rBc1f6a49ae4cc01dff68a8d5fba01ab518bba67aa

Fix snapping pose mode bugs

- Object/pose checks were performed in same loop,
  so selected pose bones were moved instead of the object.
- Snap selected to cursor/active incorrectly used unique object-data.

===================================================================

M	source/blender/editors/space_view3d/view3d_snap.c

===================================================================

diff --git a/source/blender/editors/space_view3d/view3d_snap.c b/source/blender/editors/space_view3d/view3d_snap.c
index 07e5b20db75..13e6ea5c35a 100644
--- a/source/blender/editors/space_view3d/view3d_snap.c
+++ b/source/blender/editors/space_view3d/view3d_snap.c
@@ -70,7 +70,7 @@ static int snap_sel_to_grid_exec(bContext *C, wmOperator *UNUSED(op))
 {
   Depsgraph *depsgraph = CTX_data_ensure_evaluated_depsgraph(C);
   ViewLayer *view_layer_eval = DEG_get_evaluated_view_layer(depsgraph);
-  Object *obedit = CTX_data_edit_object(C);
+  Object *obact = CTX_data_active_object(C);
   Scene *scene = CTX_data_scene(C);
   RegionView3D *rv3d = CTX_wm_region_data(C);
   View3D *v3d = CTX_wm_view3d(C);
@@ -81,13 +81,13 @@ static int snap_sel_to_grid_exec(bContext *C, wmOperator *UNUSED(op))
 
   gridf = ED_view3d_grid_view_scale(scene, v3d, rv3d, NULL);
 
-  if (obedit) {
+  if (OBEDIT_FROM_OBACT(obact)) {
     ViewLayer *view_layer = CTX_data_view_layer(C);
     uint objects_len = 0;
     Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(
         view_layer, CTX_wm_view3d(C), &objects_len);
     for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
-      obedit = objects[ob_index];
+      Object *obedit = objects[ob_index];
 
       if (obedit->type == OB_MESH) {
         BMEditMesh *em = BKE_editmesh_from_object(obedit);
@@ -124,89 +124,96 @@ static int snap_sel_to_grid_exec(bContext *C, wmOperator *UNUSED(op))
     }
     MEM_freeN(objects);
   }
-  else {
+  else if (OBPOSE_FROM_OBACT(obact)) {
     struct KeyingSet *ks = ANIM_get_keyingset_for_autokeying(scene, ANIM_KS_LOCATION_ID);
-
-    FOREACH_SELECTED_EDITABLE_OBJECT_BEGIN (view_layer_eval, v3d, ob_eval) {
+    uint objects_len = 0;
+    Object **objects_eval = BKE_object_pose_array_get(view_layer_eval, v3d, &objects_len);
+    for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
+      Object *ob_eval = objects_eval[ob_index];
       Object *ob = DEG_get_original_object(ob_eval);
-      if (ob->mode & OB_MODE_POSE) {
-        bPoseChannel *pchan_eval;
-        bArmature *arm_eval = ob_eval->data;
-
-        invert_m4_m4(ob_eval->imat, ob_eval->obmat);
-
-        for (pchan_eval = ob_eval->pose->chanbase.first; pchan_eval;
-             pchan_eval = pchan_eval->next) {
-          if (pchan_eval->bone->flag & BONE_SELECTED) {
-            if (pchan_eval->bone->layer & arm_eval->layer) {
-              if ((pchan_eval->bone->flag & BONE_CONNECTED) == 0) {
-                float nLoc[3];
-
-                /* get nearest grid point to snap to */
-                copy_v3_v3(nLoc, pchan_eval->pose_mat[3]);
-                /* We must operate in world space! */
-                mul_m4_v3(ob_eval->obmat, nLoc);
-                vec[0] = gridf * floorf(0.5f + nLoc[0] / gridf);
-                vec[1] = gridf * floorf(0.5f + nLoc[1] / gridf);
-                vec[2] = gridf * floorf(0.5f + nLoc[2] / gridf);
-                /* Back in object space... */
-                mul_m4_v3(ob_eval->imat, vec);
-
-                /* Get location of grid point in pose space. */
-                BKE_armature_loc_pose_to_bone(pchan_eval, vec, vec);
-
-                /* adjust location on the original pchan*/
-                bPoseChannel *pchan = BKE_pose_channel_find_name(ob->pose, pchan_eval->name);
-                if ((pchan->protectflag & OB_LOCK_LOCX) == 0) {
-                  pchan->loc[0] = vec[0];
-                }
-                if ((pchan->protectflag & OB_LOCK_LOCY) == 0) {
-                  pchan->loc[1] = vec[1];
-                }
-                if ((pchan->protectflag & OB_LOCK_LOCZ) == 0) {
-                  pchan->loc[2] = vec[2];
-                }
-
-                /* auto-keyframing */
-                ED_autokeyframe_pchan(C, scene, ob, pchan, ks);
+      bPoseChannel *pchan_eval;
+      bArmature *arm_eval = ob_eval->data;
+
+      invert_m4_m4(ob_eval->imat, ob_eval->obmat);
+
+      for (pchan_eval = ob_eval->pose->chanbase.first; pchan_eval; pchan_eval = pchan_eval->next) {
+        if (pchan_eval->bone->flag & BONE_SELECTED) {
+          if (pchan_eval->bone->layer & arm_eval->layer) {
+            if ((pchan_eval->bone->flag & BONE_CONNECTED) == 0) {
+              float nLoc[3];
+
+              /* get nearest grid point to snap to */
+              copy_v3_v3(nLoc, pchan_eval->pose_mat[3]);
+              /* We must operate in world space! */
+              mul_m4_v3(ob_eval->obmat, nLoc);
+              vec[0] = gridf * floorf(0.5f + nLoc[0] / gridf);
+              vec[1] = gridf * floorf(0.5f + nLoc[1] / gridf);
+              vec[2] = gridf * floorf(0.5f + nLoc[2] / gridf);
+              /* Back in object space... */
+              mul_m4_v3(ob_eval->imat, vec);
+
+              /* Get location of grid point in pose space. */
+              BKE_armature_loc_pose_to_bone(pchan_eval, vec, vec);
+
+              /* adjust location on the original pchan*/
+              bPoseChannel *pchan = BKE_pose_channel_find_name(ob->pose, pchan_eval->name);
+              if ((pchan->protectflag & OB_LOCK_LOCX) == 0) {
+                pchan->loc[0] = vec[0];
+              }
+              if ((pchan->protectflag & OB_LOCK_LOCY) == 0) {
+                pchan->loc[1] = vec[1];
+              }
+              if ((pchan->protectflag & OB_LOCK_LOCZ) == 0) {
+                pchan->loc[2] = vec[2];
               }
-              /* if the bone has a parent and is connected to the parent,
-               * don't do anything - will break chain unless we do auto-ik.
-               */
+
+              /* auto-keyframing */
+              ED_autokeyframe_pchan(C, scene, ob, pchan, ks);
             }
+            /* if the bone has a parent and is connected to the parent,
+             * don't do anything - will break chain unless we do auto-ik.
+             */
           }
         }
-        ob->pose->flag |= (POSE_LOCKED | POSE_DO_UNLOCK);
-
-        DEG_id_tag_update(&ob->id, ID_RECALC_GEOMETRY);
       }
-      else {
-        vec[0] = -ob_eval->obmat[3][0] + gridf * floorf(0.5f + ob_eval->obmat[3][0] / gridf);
-        vec[1] = -ob_eval->obmat[3][1] + gridf * floorf(0.5f + ob_eval->obmat[3][1] / gridf);
-        vec[2] = -ob_eval->obmat[3][2] + gridf * floorf(0.5f + ob_eval->obmat[3][2] / gridf);
+      ob->pose->flag |= (POSE_LOCKED | POSE_DO_UNLOCK);
 
-        if (ob->parent) {
-          float originmat[3][3];
-          BKE_object_where_is_calc_ex(depsgraph, scene, NULL, ob, originmat);
+      DEG_id_tag_update(&ob->id, ID_RECALC_GEOMETRY);
+    }
+    MEM_freeN(objects_eval);
+  }
+  else {
+    /* Object mode. */
 
-          invert_m3_m3(imat, originmat);
-          mul_m3_v3(imat, vec);
-        }
-        if ((ob->protectflag & OB_LOCK_LOCX) == 0) {
-          ob->loc[0] = ob_eval->loc[0] + vec[0];
-        }
-        if ((ob->protectflag & OB_LOCK_LOCY) == 0) {
-          ob->loc[1] = ob_eval->loc[1] + vec[1];
-        }
-        if ((ob->protectflag & OB_LOCK_LOCZ) == 0) {
-          ob->loc[2] = ob_eval->loc[2] + vec[2];
-        }
+    struct KeyingSet *ks = ANIM_get_keyingset_for_autokeying(scene, ANIM_KS_LOCATION_ID);
 
-        /* auto-keyframing */
-        ED_autokeyframe_object(C, scene, ob, ks);
+    FOREACH_SELECTED_EDITABLE_OBJECT_BEGIN (view_layer_eval, v3d, ob_eval) {
+      Object *ob = DEG_get_original_object(ob_eval);
+      vec[0] = -ob_eval->obmat[3][0] + gridf * floorf(0.5f + ob_eval->obmat[3][0] / gridf);
+      vec[1] = -ob_eval->obmat[3][1] + gridf * floorf(0.5f + ob_eval->obmat[3][1] / gridf);
+      vec[2] = -ob_eval->obmat[3][2] + gridf * floorf(0.5f + ob_eval->obmat[3][2] / gridf);
 
-        DEG_id_tag_update(&ob->id, ID_RECALC_TRANSFORM);
+      if (ob->parent) {
+        float originmat[3][3];
+        BKE_object_where_is_calc_ex(depsgraph, scene, NULL, ob, originmat);
+
+        invert_m3_m3(imat, originmat);
+        mul_m3_v3(imat, vec);
+      }
+      if ((ob->protectflag & OB_LOCK_LOCX) == 0) {
+        ob->loc[0] = ob_eval->loc[0] + vec[0];
       }
+      if ((ob->protectflag & OB_LOCK_LOCY) == 0) {
+        ob->loc[1] = ob_eval->loc[1] + vec[1];
+      }
+      if ((ob->protectflag & OB_LOCK_LOCZ) == 0) {
+        ob->loc[2] = ob_eval->loc[2] + vec[2];
+      }
+
+      /* auto-keyframing */
+      ED_autokeyframe_object(C, scene, ob, ks);
+
+      DEG_id_tag_update(&ob->id, ID_RECALC_TRANSFORM);
     }
     FOREACH_SELECTED_EDITABLE_OBJECT_END;
   }
@@ -323,12 +330,12 @@ static int snap_selected_to_location(bContext *C,
     }
     MEM_freeN(objects);
   }
-  else if (obact && (obact->mode & OB_MODE_POSE)) {
+  else if (OBPOSE_FROM_OBACT(obact)) {
     struct KeyingSet *ks = ANIM_get_keyingset_for_autokeying(scene, ANIM_KS_LOCATION_ID);
     ViewLayer *view_layer = CTX_data_view_layer(C);
     uint objects_len = 0;
-    Object **objects = BKE_view_layer_array_from_objects_in_mode_unique_data(
-        view_layer, CTX_wm_view3d(C), &objects_len, OB_MODE_POSE);
+    Object **objects = BKE_object_pose_array_get(view_layer, v3d, &objects_len);
+
     for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
       Object *ob = objects[ob_index];
       bPoseChannel *pchan;



More information about the Bf-blender-cvs mailing list