Hi
 
yes, it's doing just that, but it written in a way to keep duplicate vertices with same position if other vertex attributes for this vertex is different. I checked it's sources and all looks fine to me. Also, same code was working fine like half a year ago.
 
Cheers.
 
25.04.2013, 21:06, "Glenn Waldron" <gwald...@gmail.com>:
Sergey,
I believe the IndexMeshVisitor attempts to detect and remove duplicate vertices. Could that be the reason?
 

Glenn Waldron / @glennwaldron


On Thu, Apr 25, 2013 at 11:16 AM, Sergey Polischuk <pol...@yandex.ru> wrote:
Hi all

once i've wrote small utility to optimize models with rig geometry, which, among other things, apply INDEX_MESH, VERTEX_PRETRANSFORM, VERTEX_POSTTRANSFORM optimizations and remaps vertex influences of rig geometry to new vertex indices. Now it suddenly dont work any more.

Problem is that after indexing geometry, there are not enough matches between old vertex attributes and new vertex attributes (some old vertex attribute values cant be found in new vertex attribute arrays after indexing, which means some data is lost).

here is some simplified code to show problem:

//////////////////////////////////////////////////////////////

template <typename T> bool compare(T* r, unsigned ri, T* l, unsigned li) //compares two array elements
{
        if ((*r)[ri] < (*l)[li])
                return false;
        if ((*l)[li] < (*r)[ri])
                return false;

        return true;
}

bool cmp (osg::Geometry::ArrayList& rhs, unsigned rhsi, osg::Geometry::ArrayList& lhs, unsigned lhsi) //compares all [rhsi] elements from rhs array list with all [lhsi] elements in lhs array list
{
        if (rhs.size() != lhs.size())
                throw std::logic_error("different vertex attrib arrays count before and after optimizations, cant do anything");
        bool result = true;
        for (unsigned i = 0; i< rhs.size(); i++)
        {
                bool compared = false;
                if (!result)
                        return result;
                {
                        osg::Vec3Array* r = dynamic_cast<osg::Vec3Array*>(rhs[i]);
                        osg::Vec3Array* l = dynamic_cast<osg::Vec3Array*>(lhs[i]);
                        if (r && l)
                        {
                                result = result && compare<>(r, rhsi, l, lhsi);
                                compared = true;
                        }
                }
                {
                        osg::Vec2Array* r = dynamic_cast<osg::Vec2Array*>(rhs[i]);
                        osg::Vec2Array* l = dynamic_cast<osg::Vec2Array*>(lhs[i]);
                        if (r && l)
                        {
                                result = result && compare<>(r, rhsi, l, lhsi);
                                compared = true;
                        }
                }
                if (!compared)
                        return false;
        }
        return result;
}

        void acceptMesh(osgAnimation::RigGeometry* rg)
        {
                osg::Geometry* g = rg->getSourceGeometry();

                osg::ref_ptr<osg::Geometry> origG = new osg::Geometry(*g, osg::CopyOp::DEEP_COPY_ALL);

                osg::Geometry::ArrayList alold;
                origG->getArrayList(alold);
                osg::ref_ptr<osg::Vec3Array> origVerts = dynamic_cast<osg::Vec3Array*>(origG->getVertexArray());

                osgUtil::IndexMeshVisitor imv;
                imv.makeMesh(*g);

                osg::Geometry::ArrayList alnew;
                g->getArrayList(alnew);

                std::map<int, int> vertsMap;//store matches between old and new vertexattrib arrays in pairs [old_index, new_index]
                osg::ref_ptr<osg::Vec3Array> newVerts = dynamic_cast<osg::Vec3Array*>(g->getVertexArray());

                unsigned id = 0;
                for (osg::Vec3Array::iterator itr = origVerts->begin(); itr != origVerts->end(); itr++)
                {
                        unsigned nid = 0;
                        for (osg::Vec3Array::iterator itr2 = newVerts->begin(); itr2 != newVerts->end(); itr2++)
                        {
                                if (cmp(alold, id, alnew, nid))//found match
                                {
                                        vertsMap[id] = nid;
                                        break;
                                }
                                nid++;
                        }
                        id++;
                }
                std::cerr<<"origVerts size:"<<origVerts->size()<<std::endl;
                std::cerr<<"verts map size:"<<vertsMap.size()<<std::endl;
        }

/////////////////////////////////////////////////////////////

here size of vertsMap map should be same as original vertex count, and it isnt, which means some data is lost when indexing geometry (and comparing floating point values with thresholds does not change anything, i've tested it).

Any ideas about what could go wrong? May be there was some changes to the way IndexMeshVisitor works? I'm testing on osg svn version updated last week or so.

Cheers,
Sergey.
_______________________________________________
osg-users mailing list
osg-users@lists.openscenegraph.org
http://lists.openscenegraph.org/listinfo.cgi/osg-users-openscenegraph.org
,

_______________________________________________
osg-users mailing list
osg-users@lists.openscenegraph.org
http://lists.openscenegraph.org/listinfo.cgi/osg-users-openscenegraph.org

_______________________________________________
osg-users mailing list
osg-users@lists.openscenegraph.org
http://lists.openscenegraph.org/listinfo.cgi/osg-users-openscenegraph.org

Reply via email to