Commit: 950c2eaf614e895f5856d08faa8e86024b75ef85
Author: Germano Cavalcante
Date:   Wed Jul 6 11:34:28 2016 +1000
Branches: master
https://developer.blender.org/rB950c2eaf614e895f5856d08faa8e86024b75ef85

Transform Snap: Replace pixel limit w/ 'dist_to_ray_sq'

When snapping to edge/vert, check the distance to the ray
instead of the screen-space pixel projection.

This also corrects the conversion of `dist_to_ray_sq` to `dist_px` which was 
being done incorrectly.

While this change was planned, it fixes T48791, caused by error in b01a56ee.

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

M       source/blender/editors/transform/transform_snap_object.c

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

diff --git a/source/blender/editors/transform/transform_snap_object.c 
b/source/blender/editors/transform/transform_snap_object.c
index e85b686..c703b87 100644
--- a/source/blender/editors/transform/transform_snap_object.c
+++ b/source/blender/editors/transform/transform_snap_object.c
@@ -221,170 +221,115 @@ static void raycast_all_cb(void *userdata, int index, 
const BVHTreeRay *ray, BVH
 /** \name Internal Object Snapping API
  * \{ */
 
-static bool snapEdge(
-        const ARegion *ar, const float v1co[3], const short v1no[3], const 
float v2co[3], const short v2no[3],
-        float obmat[4][4], float timat[3][3], const float mval_fl[2],
-        const float ray_start[3], const float ray_start_local[3], const float 
ray_normal_local[3],
+#define V3_MUL_ELEM(a, b) \
+       (a)[0] * (b)[0], \
+       (a)[1] * (b)[1], \
+       (a)[2] * (b)[2]
+
+static bool test_vert(
+        const float vco[3], const float vno[3], const float ray_co[3], const 
float ray_dir[3],
+        const float ray_depth_range[2], const float scale[3], const bool 
is_persp,
         /* read/write args */
-        float *ray_depth, float *dist_px,
+        float *ray_depth, float *dist_to_ray_sq,
         /* return args */
-        float r_loc[3], float r_no[3])
+        float r_co[3], float r_no[3])
 {
-       float intersect[3] = {0, 0, 0}, ray_end[3], dvec[3];
-       int result;
-       bool retval = false;
-
-       copy_v3_v3(ray_end, ray_normal_local);
-       mul_v3_fl(ray_end, 2000);
-       add_v3_v3v3(ray_end, ray_start_local, ray_end);
+       const float vco_sc[3]   = {V3_MUL_ELEM(vco, scale)};
+       const float co_sc[3]    = {V3_MUL_ELEM(ray_co, scale)};
+       const float dir_sc[3]   = {V3_MUL_ELEM(ray_dir, scale)};
 
-       /* dvec used but we don't care about result */
-       result = isect_line_line_v3(v1co, v2co, ray_start_local, ray_end, 
intersect, dvec);
+       float depth;
+       float dist_sq = dist_squared_to_ray_v3(co_sc, dir_sc, vco_sc, &depth);
 
-       if (result) {
-               float edge_loc[3], vec[3];
-               float mul;
+       if (depth < ray_depth_range[0]) {
+               return false;
+       }
 
-               /* check for behind ray_start */
-               sub_v3_v3v3(dvec, intersect, ray_start_local);
+       if (is_persp) {
+               dist_sq /= SQUARE(depth);
+       }
 
-               sub_v3_v3v3(edge_loc, v1co, v2co);
-               sub_v3_v3v3(vec, intersect, v2co);
+       if ((dist_sq < *dist_to_ray_sq) && (depth < *ray_depth)) {
+               *dist_to_ray_sq = dist_sq;
 
-               mul = dot_v3v3(vec, edge_loc) / dot_v3v3(edge_loc, edge_loc);
+               copy_v3_v3(r_co, vco);
 
-               if (mul > 1) {
-                       mul = 1;
-                       copy_v3_v3(intersect, v1co);
-               }
-               else if (mul < 0) {
-                       mul = 0;
-                       copy_v3_v3(intersect, v2co);
+               if (vno) {
+                       copy_v3_v3(r_no, vno);
                }
 
-               if (dot_v3v3(ray_normal_local, dvec) > 0) {
-                       float location[3];
-                       float new_depth;
-                       float screen_loc[2];
-                       float new_dist;
-
-                       copy_v3_v3(location, intersect);
-
-                       mul_m4_v3(obmat, location);
-
-                       new_depth = len_v3v3(location, ray_start);
-
-                       if (ED_view3d_project_float_global(ar, location, 
screen_loc, V3D_PROJ_TEST_NOP) == V3D_PROJ_RET_OK) {
-                               new_dist = len_manhattan_v2v2(mval_fl, 
screen_loc);
-                       }
-                       else {
-                               new_dist = TRANSFORM_DIST_MAX_PX;
-                       }
-
-                       /* 10% threshold if edge is closer but a bit further
-                        * this takes care of series of connected edges a bit 
slanted w.r.t the viewport
-                        * otherwise, it would stick to the verts of the 
closest edge and not slide along merrily
-                        * */
-                       if (new_dist <= *dist_px && new_depth < *ray_depth * 
1.001f) {
-                               float n1[3], n2[3];
-
-                               *ray_depth = new_depth;
-                               retval = true;
-
-                               sub_v3_v3v3(edge_loc, v1co, v2co);
-                               sub_v3_v3v3(vec, intersect, v2co);
-
-                               mul = dot_v3v3(vec, edge_loc) / 
dot_v3v3(edge_loc, edge_loc);
-
-                               if (r_no) {
-                                       normal_short_to_float_v3(n1, v1no);
-                                       normal_short_to_float_v3(n2, v2no);
-                                       interp_v3_v3v3(r_no, n2, n1, mul);
-                                       mul_m3_v3(timat, r_no);
-                                       normalize_v3(r_no);
-                               }
-
-                               copy_v3_v3(r_loc, location);
-
-                               *dist_px = new_dist;
-                       }
-               }
+               *ray_depth = depth;
+               return true;
        }
-
-       return retval;
+       return false;
 }
 
-static bool snapVertex(
-        const ARegion *ar, const float vco[3], const float vno[3],
-        float obmat[4][4], float timat[3][3], const float mval_fl[2],
-        const float ray_start[3], const float ray_start_local[3], const float 
ray_normal_local[3],
+static bool test_edge(
+        const float v1[3], const float v2[3], const float ray_co[3], const 
float ray_dir[3],
+        const float ray_depth_range[2], const float scale[3], const bool 
is_persp,
         /* read/write args */
-        float *ray_depth, float *dist_px,
+        float *ray_depth, float *dist_to_ray_sq,
         /* return args */
-        float r_loc[3], float r_no[3])
+        float r_co[3], float r_no[3])
 {
-       bool retval = false;
-       float dvec[3];
-
-       sub_v3_v3v3(dvec, vco, ray_start_local);
+       const float v1_sc[3]    = {V3_MUL_ELEM(v1, scale)};
+       const float v2_sc[3]    = {V3_MUL_ELEM(v2, scale)};
+       const float co_sc[3]    = {V3_MUL_ELEM(ray_co, scale)};
+       const float dir_sc[3]   = {V3_MUL_ELEM(ray_dir, scale)};
 
-       if (dot_v3v3(ray_normal_local, dvec) > 0) {
-               float location[3];
-               float new_depth;
-               float screen_loc[2];
-               float new_dist;
-
-               copy_v3_v3(location, vco);
-
-               mul_m4_v3(obmat, location);
-
-               new_depth = len_v3v3(location, ray_start);
+       float tmp_co[3], depth;
+       float dist_sq = dist_squared_ray_to_seg_v3(co_sc, dir_sc, v1_sc, v2_sc, 
tmp_co, &depth);
 
-               if (ED_view3d_project_float_global(ar, location, screen_loc, 
V3D_PROJ_TEST_NOP) == V3D_PROJ_RET_OK) {
-                       new_dist = len_manhattan_v2v2(mval_fl, screen_loc);
-               }
-               else {
-                       new_dist = TRANSFORM_DIST_MAX_PX;
-               }
+       if (depth < ray_depth_range[0]) {
+               return false;
+       }
 
+       if (is_persp) {
+               dist_sq /= SQUARE(depth);
+       }
 
-               if (new_dist <= *dist_px && new_depth < *ray_depth) {
-                       *ray_depth = new_depth;
-                       retval = true;
+       if ((dist_sq < *dist_to_ray_sq) && (depth < *ray_depth)) {
+               *dist_to_ray_sq = dist_sq;
 
-                       copy_v3_v3(r_loc, location);
+               tmp_co[0] /= scale[0];
+               tmp_co[1] /= scale[1];
+               tmp_co[2] /= scale[2];
 
-                       if (r_no) {
-                               copy_v3_v3(r_no, vno);
-                               mul_m3_v3(timat, r_no);
-                               normalize_v3(r_no);
-                       }
+               copy_v3_v3(r_co, tmp_co);
 
-                       *dist_px = new_dist;
+               if (r_no) {
+                       sub_v3_v3v3(r_no, v1, v2);
                }
-       }
 
-       return retval;
+               *ray_depth = depth;
+               return true;
+       }
+       return false;
 }
 
+#undef V3_MUL_ELEM
+
 static bool snapArmature(
-        const ARegion *ar, Object *ob, bArmature *arm, float obmat[4][4],
-        const float mval[2], const short snap_to,
-        const float ray_start[3], const float ray_normal[3],
+        Object *ob, bArmature *arm, float obmat[4][4],
+        const short snap_to, const bool is_persp,
+        const float ray_origin[3], const float ray_normal[3], const float 
ray_depth_range[2],
         /* read/write args */
-        float *ray_depth, float *dist_px,
+        float *ray_depth, float *dist_to_ray_sq,
         /* return args */
         float r_loc[3], float *UNUSED(r_no))
 {
        float imat[4][4];
-       float ray_start_local[3], ray_normal_local[3];
+       float ray_origin_local[3], ray_normal_local[3];
        bool retval = false;
 
        invert_m4_m4(imat, obmat);
 
-       mul_v3_m4v3(ray_start_local, imat, ray_start);
+       mul_v3_m4v3(ray_origin_local, imat, ray_origin);
        mul_v3_mat3_m4v3(ray_normal_local, imat, ray_normal);
 
+       float ob_scale[3];
+       mat4_to_size(ob_scale, obmat);
+
        if (arm->edbo) {
                EditBone *eBone;
 
@@ -394,21 +339,20 @@ static bool snapArmature(
                                if ((eBone->flag & (BONE_HIDDEN_A | 
BONE_ROOTSEL | BONE_TIPSEL)) == 0) {
                                        switch (snap_to) {
                                                case SCE_SNAP_MODE_VERTEX:
-                                                       retval |= snapVertex(
-                                                               ar, 
eBone->head, NULL, obmat, NULL, mval, dist_px,
-                                                               ray_start, 
ray_start_local, ray_normal_local, ray_depth,
+                                                       retval |= test_vert(
+                                                               eBone->head, 
NULL, ray_origin_local, ray_normal_local,
+                                                               
ray_depth_range, ob_scale, is_persp, ray_depth, dist_to_ray_sq,
                                                                r_loc, NULL);
-                                                       retval |= snapVertex(
-                                                               ar, 
eBone->tail, NULL, obmat, NULL, mval, dist_px,
-                                                               ray_start, 
ray_start_local, ray_normal_local, ray_depth,
+                                                       retval |= test_vert(
+                                                               eBone->tail, 
NULL, ray_origin_local, ray_normal_local,
+                                                               
ray_depth_range, ob_scale, is_persp, ray_depth, dist_to_ray_sq,
                                                                r_loc, NULL);
                                                        break;
                                                case SCE_SNAP_MODE_EDGE:
-                                                       retval |= snapEdge(
-                                                               ar, 
eBone->head, NULL, eBone->tail, NULL,
-                                                               obmat, NULL, 
mval, dist_px,
-                                                               ray_start, 
ray_start_local, ray_normal_local,
-                                                               ray_depth, 
r_loc, NULL);
+                                                       retval |= test_edge(
+                                                               eBone->head, 
eBone->tail, ray_origin_local, ray_normal_local,
+                                                               
ray_depth_range, ob_scale, is_persp, ray_depth, dist_to_ray_sq,
+                                                               r_loc, NULL);
                                                        break;
                                        }
                                }
@@ -428,41 +372,43 @@ static bool snapArmature(
 
                                switch (snap_to) {
                                        case SCE_SNAP_MODE_VERTEX:
-                                               retval |= snapVertex(
-                                                       ar, head_vec, NULL, 
obmat, NULL, mval, dist_px,
-                                                       ray_start, 
ray_start_local, ray_normal_local,
-                                                       ray_depth, r_loc, NULL);
-                                               retval |= snapVertex(
-                                                       ar, tail_vec, NULL, 
obmat, NULL, mval, dist_px,
-                                                       ray_start, 
ray_start_local, ray_normal_local, ray_depth,
+                                               retval |= test_vert(
+                                                       head_vec, NULL, 
ray_origin_local, ray_normal_local,
+                                                       ray_depth_range, 
ob_scale, is_persp, ray_depth, dist_to_ray_sq,
+                                                       r_loc, NULL);
+                                               retval |= test_vert(
+                                                       tail_vec, NULL, 
ray_origin_local, ray_normal_local,
+                                                       ray_depth_range, 
ob_scale, is_persp, ray_depth, dist_to_ray_sq,
                                                        r_loc, NULL);
                                                break;
                                        case SCE_SNAP_MODE_EDGE:
-                                               retval |= snapEdge(
-                                                       ar, head_vec, NULL, 
tail_vec, NULL,
-                                                       obmat, NULL, mval, 
dist_px,
-                                                       ray_start, 
ray_start_local, ray_normal_local,
-                                                       ray_depth, r_loc, NULL);
+                                               retval |= test_edge(
+                                                       head_vec, tail_vec, 
ray_origin_local, ray_normal_local,
+                                                       ray_depth_range, 
ob_scale, is_persp, ray_depth, dist_to_ray_sq,
+                                                       r_loc, NULL);
                                                break;
                                }
                        }
                }
        }
-
-       return retval;
+

@@ Diff output truncated at 10240 characters. @@

_______________________________________________
Bf-blender-cvs mailing list
Bf-blender-cvs@blender.org
https://lists.blender.org/mailman/listinfo/bf-blender-cvs

Reply via email to