查看: 1746|回复: 5

添加纹理坐标后 ive文件反而变小了?

[复制链接]

该用户从未签到

发表于 2009-9-6 13:50:36 | 显示全部楼层 |阅读模式
今天遇到一个问题 我用下面的一个函数 给一个节点添加纹理坐标后 再保存出去.结果发现新输出的ive文件比原来的要小 打开一看 非常的模糊.原有的地形起伏基本都消失了.
如果不调用这个函数 直接保存的话 .则不会出项这种情况.

  1. ref_ptr<Node> data=osgDB::readNodeFile (file);               
  2. applyTexture(data,txt_width,txt_height);
  3. osgDB::writeNodeFile (*(data.get()),output);
复制代码
其中调用的applyTexture方法 作用是递归找 直到找到下面的所有的Geode节点为止.
  1. void applyTexture(Node* root,float width,float height){  
  2.    Geode* gn=root->asGeode ();
  3.    if(gn)applyGeode(gn,width,height);
  4.    Group* gp=root->asGroup ();
  5.    if(gp){
  6.        for(unsigned int i=0;i<gp->getNumChildren ();i++)
  7.        {
  8.            Node* child=gp->getChild(i);
  9.            applyTexture(child,width,height);
  10.        }
  11.    }
  12. }
复制代码
最后实际写纹理坐标的代码:
  1. void applyGeode(Geode* root,float width,float height)
  2. {
  3.     if(root==NULL) return;
  4.     //获取x,y范围
  5.    BoundingBox box=root->getBoundingBox ();
  6.    float dx=box.xMax ()-box.xMin ();
  7.    float dy=box.yMax ()-box.yMin();   
  8.    for(unsigned int i=0;i<root->getNumDrawables ();i++)
  9.    {
  10.        Drawable* draw=root->getDrawable (i);
  11.        Geometry* geom=draw->asGeometry ();
  12.        if(geom)
  13.        {
  14.            Vec3Array* va=dynamic_cast<Vec3Array*>(geom->getVertexArray ());
  15.            Vec2Array* txtCoord=new Vec2Array();
  16.            Vec3Array::iterator it=va->begin ();
  17.            while(it!=va->end()){
  18.                float px=(*it).x();
  19.                float py=(*it).y();
  20.                float tx=(px-box.xMin())*width/dx;
  21.                float ty=(py-box.yMin())*height/dy;
  22.                txtCoord->push_back (Vec2(tx,ty));
  23.                
  24.                it++;
  25.            }
  26.            geom->setTexCoordArray (0,txtCoord);
  27.            //set normal data
  28.            Vec3Array* nc=new Vec3Array;
  29.            nc->push_back(Vec3(0.f,-1.f,0.f));

  30.            geom->setNormalArray(nc);
  31.            geom->setNormalBinding(Geometry::BIND_OVERALL );
  32.        }
  33.    }
  34. }
复制代码
我觉得文件应该变大才对.
而且地形起伏也不会收到影响啊.

该用户从未签到

发表于 2009-9-6 16:43:23 | 显示全部楼层
从您这段代码中我看不出什么端倪,纹理坐标的设置不会影响到地形顶点坐标,不知是不是您别的代码有错误
此外建议用NodeVisitor而不是递归函数

该用户从未签到

 楼主| 发表于 2009-9-6 18:00:44 | 显示全部楼层
这就是全部的代码了. 第一段代码 就是main()函数的内容.. 呵呵 我也觉得很奇怪.

用NodeVisitor就需要单独写一个class. 像这种不大复用的功能 我一般都是直接递归.

该用户从未签到

发表于 2009-9-6 18:26:31 | 显示全部楼层
void applyTexture(Node* root,float width,float height){  
   Geode* gn=root->asGeode ();
   if(gn)applyGeode(gn,width,height);
   Group* gp=root->asGroup ();

   if(gp){
       for(unsigned int i=0;i<gp->getNumChildren ();i++)
       {
           Node* child=gp->getChild(i);
           applyTexture(child,width,height);
       }
   }
}

你跟踪一下这个函数~~~~~

该用户从未签到

 楼主| 发表于 2009-9-7 10:08:48 | 显示全部楼层

  1. //set normal data
  2. ec3Array* nc=new Vec3Array;
  3. nc->push_back(Vec3(0.f,-1.f,0.f));
  4. geom->setNormalArray(nc);
  5. geom->setNormalBinding(Geometry::BIND_OVERALL );
复制代码
这段代码有问题.我把ive文件转成osg文件后 发现其中的几何图形本来已经有法向量坐标了 而且是BIND_PER_VERTEX的. 所以数据量比较大 被我替换成BIND_OVERALL后数据就变小了.

在去掉这一段代码后 输出的文件和原始文件一样大了。但是还是不符合我的预期 。数据应该会变大才对.每个节点一个纹理坐标 这样坐标数相当于多了一倍.由于纹理是Vec2,文件体积应该增加原来的大约2/3才对.

该用户从未签到

发表于 2009-9-7 11:15:05 | 显示全部楼层
IVE文件的存储不是您想象的那种方式,因此不能简单地按比例去计算。如果想知道纹理坐标是否正确写入的话,不妨把模型重新读入并打印它的信息
您需要登录后才可以回帖 登录 | 注册

本版积分规则

OSG中国官方论坛-有您OSG在中国才更好

网站简介:osgChina是国内首个三维相关技术开源社区,旨在为国内更多的技术开发人员提供最前沿的技术资讯,为更多的三维从业者提供一个学习、交流的技术平台。

联系我们

  • 工作时间:09:00--18:00
  • 反馈邮箱:1315785073@qq.com
快速回复 返回顶部 返回列表