如何通过指针而不是OpenSceneGraph中的副本访问数组数据?

时间:2015-10-29 15:07:51

标签: c++ openscenegraph

我用OpenSceneGraph(osg)编写了一个小动画程序。在每个帧中,我应该更新场景中的模型(顶点位置,法线,颜色和其他东西)。

现在我在每帧中将数据转换为osg。代码如下:

cog_.vertex_->clear();
cog_.vertex_->push_back(osg::Vec3(1.0,1.0,1.0));

然而,这些转换非常耗时。所以我想知道如何通过指针直接访问数据。我试过但失败了。以下是我的所作所为,希望有人能帮助我找到问题,或者告诉我更好的解决方案:

首先,我将指针包装到osg :: Vec3,

class vec3_map : public osg::Vec3
{
public:
    typedef osg::Vec3::value_type value_type;
    osg::Vec3::value_type* p_;

    vec3_map() :p_(0) {}
    vec3_map(osg::Vec3::value_type*p, int offset = 0) :p_(p+offset){}

    inline value_type& x() { return *(p_+0); }
    inline value_type& y() { return *(p_+1); }
    inline value_type& z() { return *(p_+2); }

    // some other stuff
};

当我想构建一个vec3_map数组时,我发现osg使用tempalte来键入def Vec3Array,但是没有任何类型的指针,所以我选择了一个(我知道指针是一个带有unsigned的变量) long int type):

 typedef osg::TemplateArray<vec3_map, osg::Array::UIntArrayType, 1, GL_UNSIGNED_INT> Vec3_map_Array;

通过这个定义,我可以将我的问题重写为以下内容:

#define BOOST_ALL_NO_LIB
#include <boost/shared_ptr.hpp>
#include <fstream>

#include <vector>
#include <osg/Group>
#include <osg/Geometry>
#include <osgViewer/Viewer>
#include <osg/Vec3>

class vec3_map : public osg::Vec3
{
public:
typedef osg::Vec3::value_type value_type;
osg::Vec3::value_type* p_;

vec3_map() :p_(0) {}
vec3_map(osg::Vec3::value_type*p, int offset = 0) :p_(p + offset) {}

inline value_type* ptr() { return p_; }
inline const value_type* ptr() const { return p_; }

inline value_type& operator [] (int i) { return *(p_ + i); }
inline value_type operator [] (int i) const { return *(p_ + i); }

inline value_type& x() { return *(p_ + 0); }
inline value_type& y() { return *(p_ + 1); }
inline value_type& z() { return *(p_ + 2); }

inline value_type x() const { return *(p_); }
inline value_type y() const { return *(p_ + 1); }
inline value_type z() const { return *(p_ + 2); }
};


typedef osg::TemplateArray<vec3_map, osg::Array::UIntArrayType, 1,     GL_UNSIGNED_INT> Vec3_map_Array;

struct point_data
{
 point_data(float xx, float yy, float zz) { x = xx; y = yy; z = zz; }
 float x;
 float y;
 float z;
};

osg::Geode* create_point_node(boost::shared_ptr<std::vector<point_data> > ptr)
{
 osg::Geode *geode_ = new osg::Geode;
 osg::Geometry* geometry_ = new osg::Geometry;
 Vec3_map_Array* vertex_ = new Vec3_map_Array;
 osg::DrawElementsUInt* point_idx_ = new osg::DrawElementsUInt;

 vertex_->reserve(ptr->size());
 point_idx_->reserve(ptr->size());

 vec3_map vm;
 std::vector<point_data> & pd = *ptr;
 for (size_t i = 0; i < ptr->size(); ++i)
 {
    vertex_->push_back(vec3_map(&(pd[i].x)));
    point_idx_->push_back(i);
 }

 geometry_->setVertexArray(vertex_);
 geometry_->addPrimitiveSet(point_idx_);
 geode_->addDrawable(geometry_);
 return geode_;
}

int main(int argc, char *argv[])
{
 boost::shared_ptr<std::vector<point_data> > pd(new std::vector<point_data>);
 pd->push_back(point_data(1.0, 1.0, 1.0));
 pd->push_back(point_data(2.0, 2.0, 2.0));

 osgViewer::Viewer viewer;
 osg::Node *node = create_point_node(pd);
 viewer.setSceneData(node);
 return viewer.run();
}

然而,这个问题崩溃了。我不确定我是否可以做这样的事情。

0 个答案:

没有答案