OSG中提到的visitor通常都是使用NodeVisitor,在毕设论文中做场景重构的时候需要获取三角面片的纹理坐标时,用到了getTexCoorArray()函数,对他们的读取要用到ArrayVisitor。但是网上有关ArrayVisitor的资料相当少,可能是因为ArrayVisitor的处理相对比较简单的原因?
1.使用ArrayVisitor的方法获取。
类似于NodeVisitor一样,需要定义Visitor类:
#include <iostream>
#include <osgDB/ReadFile>
#include <osg/Node>
#include <osg/Group>
#include <osg/Geode>
#include <osgViewer/Viewer>
#include <osg/Array>
class TexCoorVisitor : public osg::ArrayVisitor
{
public:
TexCoorVisitor(): osg::ArrayVisitor()
{
mTexCoorArray = new osg::Vec2Array;
}
virtual void apply(osg::Vec2Array &array)
{
mTexCoorArray = &array;
}
osg::Vec2Array* GetTexCoorArray()
{
return mTexCoorArray;
}
private:
osg::Vec2Array* mTexCoorArray;
};
void main(int argc, char* argv[])
{
osg::Node* node = osgDB::readNodeFile("cow.osg");
osgViewer::Viewer* view = new osgViewer::Viewer;
osg::ref_ptr<osg::Group> group = new osg::Group;
group->addChild(node);
//view->setSceneData(group.get());
//view->run();
osg::Geometry* geom = node->asGroup()->getChild(0)->asGeode()->getDrawable(0)->asGeometry();
osg::Array* tmp = geom->getTexCoordArray(0);
TexCoorVisitor* tcv = new TexCoorVisitor;
tmp->accept(*tcv);
osg::Vec2Array* res = tcv->GetTexCoorArray();
std::cout<<res->size()<<std::endl;
auto it = res->begin();
for(; it<res->end(); it++)
{
std::cout<<(*it).x()<<" "<<(*it).y()<<std::endl;
}
system("pause");
}
2.使用地址强转的方法来获取纹理坐标数组
如果明白ArrayVisitor的原理的话,其实还可以用地址强转这种比较简单的方法来获取纹理坐标。
osg::Vec2Array* coorArray = (osg::Vec2Array*) tmp;
auto it = coorArray->begin();
// for(; it<tmp2->end(); it++)
// {
// std::cout<<it->x()<<std::endl;
// std::cout<<count++<<std::endl;
// }