Fix (unreported): Issues with 'SNAP_NOT_SELECTED' for pose and edit modes

This is a regression partially introduced in rB0a6f428be7f0.

Bones being transformed into edit mode were snapping to themselves.

And the bones of the pose mode weren't even snapping.

(Curious that this was not reported).
This commit is contained in:
Germano Cavalcante 2022-02-12 16:13:28 -03:00
parent 824f514f8f
commit 52be063012
Notes: blender-bot 2024-02-28 14:23:59 +01:00
Referenced by commit 9de3ed5c82, Fix T97490: snap to multiple objects with linked data can crash
Referenced by commit 4b35d6950d, Fix T96711: snap in edit mode for selected objects does not work
Referenced by issue #97710, Regression: Crash When Appending Items and Editing Expressions
Referenced by issue #97571, Motion blur create wierd artifacts on certain frames when renderring animation with cycles
Referenced by issue #96124, Cloth Filter Doesn't respect collision outer surface thickness
Referenced by issue #95759, Crash iterating over collection that (1) contains an object and (2) contains a child collection that also contains an object and setting "is_holdout"
Referenced by issue #95711, Rotate bone snapping
Referenced by issue #95230, Freezing viewport when adding ColorRamp
2 changed files with 34 additions and 12 deletions

View File

@ -628,13 +628,16 @@ static short snap_select_type_get(TransInfo *t)
else if (!t->tsnap.snap_self) {
r_snap_select = SNAP_NOT_ACTIVE;
}
else {
r_snap_select = SNAP_NOT_SELECTED;
}
}
else if ((obedit_type == -1) && base_act && base_act->object &&
(base_act->object->mode & OB_MODE_PARTICLE_EDIT)) {
/* Particles edit mode. */
}
else if (obedit_type == -1) {
/* Object mode */
/* Object or pose mode. */
r_snap_select = SNAP_NOT_SELECTED;
}
}

View File

@ -477,7 +477,10 @@ static void iter_snap_objects(SnapObjectContext *sctx,
}
}
else if (snap_select == SNAP_NOT_SELECTED) {
if ((base->flag & BASE_SELECTED) || (base->flag_legacy & BA_WAS_SEL)) {
if (is_object_active && !(base->object->mode & OB_MODE_OBJECT)) {
/* Pass. Consider the selection of elements being edited. */
}
else if ((base->flag & BASE_SELECTED) || (base->flag_legacy & BA_WAS_SEL)) {
continue;
}
}
@ -1818,6 +1821,7 @@ static short snapArmature(SnapObjectContext *sctx,
const struct SnapObjectParams *params,
Object *ob_eval,
const float obmat[4][4],
bool is_object_active,
/* read/write args */
float *dist_px,
/* return args */
@ -1838,9 +1842,10 @@ static short snapArmature(SnapObjectContext *sctx,
dist_squared_to_projected_aabb_precalc(
&neasrest_precalc, lpmat, sctx->runtime.win_size, sctx->runtime.mval);
bool use_obedit = ((bArmature *)ob_eval->data)->edbo != NULL;
bArmature *arm = ob_eval->data;
const bool is_editmode = arm->edbo != NULL;
if (use_obedit == false) {
if (is_editmode == false) {
/* Test BoundBox */
BoundBox *bb = BKE_armature_boundbox_get(ob_eval);
if (bb && !snap_bound_box_check_dist(bb->vec[0],
@ -1859,10 +1864,11 @@ static short snapArmature(SnapObjectContext *sctx,
mul_v4_m4v4(clip_planes_local[i], tobmat, sctx->runtime.clip_plane[i]);
}
const eSnapSelect snap_select = params->snap_select;
bool is_persp = sctx->runtime.view_proj == VIEW_PROJ_PERSP;
const bool is_posemode = is_object_active && (ob_eval->mode & OB_MODE_POSE);
const bool skip_selected = (is_editmode || is_posemode) &&
(params->snap_select == SNAP_NOT_SELECTED);
const bool is_persp = sctx->runtime.view_proj == VIEW_PROJ_PERSP;
bArmature *arm = ob_eval->data;
if (arm->edbo) {
LISTBASE_FOREACH (EditBone *, eBone, arm->edbo) {
if (eBone->layer & arm->layer) {
@ -1872,7 +1878,7 @@ static short snapArmature(SnapObjectContext *sctx,
}
const bool is_selected = (eBone->flag & (BONE_ROOTSEL | BONE_TIPSEL)) != 0;
if (is_selected && snap_select == SNAP_NOT_SELECTED) {
if (is_selected && skip_selected) {
continue;
}
bool has_vert_snap = false;
@ -1916,10 +1922,16 @@ static short snapArmature(SnapObjectContext *sctx,
else if (ob_eval->pose && ob_eval->pose->chanbase.first) {
LISTBASE_FOREACH (bPoseChannel *, pchan, &ob_eval->pose->chanbase) {
Bone *bone = pchan->bone;
/* skip hidden bones */
if (!bone || (bone->flag & (BONE_HIDDEN_P | BONE_HIDDEN_PG))) {
/* Skip hidden bones. */
continue;
}
const bool is_selected = (bone->flag & (BONE_SELECTED | BONE_ROOTSEL | BONE_TIPSEL)) != 0;
if (is_selected && skip_selected) {
continue;
}
bool has_vert_snap = false;
const float *head_vec = pchan->pose_head;
const float *tail_vec = pchan->pose_tail;
@ -2685,7 +2697,7 @@ static void snap_obj_fn(SnapObjectContext *sctx,
const struct SnapObjectParams *params,
Object *ob_eval,
float obmat[4][4],
bool UNUSED(is_object_active),
bool is_object_active,
void *data)
{
struct SnapObjUserData *dt = data;
@ -2721,8 +2733,15 @@ static void snap_obj_fn(SnapObjectContext *sctx,
break;
}
case OB_ARMATURE:
retval = snapArmature(
sctx, params, ob_eval, obmat, dt->dist_px, dt->r_loc, dt->r_no, dt->r_index);
retval = snapArmature(sctx,
params,
ob_eval,
obmat,
is_object_active,
dt->dist_px,
dt->r_loc,
dt->r_no,
dt->r_index);
break;
case OB_CURVE:
retval = snapCurve(