Take the 2-minute tour ×

I know how to convert in pixels the value obtained from Joint.Position.X and Joint.Position.Y. There is an example in which I do it:

void kinectSensor_SkeletonFrameReady(object sender, SkeletonFrameReadyEventArgs e)
        using (SkeletonFrame skeletonFrame = e.OpenSkeletonFrame())
            if (skeletonFrame != null)
                Skeleton[] skeletonData = new Skeleton[skeletonFrame.SkeletonArrayLength]; //conterrà tutti gli skeleton


                Skeleton playerSkeleton = (from s in skeletonData where s.TrackingState == SkeletonTrackingState.Tracked select s).FirstOrDefault();

                if (playerSkeleton != null)
                    Joint rightHand = playerSkeleton.Joints[JointType.HandRight];
                    Joint leftHand = playerSkeleton.Joints[JointType.HandLeft];

                    //EDIT: The following formulas used to convert X and Y coordinates in pixels are wrong.
                    //Please, see the answer for details
                    rightHandPosition = new float[] { (((0.5f * rightHand.Position.X) + 0.5f) * (640)), (((-0.5f * rightHand.Position.Y) + 0.5f) * (480)) };
                    leftHandPosition = new float[] { (((0.5f * leftHand.Position.X) + 0.5f) * (640)), (((-0.5f * leftHand.Position.Y) + 0.5f) * (480)), leftHand.Position.Z };

Now, what I want to do is obtain the real depth (in millimeters) using Joint.Depth.Z. Referring to the previous example, I want to obtain two 3D arrays for rightHandPosition and leftHandPosition, with the the last coordinate that represents the depth. What is the right formula in order to transform the value returned from rightHand.Position.Z and leftHand.Position.Z in the corresponding value in millimeters?

EDIT: The formulas used to transform X and Y coordinates in pixels in the code above are wrong. Please, read the following answer by me.

share|improve this question
I don't know anything about how the Kinect works, but I can deduce a bit from what you've posted. Judging from what you posted, rightHand (and leftHand).Position gives you a 3D {x,yz,} value, normalized from 0 to 1. So, you have a 3D coordinate. You just need to scale and maybe translate it. What is that 0..1 range covering? I'd assume it's the bounding box of what the Kinect scans. Can you query that information from somewhere? If so, just multiply each dimension times (its end point - its start point) and add the start point. –  Scott Mermelstein Mar 13 '13 at 16:29
I asked this question because sometimes I receive values for Z that are greater than 1. That's the problem... But thank you for your suggestions :) –  VitoShadow Mar 13 '13 at 16:53
The value returned by Position.Z is in meters. –  Evil Closet Monkey Mar 13 '13 at 16:55
@Evil Closet Monkey: Can you give me a reference in which what you said is confirmed? –  VitoShadow Mar 13 '13 at 17:09
msdn.microsoft.com/en-us/library/hh973078.aspx -- "skeleton space coordinates are expressed in meters." –  Evil Closet Monkey Mar 13 '13 at 17:11
show 2 more comments

1 Answer

up vote 4 down vote accepted

I have realized that Joint.Position.X and Joint.Position.Y are not limited between -1 and 1. This wrong information is quite diffused on internet, and this is the reason why I'm replying to myself.

As Evil Closet Monkey has mentioned, in the comments above, the official documentation says that "skeleton space coordinates are expressed in meters". It's also confirmed by a member of the Kinect for Windows Team in this post.

It means that in order to convert X, Y and Z coordinates, obtained with Joint.Position.X, Joint.Position.Y and Joint.Position.Z, in millimeters, you simply have to divide these values by 1000 (or you can also work in meters, with no conversions needed).

share|improve this answer
add comment

Your Answer


