writeSTL.cpp 2.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102
  1. #include "writeSTL.h"
  2. #include <iostream>
  3. template <typename DerivedV, typename DerivedF, typename DerivedN>
  4. IGL_INLINE bool igl::writeSTL(
  5. const std::string & filename,
  6. const Eigen::PlainObjectBase<DerivedV> & V,
  7. const Eigen::PlainObjectBase<DerivedF> & F,
  8. const Eigen::PlainObjectBase<DerivedN> & N,
  9. const bool ascii)
  10. {
  11. using namespace std;
  12. assert(N.rows() == 0 || F.rows() == N.rows());
  13. if(ascii)
  14. {
  15. FILE * stl_file = fopen(filename.c_str(),"w");
  16. if(stl_file == NULL)
  17. {
  18. cerr<<"IOError: "<<filename<<" could not be opened for writing."<<endl;
  19. return false;
  20. }
  21. fprintf(stl_file,"solid %s\n",filename.c_str());
  22. for(int f = 0;f<F.rows();f++)
  23. {
  24. fprintf(stl_file,"facet normal ");
  25. if(N.rows()>0)
  26. {
  27. fprintf(stl_file,"%e %e %e\n",
  28. (float)N(f,0),
  29. (float)N(f,1),
  30. (float)N(f,2));
  31. }else
  32. {
  33. fprintf(stl_file,"0 0 0\n");
  34. }
  35. fprintf(stl_file,"outer loop\n");
  36. for(int c = 0;c<F.cols();c++)
  37. {
  38. fprintf(stl_file,"vertex %e %e %e\n",
  39. (float)V(F(f,c),0),
  40. (float)V(F(f,c),1),
  41. (float)V(F(f,c),2));
  42. }
  43. fprintf(stl_file,"endloop\n");
  44. fprintf(stl_file,"endfacet\n");
  45. }
  46. fprintf(stl_file,"endsolid %s\n",filename.c_str());
  47. fclose(stl_file);
  48. return true;
  49. }else
  50. {
  51. FILE * stl_file = fopen(filename.c_str(),"wb");
  52. if(stl_file == NULL)
  53. {
  54. cerr<<"IOError: "<<filename<<" could not be opened for writing."<<endl;
  55. return false;
  56. }
  57. // Write unused 80-char header
  58. for(char h = 0;h<80;h++)
  59. {
  60. fwrite(&h,sizeof(char),1,stl_file);
  61. }
  62. // Write number of triangles
  63. unsigned int num_tri = F.rows();
  64. fwrite(&num_tri,sizeof(unsigned int),1,stl_file);
  65. assert(F.cols() == 3);
  66. // Write each triangle
  67. for(int f = 0;f<F.rows();f++)
  68. {
  69. vector<float> n(3,0);
  70. if(N.rows() > 0)
  71. {
  72. n[0] = N(f,0);
  73. n[1] = N(f,1);
  74. n[2] = N(f,2);
  75. }
  76. fwrite(&n[0],sizeof(float),3,stl_file);
  77. for(int c = 0;c<3;c++)
  78. {
  79. vector<float> v(3);
  80. v[0] = V(F(f,c),0);
  81. v[1] = V(F(f,c),1);
  82. v[2] = V(F(f,c),2);
  83. fwrite(&v[0],sizeof(float),3,stl_file);
  84. }
  85. unsigned short att_count = 0;
  86. fwrite(&att_count,sizeof(unsigned short),1,stl_file);
  87. }
  88. fclose(stl_file);
  89. return true;
  90. }
  91. }
  92. template <typename DerivedV, typename DerivedF>
  93. IGL_INLINE bool igl::writeSTL(
  94. const std::string & filename,
  95. const Eigen::PlainObjectBase<DerivedV> & V,
  96. const Eigen::PlainObjectBase<DerivedF> & F,
  97. const bool ascii)
  98. {
  99. return writeSTL(filename,V,F, Eigen::PlainObjectBase<DerivedV>(), ascii);
  100. }