Reputation: 458
I have just working on kinect and C# programming so I am very amateur at it I would like to know about joint angles.
I created this code just to test my skill without using kinect but am having trouble with the code.
I supposed vector3 v1
and vector3 v2
as a joint replacement but the value return from Find_angle
is NaN
.
Am I missing something in the process? Please any help in this regard will be helpful.
Vector3 V1 = new Vector3(100,40,90);
Vector3 v2 = new Vector3(160,60,90);
public MainWindow()
{
InitializeComponent();
Vector3.Normalize(V1);
Vector3.Normalize(v2);
float Result = this.find_angle(V1,v2);
MessageBox.Show(Result.ToString());
}
public float find_angle(Vector3 va, Vector3 vb)
{
float dot_pro=Vector3.Dot(va, vb);
double angle = Math.Acos(dot_pro);
angle = angle * 180 / Math.PI;
return (float)(angle);
}
Upvotes: 2
Views: 6359
Reputation: 4681
I am not familiar with it but you should divide the product of the vectors by the size of them before applying the acos.
Example:
double len_prod = va.Len * vb.Len;
double angle = Math.Acos(dot_pro / len_prod);
Upvotes: 0
Reputation: 1088
If you are using Kinect SDK to get the skeletal tracking, the you can use this:
/// <summary>
/// Return the angle between 3 Joints
/// Regresa el ángulo interno dadas 3 Joints
/// </summary>
/// <param name="j1"></param>
/// <param name="j2"></param>
/// <param name="j3"></param>
/// <returns></returns>
public static double AngleBetweenJoints(Joint j1, Joint j2, Joint j3)
{
double Angulo = 0;
double shrhX = j1.Position.X - j2.Position.X;
double shrhY = j1.Position.Y - j2.Position.Y;
double shrhZ = j1.Position.Z - j2.Position.Z;
double hsl = vectorNorm(shrhX, shrhY, shrhZ);
double unrhX = j3.Position.X - j2.Position.X;
double unrhY = j3.Position.Y - j2.Position.Y;
double unrhZ =j3.Position.Z - j2.Position.Z;
double hul = vectorNorm(unrhX, unrhY, unrhZ);
double mhshu = shrhX * unrhX + shrhY * unrhY + shrhZ * unrhZ;
double x = mhshu / (hul * hsl);
if (x != Double.NaN)
{
if (-1 <= x && x <= 1)
{
double angleRad = Math.Acos(x);
Angulo = angleRad *(180.0 / Math.PI);
}
else
Angulo = 0;
}
else
Angulo = 0;
return Angulo;
}
/// <summary>
/// Euclidean norm of 3-component Vector
/// </summary>
/// <param name="x"></param>
/// <param name="y"></param>
/// <param name="z"></param>
/// <returns></returns>
private static double vectorNorm(double x, double y, double z)
{
return Math.Sqrt(Math.Pow(x, 2) + Math.Pow(y, 2) + Math.Pow(z, 2));
}
This method use 3 joints to get an angle.
Upvotes: 1
Reputation: 441
Get the X and Y's of the joint you want, then get a joint on either side of it. Then see how to calculate the angle for How do I calculate angle from two coordinates?
Basically do:
float x1 = joint1.X;
float y1 = joint1.Y;
float x2 = joint2.X;
float y2 = joint2.Y;
float angleRadians;
float diffX = x2 - x1;
float diffY = y2 - y1;
float atan2Result = (float)Math.Atan2(diffX, diffY);
angleRadians = atan2Result / 2;
if (angleRadians < 0.0f)
angleRadians += (float)Math.PI;
float tempCosine = (float)Math.Cos(angleRadians);
float tempSine = ((float)Math.Sin(angleRadians) * -1);
EDIT
You might want to see Kinect sideways skeleton tracking for the capabilities of joint tracking
Upvotes: 2