Go to the documentation of this file.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 #include <rve_mesh_loader/stl_parser.h>
00031 #include <ros/console.h>
00032
00033 #include <rve_msgs/Mesh.h>
00034
00035 #include <Eigen/Geometry>
00036
00037 namespace rve_mesh_loader
00038 {
00039
00040 void calculateUV(const Eigen::Vector3f& vec, float& u, float& v)
00041 {
00042 Eigen::Vector3f pos(vec);
00043 pos.normalize();
00044 u = acos( pos.y() / pos.norm() );
00045
00046 float val = pos.x() / ( sin( u ) );
00047 v = acos( val );
00048
00049 u /= M_PI;
00050 v /= M_PI;
00051 }
00052
00053 void parseSTL(uint8_t* buffer, size_t buffer_size, const std::string& extension, rve_msgs::Mesh& out_mesh)
00054 {
00055 out_mesh.submeshes.resize(1);
00056 rve_msgs::SubMesh& submesh = out_mesh.submeshes[0];
00057 uint8_t* pos = buffer;
00058 pos += 80;
00059
00060 uint32_t tri_count = *(uint32_t*)pos;
00061 pos += 4;
00062
00063 submesh.positions.resize(tri_count * 3);
00064 submesh.normals.resize(tri_count * 3);
00065 submesh.indices.resize(tri_count * 3);
00066 submesh.tex_coords.resize(1);
00067 submesh.tex_coords[0].array.resize(tri_count * 3);
00068 submesh.tex_coords[0].dims = 2;
00069 for ( uint32_t tri = 0; tri < tri_count; ++tri )
00070 {
00071
00072 Eigen::Vector3f normal;
00073
00074 normal.x() = *(float*)pos;
00075 pos += 4;
00076 normal.y() = *(float*)pos;
00077 pos += 4;
00078 normal.z() = *(float*)pos;
00079 pos += 4;
00080
00081
00082 for (uint32_t i = 0; i < 3; ++i)
00083 {
00084 uint32_t vert_index = tri * 3 + i;
00085 rve_msgs::Vector3& p = submesh.positions[vert_index];
00086 p.x = *(float*)pos;
00087 pos += 4;
00088 p.y = *(float*)pos;
00089 pos += 4;
00090 p.z = *(float*)pos;
00091 pos += 4;
00092
00093 rve_msgs::TexCoord& uvw = submesh.tex_coords[0].array[vert_index];
00094 calculateUV( Eigen::Vector3f(p.x, p.y, p.z), uvw.uvw[0], uvw.uvw[1] );
00095 }
00096
00097
00098
00099 pos += 2;
00100
00101
00102
00103 if (normal.squaredNorm() < 0.001)
00104 {
00105 rve_msgs::Vector3& p0 = submesh.positions[0];
00106 rve_msgs::Vector3& p1 = submesh.positions[1];
00107 rve_msgs::Vector3& p2 = submesh.positions[2];
00108 Eigen::Vector3f side1 = Eigen::Vector3f(p0.x, p0.y, p0.z) - Eigen::Vector3f(p1.x, p1.y, p1.z);
00109 Eigen::Vector3f side2 = Eigen::Vector3f(p1.x, p1.y, p1.z) - Eigen::Vector3f(p2.x, p2.y, p2.z);
00110 normal = side1.cross(side2);
00111 normal.normalize();
00112 }
00113
00114
00115 for (uint32_t i = 0; i < 3; ++i)
00116 {
00117 uint32_t vert_index = tri * 3 + i;
00118 rve_msgs::Vector3& n = submesh.normals[vert_index];
00119 n.x = normal.x();
00120 n.y = normal.y();
00121 n.z = normal.z();
00122 }
00123 }
00124 }
00125
00126 }