Browse Source

refactoring Vector2D

Alexander Hendrich 10 years ago
parent
commit
b93b8c50e6

+ 20 - 26
bbiwarg/Detectors/FingerDetection/FingerDetector.cs

@@ -23,7 +23,6 @@ namespace bbiwarg.Detectors.FingerDetection
 
         public FingerDetector(DepthImage depthImage, EdgeImage edgeImage, OutputImage outputImage)
         {
-            Console.WriteLine("---");
             this.depthImage = depthImage;
             this.edgeImageOriginal = edgeImage;
             this.edgeImageAdapted = edgeImage.copy();
@@ -35,8 +34,8 @@ namespace bbiwarg.Detectors.FingerDetection
 
         private void detectFingers()
         {
-            int maxX = depthImage.Width - 1;
-            int maxY = depthImage.Height - 1;
+            int maxX = depthImage.BottomRight.IntX;
+            int maxY = depthImage.BottomRight.IntY;
 
             Fingers = new List<Finger>();
 
@@ -83,15 +82,12 @@ namespace bbiwarg.Detectors.FingerDetection
 
         private FingerSliceTrail findFingerSliceTrail(FingerSlice startSlice, Vector2D startDirection)
         {
-            int maxX = depthImage.Width - 1;
-            int maxY = depthImage.Height - 1;
-
             FingerSliceTrail trail = new FingerSliceTrail(startSlice);
 
             Vector2D direction = startDirection;
             Vector2D position = startSlice.Mid + Constants.FingerStepSize * direction;
 
-            if (position.isWithin(0, 0, maxX, maxY))
+            if (position.isInBound(Vector2D.Zero, depthImage.BottomRight))
             {
                 FingerSlice nextSlice = findFingerSliceFromMid(position, direction);
                 if (nextSlice != null)
@@ -116,9 +112,6 @@ namespace bbiwarg.Detectors.FingerDetection
 
         private FingerSliceTrail expandTrail(FingerSliceTrail trail, bool reversed = false)
         {
-            int maxX = depthImage.Width - 1;
-            int maxY = depthImage.Height - 1;
-
             Vector2D currentDirection = trail.getEndDirection();
             Vector2D currentPosition = trail.EndSlice.Mid + Constants.FingerStepSize * currentDirection;
 
@@ -128,7 +121,7 @@ namespace bbiwarg.Detectors.FingerDetection
             FingerSlice lastSlice = trail.EndSlice;
             FingerSlice nextSlice;
 
-            while (currentPosition.isWithin(0, 0, maxX, maxY) && gapCounter <= Math.Min(numSlices, Constants.FingerMaxGapCounter))
+            while (currentPosition.isInBound(Vector2D.Zero, depthImage.BottomRight) && gapCounter <= Math.Min(numSlices, Constants.FingerMaxGapCounter))
             {
                 if (reversed)
                     nextSlice = findFingerSliceFromMid(currentPosition, currentDirection.getInverse());
@@ -180,22 +173,23 @@ namespace bbiwarg.Detectors.FingerDetection
 
         private Vector2D findNextEdge(Vector2D start, Vector2D direction, bool adaptedEdgeImage = true, bool stopAtMaxFingerSize = true, bool returnBoundIfNoEdge = false)
         {
-            int maxX = depthImage.Width - 1;
-            int maxY = depthImage.Height - 1;
+            Vector2D max = depthImage.BottomRight;
+            Vector2D maxGrow = (max - start) / direction;
+            Vector2D maxDecline = start / direction.getAbsolute();
 
             int maxStepsX;
             if (direction.X > 0)
-                maxStepsX = (int)((maxX - start.X) / direction.X);
+                maxStepsX = maxGrow.IntX;
             else if (direction.X < 0)
-                maxStepsX = (int)(start.X / Math.Abs(direction.X));
+                maxStepsX = maxDecline.IntX;
             else
                 maxStepsX = int.MaxValue;
 
             int maxStepsY;
             if (direction.Y > 0)
-                maxStepsY = (int)((maxY - start.Y) / direction.Y);
+                maxStepsY = maxGrow.IntY;
             else if (direction.Y < 0)
-                maxStepsY = (int)(start.Y / Math.Abs(direction.Y));
+                maxStepsY = maxDecline.IntY;
             else
                 maxStepsY = int.MaxValue;
 
@@ -227,8 +221,9 @@ namespace bbiwarg.Detectors.FingerDetection
             int maxY = depthImage.Height - 1;
 
             Vector2D direction = (end - start).normalize();
-            Vector2D beforeStart = (start - Constants.FingerSliceOverlapFactor * direction).moveInBound(0, 0, maxX, maxY);
-            Vector2D behindEnd = (end + Constants.FingerSliceOverlapFactor * direction).moveInBound(0, 0, maxY, maxY);
+            Vector2D directionInv = direction.getInverse();
+            Vector2D beforeStart = (start + Constants.FingerSliceOverlapFactor * directionInv).moveInBound(Vector2D.Zero, depthImage.BottomRight, direction);
+            Vector2D behindEnd = (end + Constants.FingerSliceOverlapFactor * direction).moveInBound(Vector2D.Zero, depthImage.BottomRight, directionInv);
 
             FingerSlice slice = new FingerSlice(beforeStart, behindEnd);
             if (slice.Length >= Constants.FingerMinSize && slice.Length <= Constants.FingerMaxSize && fingerSliceDepthTest(slice))
@@ -256,8 +251,6 @@ namespace bbiwarg.Detectors.FingerDetection
             //add finger
             if (!isCrippleFinger(finger))
                 Fingers.Add(finger);
-            else
-                Console.WriteLine("cripple");
 
             //remove edges around detected finger to improve performance
             edgeImageAdapted.removeEdgesInsidePolygon(finger.Contour.ToArray());
@@ -270,8 +263,9 @@ namespace bbiwarg.Detectors.FingerDetection
 
             FingerSlice midSlice = finger.SliceTrail.MidSlice;
             Vector2D direction = midSlice.Direction;
-            Vector2D out1 = (midSlice.Start - Constants.FingerCrippleOutFactor * direction).moveInBound(0, 0, maxX, maxY);
-            Vector2D out2 = (midSlice.End + Constants.FingerCrippleOutFactor * direction).moveInBound(0, 0, maxX, maxY);
+            Vector2D directionInv = direction.getInverse();
+            Vector2D out1 = (midSlice.Start + Constants.FingerCrippleOutFactor * directionInv).moveInBound(Vector2D.Zero, depthImage.BottomRight, direction);
+            Vector2D out2 = (midSlice.End + Constants.FingerCrippleOutFactor * direction).moveInBound(Vector2D.Zero, depthImage.BottomRight, directionInv);
 
             Int16 depthAtFinger = depthImage.getDepthAt(midSlice.Mid);
             Int16 depthAtOut1 = depthImage.getDepthAt(out1);
@@ -289,7 +283,7 @@ namespace bbiwarg.Detectors.FingerDetection
             Vector2D dirOrth1 = direction.getOrthogonal(true);
             Vector2D dirOrth2 = direction.getOrthogonal(false);
 
-            Vector2D outPoint = (start + Constants.FingerOutSliceFactor * direction).moveInBound(0, 0, maxX, maxY);
+            Vector2D outPoint = (start + Constants.FingerOutSliceFactor * direction).moveInBound(Vector2D.Zero, depthImage.BottomRight, direction.getInverse());
             Vector2D p1 = findNextEdge(outPoint, dirOrth1, false, false, true);
             Vector2D p2 = findNextEdge(outPoint, dirOrth2, false, false, true);
 
@@ -314,10 +308,10 @@ namespace bbiwarg.Detectors.FingerDetection
             float startOutLength = float.MaxValue;
             float endOutLength = float.MaxValue;
 
-            if (startOutSlice.Start.isWithin(1, 1, maxX, maxY) && startOutSlice.End.isWithin(1, 1, maxX, maxY))
+            if (startOutSlice.Start.isInBound(Vector2D.Zero, depthImage.BottomRight) && startOutSlice.End.isInBound(Vector2D.Zero, depthImage.BottomRight))
                 startOutLength = startOutSlice.Length;
 
-            if (endOutSlice.Start.isWithin(1, 1, maxX, maxY) && endOutSlice.End.isWithin(1, 1, maxX, maxY))
+            if (endOutSlice.Start.isInBound(Vector2D.Zero, depthImage.BottomRight) && endOutSlice.End.isInBound(Vector2D.Zero, depthImage.BottomRight))
                 endOutLength = endOutSlice.Length;
 
             if (startOutLength <= endOutLength)

+ 2 - 2
bbiwarg/Detectors/TouchDetection/TouchDetector.cs

@@ -37,8 +37,8 @@ namespace bbiwarg.Detectors.TouchDetection
                 if (floodValue > Constants.TouchEventMinFloodValue)
                 {
                     //correct touchEvent position
-                    Vector2D direction = finger.LineSegment.Line.Direction;
-                    Vector2D tep = (tipPoint + Constants.TouchEventTipCorrectionFactor * direction).moveInBound(0, 0, depthImage.Width - 1, depthImage.Height - 1);
+                    Vector2D direction = finger.Direction;
+                    Vector2D tep = (tipPoint + Constants.TouchEventTipCorrectionFactor * direction).moveInBound(Vector2D.Zero, depthImage.BottomRight, direction.getInverse());
 
                     outputImage.fillCircle(tep.IntX, tep.IntY, 5, Constants.TouchEventDetectedColor);
                     TouchEvent touchEvent = new TouchEvent(tep, floodValue, finger);

+ 2 - 0
bbiwarg/Images/DepthImage.cs

@@ -19,6 +19,7 @@ namespace bbiwarg.Images
         public Image<Gray, byte> BackgroundMask { get; private set; }
         public int Width { get; private set; }
         public int Height { get; private set; }
+        public Vector2D BottomRight { get; private set; }
         public Int16 MinDepth { get; private set; }
         public Int16 MaxDepth { get; private set; }
 
@@ -26,6 +27,7 @@ namespace bbiwarg.Images
         {
             Width = image.Width;
             Height = image.Height;
+            BottomRight = new Vector2D(Width - 1, Height - 1);
 
             image = image.SmoothMedian(Constants.DepthImageMedianSize);
 

+ 2 - 2
bbiwarg/Utility/Line2D.cs

@@ -63,8 +63,8 @@ namespace bbiwarg.Utility
             Vector2D q = line.PointOnLine;
             Vector2D s = line.Direction;
 
-            float r_cross_s = r.cross(s);
-            float q_p_cross_s = (q - p).cross(s);
+            float r_cross_s = r.crossProduct(s);
+            float q_p_cross_s = (q - p).crossProduct(s);
 
             if (r_cross_s == 0.0)
                 return null;

+ 24 - 22
bbiwarg/Utility/Vector2D.cs

@@ -55,7 +55,7 @@ namespace bbiwarg.Utility
             return X * vector.X + Y * vector.Y;
         }
 
-        public float cross(Vector2D v)
+        public float crossProduct(Vector2D v)
         {
             return X * v.Y - Y * v.X;
         }
@@ -69,33 +69,27 @@ namespace bbiwarg.Utility
             return (minX <= X && X <= maxX && minY <= Y && Y <= maxY);
         }
 
-        public Vector2D normalize()
-        {
-            float length = Length;
-            return new Vector2D(X / length, Y / length);
+        public bool isInBound(Vector2D topLeft, Vector2D bottomRight) {
+            return (X >= topLeft.X && X <= bottomRight.X && Y >= topLeft.Y && Y <= bottomRight.Y);
         }
 
-        public Vector2D normalizeComponentOne() {
-            if (Math.Abs(X) > Math.Abs(Y))
-                return new Vector2D(1, Y / X);
-            else
-                return new Vector2D(X / Y, 1);
-        } 
-
-        public bool isWithin(float minX, float minY, float maxX, float maxY)
+        /*public bool isOnBound(float minX, float minY, float maxX, float maxY)
         {
-            return (X >= minX && Y >= minY && X <= maxX && Y <= maxY);
-        }
+            return (IntX == minX || IntX == maxX || IntY == minY || IntY == maxY);
+        }*/
 
-        public Vector2D moveInBound(float minX, float minY, float maxX, float maxY)
-        {
-            float x = Math.Min(maxX, Math.Max(minX, X));
-            float y = Math.Min(maxY, Math.Max(minY, Y));
-            return new Vector2D(x, y);
+        public Vector2D moveInBound(Vector2D topLeft, Vector2D bottomRight, Vector2D direction) {
+            Vector2D pos = new Vector2D(X, Y);
+            while (!pos.isInBound(topLeft, bottomRight)) {
+                pos += direction;
+            }
+            return pos;
         }
 
-        public bool isOnBound(float minX, float minY, float maxX, float maxY) {
-            return (IntX == minX || IntX == maxX || IntY == minY || IntY == maxY);
+        public Vector2D normalize()
+        {
+            float length = Length;
+            return new Vector2D(X / length, Y / length);
         }
 
         public Vector2D getOrthogonal(bool side)
@@ -111,6 +105,10 @@ namespace bbiwarg.Utility
             return new Vector2D(-X, -Y);
         }
 
+        public Vector2D getAbsolute() {
+            return new Vector2D(Math.Abs(X), Math.Abs(Y));
+        }
+
         public override string ToString()
         {
             return "(" + X + "|" + Y + ")";
@@ -130,6 +128,10 @@ namespace bbiwarg.Utility
         {
             return new Vector2D(vector.X / scalar, vector.Y / scalar);
         }
+        public static Vector2D operator /(Vector2D vector1, Vector2D vector2)
+        {
+            return new Vector2D(vector1.X / vector2.X, vector1.Y / vector2.Y);
+        }
 
         public static Vector2D operator +(Vector2D vector1, Vector2D vector2)
         {