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:
authorCampbell Barton <ideasman42@gmail.com>2013-04-22 23:39:10 +0400
committerCampbell Barton <ideasman42@gmail.com>2013-04-22 23:39:10 +0400
commit556705f84efcb225ec1767e11167537a02553f2a (patch)
tree0bae9ac5ebb960b9845b7428b51a61cea28e4ca4 /source/blender/blenlib
parentbf51e807991b004de079736dfaeae6b642eaae4a (diff)
add clip_segment_v3_plane_n() to clip a line segment to planes (as used for view clipping).
use in ED_view3d_win_to_segment_clip() and fix error, was clipping by only 4 planes rather then 6.
Diffstat (limited to 'source/blender/blenlib')
-rw-r--r--source/blender/blenlib/BLI_math_geom.h3
-rw-r--r--source/blender/blenlib/intern/math_geom.c59
2 files changed, 60 insertions, 2 deletions
diff --git a/source/blender/blenlib/BLI_math_geom.h b/source/blender/blenlib/BLI_math_geom.h
index d24d5fb8c38..ad846823669 100644
--- a/source/blender/blenlib/BLI_math_geom.h
+++ b/source/blender/blenlib/BLI_math_geom.h
@@ -170,7 +170,8 @@ int isect_sweeping_sphere_tri_v3(const float p1[3], const float p2[3], const flo
int isect_axial_line_tri_v3(const int axis, const float co1[3], const float co2[3],
const float v0[3], const float v1[3], const float v2[3], float *r_lambda);
-int clip_line_plane(float p1[3], float p2[3], const float plane[4]);
+bool clip_segment_v3_plane(float p1[3], float p2[3], const float plane[4]);
+bool clip_segment_v3_plane_n(float p1[3], float p2[3], float plane_array[][4], const int plane_tot);
void plot_line_v2v2i(const int p1[2], const int p2[2], bool (*callback)(int, int, void *), void *userData);
diff --git a/source/blender/blenlib/intern/math_geom.c b/source/blender/blenlib/intern/math_geom.c
index 9cf83231f24..56921797659 100644
--- a/source/blender/blenlib/intern/math_geom.c
+++ b/source/blender/blenlib/intern/math_geom.c
@@ -1963,7 +1963,7 @@ int isect_point_tri_prism_v3(const float p[3], const float v1[3], const float v2
return 1;
}
-int clip_line_plane(float p1[3], float p2[3], const float plane[4])
+bool clip_segment_v3_plane(float p1[3], float p2[3], const float plane[4])
{
float dp[3], div, t, pc[3];
@@ -2011,6 +2011,63 @@ int clip_line_plane(float p1[3], float p2[3], const float plane[4])
}
}
+bool clip_segment_v3_plane_n(float r_p1[3], float r_p2[3], float plane_array[][4], const int plane_tot)
+{
+ /* intersect from both directions */
+ float p1[3], p2[3], dp[3], dp_orig[3];
+ int i;
+ copy_v3_v3(p1, r_p1);
+ copy_v3_v3(p2, r_p2);
+
+ sub_v3_v3v3(dp, p2, p1);
+ copy_v3_v3(dp_orig, dp);
+
+ for (i = 0; i < plane_tot; i++) {
+ const float *plane = plane_array[i];
+ const float div = dot_v3v3(dp, plane);
+
+ if (div != 0.0f) {
+ const float t = -(dot_v3v3(p1, plane) + plane[3]) / div;
+ if (div > 0.0f) {
+ /* clip a */
+ if (t >= 1.0f) {
+ return false;
+ }
+
+ /* intersect plane */
+ if (t > 0.0f) {
+ madd_v3_v3v3fl(p1, p1, dp, t);
+ /* recalc direction and test for flipping */
+ sub_v3_v3v3(dp, p2, p1);
+ if (dot_v3v3(dp, dp_orig) < 0.0f) {
+ return false;
+ }
+ }
+ }
+ else if (div < 0.0f) {
+ /* clip b */
+ if (t <= 0.0f) {
+ return false;
+ }
+
+ /* intersect plane */
+ if (t < 1.0f) {
+ madd_v3_v3v3fl(p2, p1, dp, t);
+ /* recalc direction and test for flipping */
+ sub_v3_v3v3(dp, p2, p1);
+ if (dot_v3v3(dp, dp_orig) < 0.0f) {
+ return false;
+ }
+ }
+ }
+ }
+ }
+
+ copy_v3_v3(r_p1, p1);
+ copy_v3_v3(r_p2, p2);
+ return true;
+}
+
void plot_line_v2v2i(const int p1[2], const int p2[2], bool (*callback)(int, int, void *), void *userData)
{
int x1 = p1[0];