如何从文件预加载 3D 模型并在 OSG 中多次使用它

How to pre-load a 3D model from file and use it multiple times in OSG?

本文关键字:OSG 文件 加载 模型 3D      更新时间:2023-10-16

有没有办法使用 osgDB 预加载静态 3D 模型文件,然后在场景中多次使用相同的模型,而不必复制osg::Node也不必再次加载文件?

理想的情况是,如果模型数据可以存储在由osg::ref_ptr指向的类中,然后该类将在表示场景中对象的节点之间重新分配。

只需将osg::Group的实例或它的某个子类的实例放在您希望节点位于场景中的位置,然后将addChild(node)调用到组中。

通常,我使用的 Group 子类是 osg::P ositionAttitudeTransform 或 osg::MatrixTransform,这样我也可以对它们应用变换。

-

希望有帮助-

使用 osg::Node,您可以使用克隆方法并定义在克隆期间在对象之间复制哪些数据。查看示例代码:

osg::ref_ptr<osg::Group> root = new osg::Group;
osg::ref_ptr<osg::Node> n = osgDB::readNodeFile(fn);
// n2 will be deep copy of n - all data of n will be copied to n2
osg::ref_ptr<osg::Node> n2 = dynamic_cast<osg::Node*>(n->clone(osg::CopyOp::DEEP_COPY_ALL));
// n3 will be shallow copy of n - all possible data will be shared between n3 and n
osg::ref_ptr<osg::Node> n3 = dynamic_cast<osg::Node*>(n->clone(osg::CopyOp::SHALLOW_COPY));

使用克隆方法和 copyOp 枚举,您可以轻松定义共享哪些数据以及复制哪些数据。更多信息可以在这里找到 OSG 文档。

我还没有找到osgDB的任何预加载选项,但是可以像这样轻松实现:

class GraphFilesManager {
    static osg::Node* GraphFilesManager::readNodeFile(std::string file)
    {
        bool wasLoaded = false;
        for (int i=0; i < loadedNodefilenames.size(); i++)
        {
        if (file.compare (loadedNodefilenames[i])==0)
            {
                osg::Node* newNode = dynamic_cast<osg::Node*>( loadedNode[i]->clone(osg::CopyOp::DEEP_COPY_NODES));
                return newNode;
            }
        }
        osg::Node* newNode = osgDB::readNodeFile(file);
        if (newNode)
        {
            loadedNode.push_back(newNode);
            loadedNodefilenames.push_back(file);
        }
        return newNode;
    }
    static std::vector <osg::Node*> loadedNode;
    static std::vector <std::string> loadedNodefilenames;
}

在我的应用程序中,模型数量很少,我不得不进行深度复制。希望它有帮助。