stl三维数据文件的读取

10 篇文章 0 订阅

STL是CAD软件中出来的一种3D模型文件格式,wiki已经解释的很清楚了。

STL文件两种格式,ASCII STLBinary STL

ASCII STL,每一个facet由7行数据组成,outer loop后面三个顶点的顺序沿法线矢量逆时针排序,格式如下:

复制代码
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                  // 整个文件结束
复制代码

Binary STL,起始有80个字节文件头用于存储文件名,紧接4个字节表示三角形数量,而每个三角面片占用固定的50个字节,3个4字节浮点数(法线矢量),3个4字节浮点数(第一个顶点坐标),3个4字节浮点数(第二个顶点坐标),3个4字节浮点数(第三个顶点坐标),接着2个字节描述三角形基本属性,那么一个完整的二进制STL文件的字节大小就是三角形面数乘50再加上84字节,格式如下:

复制代码
UINT8[80] – Header             // 文件头
UINT32 – Number of triangles   // 三角形数量

foreach triangle
REAL32[3] – Normal vector      // 法线矢量
REAL32[3] – Vertex 1           // 第一个顶点坐标
REAL32[3] – Vertex 2           // 第二个顶点坐标
REAL32[3] – Vertex 3           // 第三个顶点坐标
UINT16 – Attribute byte count  // 文件属性
end
复制代码

下面为代码,

复制代码
#include <fstream>
#include <string>
#include <vector>
bool ReadSTLFile(const char *cfilename)
{
    if (cfilename == NULL)
        return false;

    std::ifstream in(cfilename, std::ifstream::in);

    if (!in)
        return false;

    std::string headStr;
    getline(in, headStr, ' ');
    in.close();

    if (headStr.empty())
        return false;

    if (headStr[0] == 's')
    {
        ReadASCII(cfilename);
    }
    else
    {
        ReadBinary(cfilename);
    }
    return true;
}

bool ReadASCII(const char *cfilename)
{
    std::vector<float> coorX;
    std::vector<float> coorY;
    std::vector<float> coorZ;

    int i = 0, j = 0, cnt = 0, pCnt = 4;
    char a[100];
    char str[100];
    double x = 0, y = 0, z = 0;

    std::ifstream in(cfilename, std::ifstream::in);

    if (!in)
        return false;
    do
    {
        i = 0;
        cnt = 0;
        in.getline(a, 100, '\n');
        while (a[i] != '\0')
        {
            if (!islower((int)a[i]) && !isupper((int)a[i]) && a[i] != ' ')
                break;
            cnt++;
            i++;
        }

        while (a[cnt] != '\0')
        {
            str[j] = a[cnt];
            cnt++;
            j++;
        }
        str[j] = '\0';
        j = 0;

        if (sscanf(str, "%lf%lf%lf", &x, &y, &z) == 3)
        {
            coorX.push_back(x);
            coorY.push_back(y);
            coorZ.push_back(z);
        }
        pCnt++;
    } while (!in.eof());

    return true;
}

bool ReadBinary(const char *cfilename)
{
    std::vector<float> coorX;
    std::vector<float> coorY;
    std::vector<float> coorZ;

    char str[80];
    std::ifstream in(cfilename, std::ifstream::in | std::ifstream::binary);

    if (!in)
        return false;

    in.read(str, 80);

    //number of triangles  
    int triangles;
    in.read((char*)&triangles, sizeof(int));

    if (triangles == 0)
        return false;

    for (int i = 0; i < triangles; i++)
    {
        float coorXYZ[12];
        in.read((char*)coorXYZ, 12 * sizeof(float));

        for (int j = 1; j < 4; j++)
        {
            coorX.push_back(coorXYZ[j * 3]);
            coorY.push_back(coorXYZ[j * 3 + 1]);
            coorZ.push_back(coorXYZ[j * 3 + 2]);
        }

        in.read((char*)coorXYZ, 2);
    }

    in.close();

    return true;
}



原文地址:
https://www.cnblogs.com/clairvoyant/p/5879046.html
写的不错,如果想要提取三维坐标,还需要自己认为进行数据信息的处理的,比较简单,不再赘述

扫一扫关注我:

免费获得更多的知识哦,加入就是机会,欢迎您的加入

C语言读取STL三维结构文件可以使用以下步骤进行操作。 首先,我们需要打开STL文件。可以使用C语言的文件操作函数来实现,比如fopen函数。我们需要声明一个指向文件的指针变量,然后使用fopen函数打开STL文件,并将返回的文件指针赋值给该变量。 接下来,我们需要确定STL文件的格式。STL文件有两种格式:ASCII格式和二进制格式。根据不同的格式选择不同的读取方法。 如果是ASCII格式的STL文件,我们可以使用fgets函数逐行读取文件内容。可以声明一个字符数组,然后使用fgets函数读取一行内容,并将其存储在该数组中。然后我们可以对这一行内容进行处理,提取出需要的信息。 如果是二进制格式的STL文件,我们需要声明一个结构体变量来存储STL文件中的数据。我们可以使用fread函数从文件读取指定大小的数据,并将其存储在结构体变量中。需要根据STL文件的格式来确定读取的具体方式。 无论是ASCII格式还是二进制格式的STL文件,我们在读取文件内容后都需要对文件进行关闭操作,以释放资源。可以使用fclose函数来关闭文件。 总结来说,C语言读取STL三维结构文件的步骤包括打开文件、确定文件格式、读取文件内容,处理需要的信息,并最后关闭文件。根据具体的STL文件格式和需求,我们可以选择适当的文件读取方法来完成相应的操作。
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值