Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGermano <germano.costa@ig.com.br>2018-05-14 22:08:17 +0300
committerGermano <germano.costa@ig.com.br>2018-05-14 22:08:17 +0300
commitbf7c46cae0a418776f381d33080988b11deabedf (patch)
treeec2a55a3a083a820ac5aa61243ffe07ed7a1838f /source/blender/editors/transform
parent8cbf402eb61bde42c63963eb092bf6722516280b (diff)
Transform: Use the new BLI_bvhtree_find_nearest_projected function to snap.
Diffstat (limited to 'source/blender/editors/transform')
-rw-r--r--source/blender/editors/transform/transform_snap_object.c223
1 files changed, 102 insertions, 121 deletions
diff --git a/source/blender/editors/transform/transform_snap_object.c b/source/blender/editors/transform/transform_snap_object.c
index 00976311887..b5ff9c5f2e6 100644
--- a/source/blender/editors/transform/transform_snap_object.c
+++ b/source/blender/editors/transform/transform_snap_object.c
@@ -897,8 +897,8 @@ static void cb_mlooptri_verts_get(
static bool test_projected_vert_dist(
struct DistProjectedAABBPrecalc *neasrest_precalc,
- const float depth_range[2], const float co[3],
- const bool is_persp,
+ const float depth_range[2],
+ const bool is_persp, const float co[3],
float *dist_px_sq, float r_co[3])
{
float w;
@@ -934,15 +934,15 @@ static bool test_projected_edge_dist(
float *dist_px_sq, float r_co[3])
{
- float tmp_co[3], dummy_depth;
+ float near_co[3], dummy_depth;
dist_squared_ray_to_seg_v3(
neasrest_precalc->ray_origin,
neasrest_precalc->ray_direction,
- va, vb, tmp_co, &dummy_depth);
+ va, vb, near_co, &dummy_depth);
return test_projected_vert_dist(
neasrest_precalc, depth_range,
- tmp_co, is_persp, dist_px_sq, r_co);
+ is_persp, near_co, dist_px_sq, r_co);
}
/** \} */
@@ -958,8 +958,6 @@ typedef void (*Nearest2DGetTriEdgesCallback)(const int index, int e_index[3], vo
typedef void (*Nearest2DCopyVertNoCallback)(const int index, float r_no[3], void *data);
typedef struct Nearest2dUserData {
- struct DistProjectedAABBPrecalc data_precalc;
- bool r_axis_closest[3];
bool is_persp;
float depth_range[2];
short snap_to;
@@ -971,32 +969,13 @@ typedef struct Nearest2dUserData {
Nearest2DGetTriEdgesCallback get_tri_edges_index;
Nearest2DCopyVertNoCallback copy_vert_no;
- float dist_px_sq;
- int index;
- float co[3];
- float no[3];
} Nearest2dUserData;
-static bool cb_walk_parent_snap_project(const BVHTreeAxisRange *bounds, void *user_data)
-{
- Nearest2dUserData *data = user_data;
- const float bbmin[3] = {bounds[0].min, bounds[1].min, bounds[2].min};
- const float bbmax[3] = {bounds[0].max, bounds[1].max, bounds[2].max};
- const float rdist = dist_squared_to_projected_aabb(
- &data->data_precalc, bbmin, bbmax, data->r_axis_closest);
- return rdist < data->dist_px_sq;
-}
-
-static bool cb_nearest_walk_order(
- const BVHTreeAxisRange *UNUSED(bounds), char axis, void *userdata)
-{
- const bool *r_axis_closest = ((struct Nearest2dUserData *)userdata)->r_axis_closest;
- return r_axis_closest[axis];
-}
-
-static bool cb_walk_leaf_snap_vert(
- const BVHTreeAxisRange *UNUSED(bounds), int index, void *userdata)
+static void cb_walk_leaf_snap_vert(
+ void *userdata, int index,
+ struct DistProjectedAABBPrecalc *precalc,
+ BVHTreeNearest *nearest)
{
struct Nearest2dUserData *data = userdata;
@@ -1004,20 +983,22 @@ static bool cb_walk_leaf_snap_vert(
data->get_vert_co(index, &co, data->userdata);
if (test_projected_vert_dist(
- &data->data_precalc,
- data->depth_range, co,
+ precalc,
+ data->depth_range,
data->is_persp,
- &data->dist_px_sq,
- data->co))
+ co,
+ &nearest->dist_sq,
+ nearest->co))
{
- data->copy_vert_no(index, data->no, data->userdata);
- data->index = index;
+ data->copy_vert_no(index, nearest->no, data->userdata);
+ nearest->index = index;
}
- return true;
}
-static bool cb_walk_leaf_snap_edge(
- const BVHTreeAxisRange *UNUSED(bounds), int index, void *userdata)
+static void cb_walk_leaf_snap_edge(
+ void *userdata, int index,
+ struct DistProjectedAABBPrecalc *precalc,
+ BVHTreeNearest *nearest)
{
struct Nearest2dUserData *data = userdata;
@@ -1030,31 +1011,31 @@ static bool cb_walk_leaf_snap_edge(
data->get_vert_co(vindex[1], &v_pair[1], data->userdata);
if (test_projected_edge_dist(
- &data->data_precalc,
+ precalc,
data->depth_range,
data->is_persp,
v_pair[0], v_pair[1],
- &data->dist_px_sq,
- data->co))
+ &nearest->dist_sq,
+ nearest->co))
{
- sub_v3_v3v3(data->no, v_pair[0], v_pair[1]);
- data->index = index;
+ sub_v3_v3v3(nearest->no, v_pair[0], v_pair[1]);
+ nearest->index = index;
}
}
else {
for (int i = 0; i < 2; i++) {
- if (vindex[i] == data->index) {
+ if (vindex[i] == nearest->index) {
continue;
}
- cb_walk_leaf_snap_vert(NULL, vindex[i], userdata);
+ cb_walk_leaf_snap_vert(userdata, vindex[i], precalc, nearest);
}
}
-
- return true;
}
-static bool cb_walk_leaf_snap_tri(
- const BVHTreeAxisRange *UNUSED(bounds), int index, void *userdata)
+static void cb_walk_leaf_snap_tri(
+ void *userdata, int index,
+ struct DistProjectedAABBPrecalc *precalc,
+ BVHTreeNearest *nearest)
{
struct Nearest2dUserData *data = userdata;
@@ -1063,10 +1044,10 @@ static bool cb_walk_leaf_snap_tri(
data->get_tri_edges_index(index, eindex, data->userdata);
for (int i = 0; i < 3; i++) {
if (eindex[i] != -1) {
- if (eindex[i] == data->index) {
+ if (eindex[i] == nearest->index) {
continue;
}
- cb_walk_leaf_snap_edge(NULL, eindex[i], userdata);
+ cb_walk_leaf_snap_edge(userdata, eindex[i], precalc, nearest);
}
}
}
@@ -1074,13 +1055,12 @@ static bool cb_walk_leaf_snap_tri(
int vindex[3];
data->get_tri_verts_index(index, vindex, data->userdata);
for (int i = 0; i < 3; i++) {
- if (vindex[i] == data->index) {
+ if (vindex[i] == nearest->index) {
continue;
}
- cb_walk_leaf_snap_vert(NULL, vindex[i], userdata);
+ cb_walk_leaf_snap_vert(userdata, vindex[i], precalc, nearest);
}
}
- return true;
}
/** \} */
@@ -1134,10 +1114,10 @@ static bool snapArmature(
case SCE_SNAP_MODE_VERTEX:
retval |= test_projected_vert_dist(
&neasrest_precalc, snapdata->depth_range,
- eBone->head, is_persp, &dist_px_sq, r_loc);
+ is_persp, eBone->head, &dist_px_sq, r_loc);
retval |= test_projected_vert_dist(
&neasrest_precalc, snapdata->depth_range,
- eBone->tail, is_persp, &dist_px_sq, r_loc);
+ is_persp, eBone->tail, &dist_px_sq, r_loc);
break;
case SCE_SNAP_MODE_EDGE:
retval |= test_projected_edge_dist(
@@ -1162,10 +1142,10 @@ static bool snapArmature(
case SCE_SNAP_MODE_VERTEX:
retval |= test_projected_vert_dist(
&neasrest_precalc, snapdata->depth_range,
- head_vec, is_persp, &dist_px_sq, r_loc);
+ is_persp, head_vec, &dist_px_sq, r_loc);
retval |= test_projected_vert_dist(
&neasrest_precalc, snapdata->depth_range,
- tail_vec, is_persp, &dist_px_sq, r_loc);
+ is_persp, tail_vec, &dist_px_sq, r_loc);
break;
case SCE_SNAP_MODE_EDGE:
retval |= test_projected_edge_dist(
@@ -1239,7 +1219,7 @@ static bool snapCurve(
}
retval |= test_projected_vert_dist(
&neasrest_precalc, snapdata->depth_range,
- nu->bezt[u].vec[1], is_persp, &dist_px_sq,
+ is_persp, nu->bezt[u].vec[1], &dist_px_sq,
r_loc);
/* don't snap if handle is selected (moving), or if it is aligning to a moving handle */
if (!(nu->bezt[u].f1 & SELECT) &&
@@ -1247,7 +1227,7 @@ static bool snapCurve(
{
retval |= test_projected_vert_dist(
&neasrest_precalc, snapdata->depth_range,
- nu->bezt[u].vec[0], is_persp, &dist_px_sq,
+ is_persp, nu->bezt[u].vec[0], &dist_px_sq,
r_loc);
}
if (!(nu->bezt[u].f3 & SELECT) &&
@@ -1255,7 +1235,7 @@ static bool snapCurve(
{
retval |= test_projected_vert_dist(
&neasrest_precalc, snapdata->depth_range,
- nu->bezt[u].vec[2], is_persp, &dist_px_sq,
+ is_persp, nu->bezt[u].vec[2], &dist_px_sq,
r_loc);
}
}
@@ -1266,7 +1246,7 @@ static bool snapCurve(
}
retval |= test_projected_vert_dist(
&neasrest_precalc, snapdata->depth_range,
- nu->bp[u].vec, is_persp, &dist_px_sq,
+ is_persp, nu->bp[u].vec, &dist_px_sq,
r_loc);
}
}
@@ -1276,13 +1256,13 @@ static bool snapCurve(
if (nu->bezt) {
retval |= test_projected_vert_dist(
&neasrest_precalc, snapdata->depth_range,
- nu->bezt[u].vec[1], is_persp, &dist_px_sq,
+ is_persp, nu->bezt[u].vec[1], &dist_px_sq,
r_loc);
}
else {
retval |= test_projected_vert_dist(
&neasrest_precalc, snapdata->depth_range,
- nu->bp[u].vec, is_persp, &dist_px_sq,
+ is_persp, nu->bp[u].vec, &dist_px_sq,
r_loc);
}
}
@@ -1328,11 +1308,11 @@ static bool snapEmpty(
bool is_persp = snapdata->view_proj == VIEW_PROJ_PERSP;
float dist_px_sq = SQUARE(*dist_px);
- float tmp_co[3];
- copy_v3_v3(tmp_co, obmat[3]);
+ float co[3];
+ copy_v3_v3(co, obmat[3]);
if (test_projected_vert_dist(
&neasrest_precalc, snapdata->depth_range,
- tmp_co, is_persp, &dist_px_sq, r_loc))
+ is_persp, co, &dist_px_sq, r_loc))
{
*dist_px = sqrtf(dist_px_sq);
*ray_depth = depth_get(r_loc, snapdata->ray_start, snapdata->ray_dir);
@@ -1423,7 +1403,7 @@ static bool snapCamera(
mul_m4_v3(vertex_obmat, bundle_pos);
retval |= test_projected_vert_dist(
&neasrest_precalc, snapdata->depth_range,
- bundle_pos, is_persp, &dist_px_sq, r_loc);
+ is_persp, bundle_pos, &dist_px_sq, r_loc);
}
}
@@ -1465,23 +1445,22 @@ static bool snapMesh(
float lpmat[4][4];
mul_m4_m4m4(lpmat, snapdata->pmat, obmat);
- Nearest2dUserData neasrest2d;
- dist_squared_to_projected_aabb_precalc(
- &neasrest2d.data_precalc, lpmat, snapdata->win_size, snapdata->mval);
-
- neasrest2d.r_axis_closest[0] = true;
- neasrest2d.r_axis_closest[1] = true;
- neasrest2d.r_axis_closest[2] = true;
- neasrest2d.dist_px_sq = SQUARE(*dist_px);
+ float dist_px_sq = SQUARE(*dist_px);
/* Test BoundBox */
BoundBox *bb = BKE_mesh_boundbox_get(ob);
if (bb) {
/* In vertex and edges you need to get the pixel distance from ray to BoundBox, see: T46099, T46816 */
- float dist_px_sq = dist_squared_to_projected_aabb(
- &neasrest2d.data_precalc, bb->vec[0], bb->vec[6], neasrest2d.r_axis_closest);
- if (dist_px_sq > neasrest2d.dist_px_sq) {
+ struct DistProjectedAABBPrecalc data_precalc;
+ dist_squared_to_projected_aabb_precalc(
+ &data_precalc, lpmat, snapdata->win_size, snapdata->mval);
+
+ bool dummy[3];
+ float bb_dist_px_sq = dist_squared_to_projected_aabb(
+ &data_precalc, bb->vec[0], bb->vec[6], dummy);
+
+ if (bb_dist_px_sq > dist_px_sq) {
return retval;
}
}
@@ -1582,56 +1561,58 @@ static bool snapMesh(
* And more... ray_depth is being confused with Z-depth here... (varies only the precision) */
const float ray_depth_max_global = *ray_depth + snapdata->depth_range[0];
- neasrest2d.is_persp = snapdata->view_proj == VIEW_PROJ_PERSP;
-
- neasrest2d.depth_range[0] = snapdata->depth_range[0];
- neasrest2d.depth_range[1] = ray_depth_max_global;
-
- neasrest2d.snap_to = snapdata->snap_to;
- neasrest2d.userdata = treedata;
- neasrest2d.get_vert_co = (Nearest2DGetVertCoCallback)cb_mvert_co_get;
- neasrest2d.get_edge_verts_index = (Nearest2DGetEdgeVertsCallback)cb_medge_verts_get;
- neasrest2d.get_tri_verts_index = (Nearest2DGetTriVertsCallback)cb_mlooptri_verts_get;
- neasrest2d.get_tri_edges_index = (Nearest2DGetTriEdgesCallback)cb_mlooptri_edges_get;
- neasrest2d.copy_vert_no = (Nearest2DCopyVertNoCallback)cb_mvert_no_copy;
- neasrest2d.index = -1;
+ Nearest2dUserData neasrest2d = {
+ .is_persp = snapdata->view_proj == VIEW_PROJ_PERSP,
+ .depth_range = {snapdata->depth_range[0], ray_depth_max_global},
+ .snap_to = snapdata->snap_to,
+ .userdata = treedata,
+ .get_vert_co = (Nearest2DGetVertCoCallback)cb_mvert_co_get,
+ .get_edge_verts_index = (Nearest2DGetEdgeVertsCallback)cb_medge_verts_get,
+ .get_tri_verts_index = (Nearest2DGetTriVertsCallback)cb_mlooptri_verts_get,
+ .get_tri_edges_index = (Nearest2DGetTriEdgesCallback)cb_mlooptri_edges_get,
+ .copy_vert_no = (Nearest2DCopyVertNoCallback)cb_mvert_no_copy,
+ };
+ BVHTreeNearest nearest = {
+ .index = -1,
+ .dist_sq = dist_px_sq,
+ };
if (bvhtree[1]) {
/* snap to loose verts */
- BLI_bvhtree_walk_dfs(
- bvhtree[1],
- cb_walk_parent_snap_project, cb_walk_leaf_snap_vert, cb_nearest_walk_order, &neasrest2d);
+ BLI_bvhtree_find_nearest_projected(
+ bvhtree[1], lpmat, snapdata->win_size, snapdata->mval,
+ NULL, 0, &nearest, cb_walk_leaf_snap_vert, &neasrest2d);
}
if (bvhtree[0]) {
/* snap to loose edges */
- BLI_bvhtree_walk_dfs(
- bvhtree[0],
- cb_walk_parent_snap_project, cb_walk_leaf_snap_edge, cb_nearest_walk_order, &neasrest2d);
+ BLI_bvhtree_find_nearest_projected(
+ bvhtree[0], lpmat, snapdata->win_size, snapdata->mval,
+ NULL, 0, &nearest, cb_walk_leaf_snap_edge, &neasrest2d);
}
if (treedata->tree) {
/* snap to looptris */
- BLI_bvhtree_walk_dfs(
- treedata->tree,
- cb_walk_parent_snap_project, cb_walk_leaf_snap_tri, cb_nearest_walk_order, &neasrest2d);
+ BLI_bvhtree_find_nearest_projected(
+ treedata->tree, lpmat, snapdata->win_size, snapdata->mval,
+ NULL, 0, &nearest, cb_walk_leaf_snap_tri, &neasrest2d);
}
- if (neasrest2d.index != -1) {
+ if (nearest.index != -1) {
float imat[4][4];
float timat[3][3]; /* transpose inverse matrix for normals */
invert_m4_m4(imat, obmat);
transpose_m3_m4(timat, imat);
- copy_v3_v3(r_loc, neasrest2d.co);
+ copy_v3_v3(r_loc, nearest.co);
mul_m4_v3(obmat, r_loc);
if (r_no) {
- copy_v3_v3(r_no, neasrest2d.no);
+ copy_v3_v3(r_no, nearest.no);
mul_m3_v3(timat, r_no);
normalize_v3(r_no);
}
- *dist_px = sqrtf(neasrest2d.dist_px_sq);
+ *dist_px = sqrtf(nearest.dist_sq);
*ray_depth = depth_get(r_loc, snapdata->ray_start, snapdata->ray_dir);
retval = true;
@@ -1733,7 +1714,6 @@ static bool snapEditMesh(
}
Nearest2dUserData neasrest2d = {
- .r_axis_closest = {true, true, true},
.is_persp = snapdata->view_proj == VIEW_PROJ_PERSP,
.depth_range = {snapdata->depth_range[0], *ray_depth + snapdata->depth_range[0]},
.snap_to = snapdata->snap_to,
@@ -1741,36 +1721,37 @@ static bool snapEditMesh(
.get_vert_co = (Nearest2DGetVertCoCallback)cb_bvert_co_get,
.get_edge_verts_index = (Nearest2DGetEdgeVertsCallback)cb_bedge_verts_get,
.copy_vert_no = (Nearest2DCopyVertNoCallback)cb_bvert_no_copy,
- .dist_px_sq = SQUARE(*dist_px),
- .index = -1};
+ };
- float lpmat[4][4];
- mul_m4_m4m4(lpmat, snapdata->pmat, obmat);
- dist_squared_to_projected_aabb_precalc(
- &neasrest2d.data_precalc, lpmat, snapdata->win_size, snapdata->mval);
+ BVHTreeNearest nearest = {
+ .index = -1,
+ .dist_sq = SQUARE(*dist_px),
+ };
- BVHTree_WalkLeafCallback cb_walk_leaf =
+ BVHTree_NearestProjectedCallback cb_walk_leaf =
(snapdata->snap_to == SCE_SNAP_MODE_VERTEX) ?
cb_walk_leaf_snap_vert : cb_walk_leaf_snap_edge;
- BLI_bvhtree_walk_dfs(
- treedata->tree,
- cb_walk_parent_snap_project, cb_walk_leaf, cb_nearest_walk_order, &neasrest2d);
+ float lpmat[4][4];
+ mul_m4_m4m4(lpmat, snapdata->pmat, obmat);
+ BLI_bvhtree_find_nearest_projected(
+ treedata->tree, lpmat, snapdata->win_size, snapdata->mval,
+ NULL, 0, &nearest, cb_walk_leaf, &neasrest2d);
- if (neasrest2d.index != -1) {
+ if (nearest.index != -1) {
float imat[4][4];
float timat[3][3]; /* transpose inverse matrix for normals */
invert_m4_m4(imat, obmat);
transpose_m3_m4(timat, imat);
- copy_v3_v3(r_loc, neasrest2d.co);
+ copy_v3_v3(r_loc, nearest.co);
mul_m4_v3(obmat, r_loc);
if (r_no) {
- copy_v3_v3(r_no, neasrest2d.no);
+ copy_v3_v3(r_no, nearest.no);
mul_m3_v3(timat, r_no);
normalize_v3(r_no);
}
- *dist_px = sqrtf(neasrest2d.dist_px_sq);
+ *dist_px = sqrtf(nearest.dist_sq);
*ray_depth = depth_get(r_loc, snapdata->ray_start, snapdata->ray_dir);
retval = true;