changeset 4764:5c80a33edd44

Fixed handling of none-closed polygons in containment test.
author Sascha L. Teichmann <teichmann@intevation.de>
date Sat, 19 Oct 2019 19:40:51 +0200
parents d786c37b02c0
children db6c2955ee31
files pkg/octree/areas.go pkg/octree/polygon.go
diffstat 2 files changed, 14 insertions(+), 16 deletions(-) [+]
line wrap: on
line diff
--- a/pkg/octree/areas.go	Sat Oct 19 19:12:18 2019 +0200
+++ b/pkg/octree/areas.go	Sat Oct 19 19:40:51 2019 +0200
@@ -233,10 +233,6 @@
 		contains(cnt, o[len(o)/2].X, o[len(o)/2].Y)
 }
 
-func (cnt contour) closed() bool {
-	return len(cnt) >= 3
-}
-
 func (cnt contour) length() int {
 	return len(cnt)
 }
--- a/pkg/octree/polygon.go	Sat Oct 19 19:12:18 2019 +0200
+++ b/pkg/octree/polygon.go	Sat Oct 19 19:40:51 2019 +0200
@@ -341,10 +341,6 @@
 	return IntersectionOutSide
 }
 
-func (rng ring) closed() bool {
-	return (len(rng) / 2) >= 3
-}
-
 func (rng ring) length() int {
 	return len(rng) / 2
 }
@@ -355,32 +351,38 @@
 }
 
 type segments interface {
-	closed() bool
 	length() int
 	point(int) (float64, float64)
 }
 
 func contains(s segments, pX, pY float64) bool {
-	if !s.closed() {
+
+	n := s.length()
+	if n < 3 {
 		return false
 	}
 
-	n := s.length()
-
 	sX, sY := s.point(0)
 	eX, eY := s.point(n - 1)
 
-	contains := intersectsWithRaycast(pX, pY, sX, sY, eX, eY)
+	const eps = 0.0000001
+
+	if math.Abs(sX-eX) > eps && math.Abs(sY-eY) > eps {
+		// It's not closed!
+		return false
+	}
+
+	var inside bool
 
 	for i := 1; i < n; i++ {
-		sX, sY := s.point(i - 1)
 		eX, eY := s.point(i)
 		if intersectsWithRaycast(pX, pY, sX, sY, eX, eY) {
-			contains = !contains
+			inside = !inside
 		}
+		sX, sY = eX, eY
 	}
 
-	return contains
+	return inside
 }
 
 // Using the raycast algorithm, this returns whether or not the passed in point