00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036 #include "pcl/pcl_macros.h"
00037
00038 namespace pcl
00039 {
00040
00041 void getTransFromUnitVectorsZY(const Eigen::Vector3f& z_axis, const Eigen::Vector3f& y_direction, Eigen::Affine3f& transformation)
00042 {
00043 Eigen::Vector3f tmp0 = (z_axis.cross(y_direction)).normalized();
00044 Eigen::Vector3f tmp1 = (z_axis.cross(tmp0)).normalized();
00045 Eigen::Vector3f tmp2 = z_axis.normalized();
00046
00047 transformation(0,0)=tmp0[0]; transformation(0,1)=tmp0[1]; transformation(0,2)=tmp0[2]; transformation(0,3)=0.0f;
00048 transformation(1,0)=tmp1[0]; transformation(1,1)=tmp1[1]; transformation(1,2)=tmp1[2]; transformation(1,3)=0.0f;
00049 transformation(2,0)=tmp2[0]; transformation(2,1)=tmp2[1]; transformation(2,2)=tmp2[2]; transformation(2,3)=0.0f;
00050 transformation(3,0)=0.0f; transformation(3,1)=0.0f; transformation(3,2)=0.0f; transformation(3,3)=1.0f;
00051 }
00052
00053 Eigen::Affine3f getTransFromUnitVectorsZY(const Eigen::Vector3f& z_axis, const Eigen::Vector3f& y_direction)
00054 {
00055 Eigen::Affine3f transformation;
00056 getTransFromUnitVectorsZY(z_axis, y_direction, transformation);
00057 return transformation;
00058 }
00059
00060 void getTransFromUnitVectorsXY(const Eigen::Vector3f& x_axis, const Eigen::Vector3f& y_direction, Eigen::Affine3f& transformation)
00061 {
00062 Eigen::Vector3f tmp2 = (x_axis.cross(y_direction)).normalized();
00063 Eigen::Vector3f tmp1 = (x_axis.cross(tmp2)).normalized();
00064 Eigen::Vector3f tmp0 = x_axis.normalized();
00065
00066 transformation(0,0)=tmp0[0]; transformation(0,1)=tmp0[1]; transformation(0,2)=tmp0[2]; transformation(0,3)=0.0f;
00067 transformation(1,0)=tmp1[0]; transformation(1,1)=tmp1[1]; transformation(1,2)=tmp1[2]; transformation(1,3)=0.0f;
00068 transformation(2,0)=tmp2[0]; transformation(2,1)=tmp2[1]; transformation(2,2)=tmp2[2]; transformation(2,3)=0.0f;
00069 transformation(3,0)=0.0f; transformation(3,1)=0.0f; transformation(3,2)=0.0f; transformation(3,3)=1.0f;
00070 }
00071
00072 Eigen::Affine3f getTransFromUnitVectorsXY(const Eigen::Vector3f& x_axis, const Eigen::Vector3f& y_direction)
00073 {
00074 Eigen::Affine3f transformation;
00075 getTransFromUnitVectorsXY(x_axis, y_direction, transformation);
00076 return transformation;
00077 }
00078
00079 void getTransformationFromTwoUnitVectors(const Eigen::Vector3f& y_direction, const Eigen::Vector3f& z_axis, Eigen::Affine3f& transformation)
00080 {
00081 getTransFromUnitVectorsZY(z_axis, y_direction, transformation);
00082 }
00083
00084 Eigen::Affine3f getTransformationFromTwoUnitVectors(const Eigen::Vector3f& y_direction, const Eigen::Vector3f& z_axis)
00085 {
00086 Eigen::Affine3f transformation;
00087 getTransformationFromTwoUnitVectors(y_direction, z_axis, transformation);
00088 return transformation;
00089 }
00090
00091 void getTransformationFromTwoUnitVectorsAndOrigin(const Eigen::Vector3f& y_direction, const Eigen::Vector3f& z_axis,
00092 const Eigen::Vector3f& origin, Eigen::Affine3f& transformation)
00093 {
00094 getTransformationFromTwoUnitVectors(y_direction, z_axis, transformation);
00095 Eigen::Vector3f translation = transformation*origin;
00096 transformation(0,3)=-translation[0]; transformation(1,3)=-translation[1]; transformation(2,3)=-translation[2];
00097 }
00098
00099 inline Eigen::Affine3f getRotationOnly(const Eigen::Affine3f& transformation)
00100 {
00101 Eigen::Affine3f ret = transformation;
00102 ret(0,3) = ret(1,3) = ret(2,3) = 0.0f;
00103 return ret;
00104 }
00105
00106 inline Eigen::Vector3f getTranslation(const Eigen::Affine3f& transformation)
00107 {
00108 return Eigen::Vector3f(transformation(0,3), transformation(1,3), transformation(2,3));
00109 }
00110
00111 inline void getInverse(const Eigen::Affine3f& transformation, Eigen::Affine3f& inverse_transformation)
00112 {
00113 inverse_transformation(0,0) = transformation(0,0);
00114 inverse_transformation(0,1) = transformation(1,0);
00115 inverse_transformation(0,2) = transformation(2,0);
00116 inverse_transformation(0,3) = -transformation(0,0)*transformation(0,3) - transformation(1,0)*transformation(1,3) - transformation(2,0)*transformation(2,3);
00117 inverse_transformation(1,0) = transformation(0,1);
00118 inverse_transformation(1,1) = transformation(1,1);
00119 inverse_transformation(1,2) = transformation(2,1);
00120 inverse_transformation(1,3) = -transformation(0,1)*transformation(0,3) - transformation(1,1)*transformation(1,3) - transformation(2,1)*transformation(2,3);
00121 inverse_transformation(2,0) = transformation(0,2);
00122 inverse_transformation(2,1) = transformation(1,2);
00123 inverse_transformation(2,2) = transformation(2,2);
00124 inverse_transformation(2,3) = -transformation(0,2)*transformation(0,3) - transformation(1,2)*transformation(1,3) - transformation(2,2)*transformation(2,3);
00125 inverse_transformation(3,0) = 0.0;
00126 inverse_transformation(3,1) = 0.0;
00127 inverse_transformation(3,2) = 0.0;
00128 inverse_transformation(3,3) = 1.0;
00129 }
00130
00131 inline Eigen::Affine3f getInverse(const Eigen::Affine3f& transformation)
00132 {
00133 Eigen::Affine3f inverse_transformation;
00134 getInverse(transformation, inverse_transformation);
00135 return inverse_transformation;
00136 }
00137
00138 template <typename PointType>
00139 inline PointType transformXYZ(const Eigen::Affine3f& tranformation, const PointType& point)
00140 {
00141 PointType ret = point;
00142 ret.getVector3fMap() = tranformation * point.getVector3fMap();
00143 return ret;
00144 }
00145
00146 template <typename PointCloudType>
00147 void getTransformedPointCloud(const PointCloudType& input, const Eigen::Affine3f& transformation, PointCloudType& output)
00148 {
00149 output = input;
00150 for (unsigned int i=0; i<output.points.size(); ++i)
00151 output.points[i].getVector3fMap() = transformation*input.points[i].getVector3fMap();
00152 }
00153
00154 void getEulerAngles(const Eigen::Affine3f& t, float& roll, float& pitch, float& yaw)
00155 {
00156 roll = atan2f(t(2,1), t(2,2));
00157 pitch = asinf(-t(2,0));
00158 yaw = atan2f(t(1,0), t(0,0));
00159 }
00160
00161 void getTranslationAndEulerAngles(const Eigen::Affine3f& t, float& x, float& y, float& z, float& roll, float& pitch, float& yaw)
00162 {
00163 x = t(0,3);
00164 y = t(1,3);
00165 z = t(2,3);
00166 roll = atan2f(t(2,1), t(2,2));
00167 pitch = asinf(-t(2,0));
00168 yaw = atan2f(t(1,0), t(0,0));
00169 }
00170
00171 void getTransformation(float x, float y, float z, float roll, float pitch, float yaw, Eigen::Affine3f& t)
00172 {
00173 float A=cosf(yaw), B=sinf(yaw), C=cosf(pitch), D=sinf(pitch),
00174 E=cosf(roll), F=sinf(roll), DE=D*E, DF=D*F;
00175 t(0,0) = A*C; t(0,1) = A*DF - B*E; t(0,2) = B*F + A*DE; t(0,3) = x;
00176 t(1,0) = B*C; t(1,1) = A*E + B*DF; t(1,2) = B*DE - A*F; t(1,3) = y;
00177 t(2,0) = -D; t(2,1) = C*F; t(2,2) = C*E; t(2,3) = z;
00178 t(3,0) = 0; t(3,1) = 0; t(3,2) = 0; t(3,3) = 1;
00179 }
00180
00181 Eigen::Affine3f getTransformation(float x, float y, float z, float roll, float pitch, float yaw)
00182 {
00183 Eigen::Affine3f t;
00184 getTransformation(x, y, z, roll, pitch, yaw, t);
00185 return t;
00186 }
00187
00188 template <typename Derived>
00189 void saveBinary(const Eigen::MatrixBase<Derived>& matrix, std::ostream& file)
00190 {
00191 uint32_t rows=matrix.rows(), cols=matrix.cols();
00192 file.write((char*) &rows, sizeof(rows));
00193 file.write((char*) &cols, sizeof(cols));
00194 for (uint32_t i=0; i<rows; ++i)
00195 for (uint32_t j=0; j<cols; ++j)
00196 {
00197 typename Derived::Scalar tmp = matrix(i,j);
00198 file.write((char*) &tmp, sizeof(tmp));
00199 }
00200 }
00201
00202 template <typename Derived>
00203 void loadBinary(Eigen::MatrixBase<Derived>& matrix, std::istream& file)
00204 {
00205 uint32_t rows, cols;
00206 file.read((char*) &rows, sizeof(rows));
00207 file.read((char*) &cols, sizeof(cols));
00208
00209 if (matrix.rows()!=(int)rows || matrix.cols()!=(int)cols)
00210 {
00211
00212 matrix.resize(rows, cols);
00213 }
00214
00215 for (uint32_t i=0; i<rows; ++i)
00216 for (uint32_t j=0; j<cols; ++j)
00217 {
00218 typename Derived::Scalar tmp;
00219 file.read((char*) &tmp, sizeof(tmp));
00220 matrix(i,j) = tmp;
00221 }
00222 }
00223
00224 }