|
@@ -13,43 +13,37 @@ namespace bbiwarg.Detectors.Fingers
|
|
|
class Finger
|
|
|
{
|
|
|
private List<FingerPoint> fingerPoints;
|
|
|
- private FingerPoint nearest;
|
|
|
- private FingerPoint farthest;
|
|
|
+ private bool lineUpToDate = false;
|
|
|
private PointF direction;
|
|
|
private PointF pointOnLine;
|
|
|
- private PointF start;
|
|
|
- private PointF end;
|
|
|
- private bool lineUpToDate;
|
|
|
-
|
|
|
+ private PointF lineEndPoint1;
|
|
|
+ private PointF lineEndPoint2;
|
|
|
+ private FingerPoint tipPoint;
|
|
|
+ private FingerPoint handPoint;
|
|
|
+ private float length;
|
|
|
+
|
|
|
public Finger(FingerPoint fingerPoint)
|
|
|
{
|
|
|
fingerPoints = new List<FingerPoint>();
|
|
|
- nearest = fingerPoint;
|
|
|
- farthest = fingerPoint;
|
|
|
- lineUpToDate = false;
|
|
|
addFingerPoint(fingerPoint);
|
|
|
}
|
|
|
|
|
|
- public FingerPoint getNearest()
|
|
|
+ public PointF getLineEndPoint1()
|
|
|
{
|
|
|
- return nearest;
|
|
|
- }
|
|
|
-
|
|
|
- public FingerPoint getFarthest()
|
|
|
- {
|
|
|
- return farthest;
|
|
|
+ if (!lineUpToDate) updateLine();
|
|
|
+ return lineEndPoint1;
|
|
|
}
|
|
|
|
|
|
- public PointF getStart()
|
|
|
+ public PointF getLineEndPoint2()
|
|
|
{
|
|
|
if (!lineUpToDate) updateLine();
|
|
|
- return start;
|
|
|
+ return lineEndPoint2;
|
|
|
}
|
|
|
|
|
|
- public PointF getEnd()
|
|
|
+ public FingerPoint getTipPoint()
|
|
|
{
|
|
|
if (!lineUpToDate) updateLine();
|
|
|
- return end;
|
|
|
+ return tipPoint;
|
|
|
}
|
|
|
|
|
|
public PointF getDirection() {
|
|
@@ -57,16 +51,15 @@ namespace bbiwarg.Detectors.Fingers
|
|
|
return direction;
|
|
|
}
|
|
|
|
|
|
+ public float getLength()
|
|
|
+ {
|
|
|
+ if (!lineUpToDate) updateLine();
|
|
|
+ return length;
|
|
|
+ }
|
|
|
+
|
|
|
public void addFingerPoint(FingerPoint fingerPoint)
|
|
|
{
|
|
|
fingerPoints.Add(fingerPoint);
|
|
|
-
|
|
|
- //update nearest
|
|
|
- if (fingerPoint.getDepth() < nearest.getDepth()) nearest = fingerPoint;
|
|
|
-
|
|
|
- //update farthest
|
|
|
- if (fingerPoint.getDepth() > farthest.getDepth()) farthest = fingerPoint;
|
|
|
-
|
|
|
lineUpToDate = false;
|
|
|
}
|
|
|
|
|
@@ -85,27 +78,6 @@ namespace bbiwarg.Detectors.Fingers
|
|
|
return minDinstance;
|
|
|
}
|
|
|
|
|
|
- public float getLength()
|
|
|
- {
|
|
|
- FingerPoint fp1 = getNearest();
|
|
|
- FingerPoint fp2 = getFarthest();
|
|
|
- float distance = fp1.getDistanceTo(fp2);
|
|
|
- return distance;
|
|
|
- }
|
|
|
-
|
|
|
- private PointF projectToLine(PointF p)
|
|
|
- {
|
|
|
- float px = p.X, py = p.Y, dx = direction.X, dy = direction.Y, ox = pointOnLine.X, oy = pointOnLine.Y;
|
|
|
- float diffx = px - ox;
|
|
|
- float diffy = py - oy;
|
|
|
-
|
|
|
- float diff_d = (diffx * dx + diffy * dy);
|
|
|
- float d_d = (dx * dx + dy * dy);
|
|
|
- float q = diff_d / d_d;
|
|
|
-
|
|
|
- return new PointF(ox + q * dx, oy + q * dy);
|
|
|
- }
|
|
|
-
|
|
|
private void updateLine() {
|
|
|
//update direction+pointonline
|
|
|
PointF[] pointArray = new PointF[fingerPoints.Count];
|
|
@@ -117,11 +89,53 @@ namespace bbiwarg.Detectors.Fingers
|
|
|
}
|
|
|
PointCollection.Line2DFitting(pointArray, Emgu.CV.CvEnum.DIST_TYPE.CV_DIST_L2, out direction, out pointOnLine);
|
|
|
|
|
|
+ FingerPoint fp1 = fingerPoints[0];
|
|
|
+ FingerPoint fp2 = fingerPoints[0];
|
|
|
+ length = 0.0f;
|
|
|
+ foreach (FingerPoint fp in fingerPoints) {
|
|
|
+ float distanceToFP1 = fp.getDistanceTo(fp1);
|
|
|
+ float distanceToFP2 = fp.getDistanceTo(fp2);
|
|
|
+ if (length < distanceToFP1 && distanceToFP1 >= distanceToFP2)
|
|
|
+ {
|
|
|
+ fp2 = fp;
|
|
|
+ length = distanceToFP1;
|
|
|
+ }
|
|
|
+ else if (length < distanceToFP2 && distanceToFP2 > distanceToFP1)
|
|
|
+ {
|
|
|
+ fp1 = fp;
|
|
|
+ length = distanceToFP2;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ if (fp1.getY() < fp2.getY())
|
|
|
+ {
|
|
|
+ tipPoint = fp1;
|
|
|
+ handPoint = fp2;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ tipPoint = fp2;
|
|
|
+ handPoint = fp1;
|
|
|
+ }
|
|
|
+
|
|
|
//update start+end
|
|
|
- start = projectToLine(new PointF(farthest.getX(), farthest.getY()));
|
|
|
- end = projectToLine(new PointF(nearest.getX(), nearest.getY()));
|
|
|
+ lineEndPoint1 = projectToLine(new PointF(tipPoint.getX(), tipPoint.getY()));
|
|
|
+ lineEndPoint2 = projectToLine(new PointF(handPoint.getX(), handPoint.getY()));
|
|
|
|
|
|
lineUpToDate = true;
|
|
|
}
|
|
|
+
|
|
|
+ private PointF projectToLine(PointF p)
|
|
|
+ {
|
|
|
+ float px = p.X, py = p.Y, dx = direction.X, dy = direction.Y, ox = pointOnLine.X, oy = pointOnLine.Y;
|
|
|
+ float diffx = px - ox;
|
|
|
+ float diffy = py - oy;
|
|
|
+
|
|
|
+ float diff_d = (diffx * dx + diffy * dy);
|
|
|
+ float d_d = (dx * dx + dy * dy);
|
|
|
+ float q = diff_d / d_d;
|
|
|
+
|
|
|
+ return new PointF(ox + q * dx, oy + q * dy);
|
|
|
+ }
|
|
|
}
|
|
|
}
|