读取三维数据.stl文件
STL文件格式有两种:ASCII字符格式,及二进制格式。
ASCII字符格式的格式如下:
solid name // 文件名是可选的字符串
facet normal ni nj nk
outer loop
vertex v1x v1y v1z
vertex v2x v2y v2z
vertex v3x v3y v3z
endloop
endfacet
endsolid name //结束行标志
二进制格式数据:
因为字符格式的STL文件比较大,占空间,因为有了二进制格式,且二进制的存储格式与ASCII的格式不同。二进制有80个字节作为文件头,一般都忽略掉,但开头不能使solid,不然就不能与ASCII格式相区分了。 另外,接下来4个字节是存放的三角片的个数。
UINT8[80] – Header
UINT32 – Number of trianglesforeach triangle
REAL32[3] – Normal vector
REAL32[3] – Vertex 1
REAL32[3] – Vertex 2
REAL32[3] – Vertex 3
UINT16 – Attribute byte count
end
读取文件之前需判断文件为哪种格式:
bool isSTLBinary(const char* fileName)
{bool isBinary = false;//return valueFILE *fp = fopen(fileName, "r");//int errorCode = fopen_s(&fp, fileName, "r");// #ifdef __unix// #define fopen_s(pFile,filename, "r") ((*(pFile))=fopen((fileName), ("r")))==NULL// #endifif (fp)//成功打开文件{printf("%s isSTLBinary open success\n", fileName);//确定文件实际大小fseek(fp, 0, SEEK_END);//将fp移动到文件尾部int fileSize = ftell(fp);//返回文档首部到fp位置大小(bytes)int facetNum;//计算标准stl二进制文件的大小fseek(fp, 80, SEEK_SET);//跳过文档开头的注释size_t t = fread(&facetNum, sizeof(int), 1, fp);//读取facet的数目并保存在facetNum中int standardBinaryFileSize = 80 + sizeof(int) + facetNum * 50;//判断是否是标准stl文件if (fileSize == standardBinaryFileSize){isBinary = true;}//判断是否是非标准stl文件unsigned char tmpbuf[128];//如果文件过短,这里会有Bugt = fread(tmpbuf, sizeof(tmpbuf), 1, fp);//读取128个char大小的数据for (unsigned int i = 0;i<sizeof(tmpbuf);i++){//char类型取值范围是-128~127,如果是ASCII格式,应该全是charif (tmpbuf[i]>127){isBinary = true;break;}}fclose(fp);printf("t=%d\n", (int)t);}else{printf("%s isSTLBinary open file fail\n", fileName);}return isBinary;
}
之后再根据文件格式选择读取方法。
读取二进制文件:
void openBinaryFile(std::string fileName, std::vector<float>& positions, std::vector<float>& normals)
{FILE *fp = fopen(fileName.c_str(), "rb");int numFacet;//int error= fopen_s(&fp,fileName, "rb");float normal[3];float point1[3];if (fp)//成功打开文件{fseek(fp, 80, SEEK_SET);//跳过开头size_t t = fread(&numFacet, sizeof(int), 1, fp);//读取facet的数目for (int facetIndex = 0; facetIndex < numFacet;++facetIndex){unsigned short attr; //用来储存属性,实际上把这个值丢弃了t = fread(normal, sizeof(float), 3, fp);//读取facet的法向量for (int i = 0; i < 3;++i){t = fread(point1, sizeof(float), 3, fp);//读取vertexpositions.push_back(point1[0] / 1000);positions.push_back(point1[1] / 1000);positions.push_back(point1[2] / 1000);normals.push_back(point1[0] / 1000);normals.push_back(point1[1] / 1000);normals.push_back(point1[2] / 1000);//printf ("%f, %f %f", point1[0], point1[1], point1[2]);}t = fread(&attr, sizeof(unsigned short), 1, fp);//读取属性}printf("t=%d\n", (int)t);}else {printf("%s open fail\n", fileName.c_str());}fclose(fp);
}
读取ASCII文件:
void openASCIIFile(std::string fileName, std::vector<float>& positions, std::vector<float>& normals)
{std::ifstream ifs;ifs.open(fileName, std::ifstream::in);if (ifs.is_open()){/*略去第一行*/std::string line;getline(ifs, line);/*读取facet*/int readCounter = 0;//记录每行读取成功的数据项int lineCounter = 0;double x,y,z = 0;double pointX, pointY, pointZ = 0;while (!ifs.eof()){/*读取facet normal ni nj nk*/getline(ifs, line);readCounter = sscanf(line.c_str(), "%*s %*s %lf %lf %lf\n", &x, &y, &z);if (readCounter!=3){// we could be in the case of a multiple solid object, where after a endfaced instead of another facet we have to skip two lines:// endloop// endfacet//endsolid <- continue on ret==0 will skip this line//solid ascii <- and this one.// facet normal 0.000000e+000 7.700727e-001 -6.379562e-001lineCounter++;continue;}//end ifgetline(ifs, line);//读取outer loop
/*读取三个顶点坐标vertex v1x v1y v1z*/for (int i = 0; i < 3;i++){getline(ifs, line);readCounter=sscanf(line.c_str(),"%*s %lf %lf %lf", &pointX, &pointY, &pointZ);positions.push_back(pointX);positions.push_back(pointY);positions.push_back(pointZ);normals.push_back(pointX);normals.push_back(pointY);normals.push_back(pointZ);}getline(ifs, line);//读取“endloop”getline(ifs, line);//读取"endfacet"lineCounter += 7;}// end while (ifs.eof())}//end if (ifs.is_open())else{return;}ifs.close();
}
读取三维数据.stl文件相关推荐
- Matlab读取并输出stl文件
*#利用matlab读取stl文件后,将其中三角形片数据×2后,保存到另一个stl文件,利用3D软件打开观察图形是否变为两倍.那么应该怎么做呢? 首先了解一下stl文件 STL(Stereo lith ...
- python读取dat数据_dat文件读写_c语言读写dat文件_c语言读dat文件 - 云+社区 - 腾讯云...
广告关闭 腾讯云11.11云上盛惠 ,精选热门产品助力上云,云服务器首年88元起,买的越多返的越多,最高返5000元! 13 }文件读写:写入目录的获取比较麻烦,各个平台不同,所以用c++自己的文件读 ...
- 成信大ENVI_IDL第三周课堂内容1:读取OMI数据(HDF5文件)以及输出+解析
目录 1. 课堂内容 2. 知识储备 3. 编程 4. 题外话(HDF5下的中文路径问题) 1. 课堂内容 OMI数据的读取与输出,这里实际考察如何取读取HDF5文件以及HDF5文件输出(这里输出是以 ...
- stl文件怎么用Java读取_vtk对stl文件进行下采样
在加载stl文件的时候有些文件的mesh太多导致加载速度太慢需要进行下采样,以便提高加载速度,可以使用vtk提供的vtkDecimatePro进行下采样. #include #include #inc ...
- 使用POI读取大量数据EXCEL文件,并解析成自定义javaBean
1.几个javaBean的定义 因为javabean比较简单 这里就不详细写了,get set和构造方法自己定义 public class Excel {private String fileName ...
- matlab db文件怎么打开,matlab下如何读取Access数据.mdb文件
用matlab读取 .mdb文件一般需要分两步: 第一步:为 .mdb文件创建一个数据源(使用ODBC来连接) 1.windows xp操作系统的:在命令行中输入odbcad32,打开odbc资源管理 ...
- python读取大数据量文件_python读取大数据文件
{"moduleinfo":{"card_count":[{"count_phone":1,"count":1}],&q ...
- 如何读取STL文件?
STL文件有两种文件格式,分别是二进制的stl和Ascii格式的stl.下面将针对这文件的两个格式,用C语言分别写出一段简单的示例代码. 一.读取二进制的STL文件 (1)二进制stl文件的结构 文件 ...
- MATLAB快速读取STL文件
MATLAB快速读取STL文件 一.STL文件格式 binary格式 ascii格式stl 二.开源代码 安装方法 使用方法 三.快速读取 binary格式stl ascii格式stl 四.效果对比 ...
最新文章
- 丰度决定了细菌在复杂群落中的功能作用
- 服务器防渗透(1)--信息收集
- android 字符串 转公式,java – 在android中将字符串转换为bigdecimal
- linux delete内存不下降_linux内存分配管理
- 高等组合学笔记(九): 球盒模型的十二模式,分拆的生成函数
- Hadoop系列之FieldSelectionMapReduce用法
- 自主编写的新书出版2个月,竟然上了51cto读书频道的动态首页,兴奋中!
- python 多线程就这么简单
- 平年用c语言的计算方式,C语言平年闰年问题
- python课堂随机点名_【工作中的Python】随机点名小脚本
- iframe 实现网页本页显示
- ttysac1 java_ttySAC0与/dev/tts/0是否对应同一个物理设备串口0
- MP3、MP4、MP5、PSP
- 这是我对智能制造的所有理念
- 随机过程在计算机领域的应用,随机过程与排队论——及其在计算机领域中的应用.doc...
- golang优雅的使用context
- 2021年专插本计算机专业分数线预估,【参考】2016-2020年专插本省最低录取控制线预估2021年最低录取分数线是多少...
- python汉字拼音查询_Python汉字转拼音
- Shufti Pro宣布获得2000万美元A轮融资以加速发展
- 使用微信小程序实现学生登录