| 4750 | } |
| 4751 | |
| 4752 | XN_C_API XnStatus xnConvertRealWorldToProjective(XnNodeHandle hInstance, XnUInt32 nCount, const XnPoint3D* aRealWorld, XnPoint3D* aProjective) |
| 4753 | { |
| 4754 | XnStatus nRetVal = XN_STATUS_OK; |
| 4755 | |
| 4756 | XN_VALIDATE_INTERFACE_TYPE(hInstance, XN_NODE_TYPE_DEPTH); |
| 4757 | |
| 4758 | /** |
| 4759 | * X_proj = X_res * (X_RW / (z*x_to_z) + 1/2) |
| 4760 | * |
| 4761 | * = X_res / x_to_z * X_RW / z + X_res/2 (more efficient) |
| 4762 | */ |
| 4763 | |
| 4764 | XnMapOutputMode outputMode; |
| 4765 | nRetVal = xnGetMapOutputMode(hInstance, &outputMode); |
| 4766 | XN_IS_STATUS_OK(nRetVal); |
| 4767 | |
| 4768 | xn::DepthPrivateData* pDepthPrivate = (xn::DepthPrivateData*)hInstance->pPrivateData; |
| 4769 | XnDouble fXToZ = pDepthPrivate->GetRealWorldXtoZ(); |
| 4770 | XnDouble fYToZ = pDepthPrivate->GetRealWorldYtoZ(); |
| 4771 | |
| 4772 | XnDouble fCoeffX = outputMode.nXRes / fXToZ; |
| 4773 | XnDouble fCoeffY = outputMode.nYRes / fYToZ; |
| 4774 | |
| 4775 | // we can assume resolution is even (so integer div is sufficient) |
| 4776 | XnUInt32 nHalfXres = outputMode.nXRes / 2; |
| 4777 | XnUInt32 nHalfYres = outputMode.nYRes / 2; |
| 4778 | |
| 4779 | for (XnUInt32 i = 0; i < nCount; ++i) |
| 4780 | { |
| 4781 | aProjective[i].X = (XnFloat)fCoeffX * aRealWorld[i].X / aRealWorld[i].Z + nHalfXres; |
| 4782 | aProjective[i].Y = nHalfYres - (XnFloat)fCoeffY * aRealWorld[i].Y / aRealWorld[i].Z; |
| 4783 | aProjective[i].Z = aRealWorld[i].Z; |
| 4784 | } |
| 4785 | |
| 4786 | return (XN_STATUS_OK); |
| 4787 | } |
| 4788 | |
| 4789 | XN_C_API XnDepthPixel* xnGetDepthMap(XnNodeHandle hInstance) |
| 4790 | { |
no test coverage detected