Hello Robert,

I have found a bug when assigning a new image to an existing texture that already has an OpenGL texture object allocated. The problem appears to be that Texture2D::apply is passing the wrong dimensions in to applyTexImage2D_subload. Since the dimensions of the image don't match the dimensions of the existing OpenGL texture object, subloading shouldn't even be used. I therefore get the following error printed out on the console:

Warning: detected OpenGL error 'invalid value' after RenderBin::draw(,)

The dimensions of the Texture::TextureObject should be validated against the data being loaded before calling subload, probably in the Texture*::apply methods.

Mark
#include <osg/Texture2D>
#include <osg/Geometry>

#include <osgViewer/Viewer>
#include <osgGA/TrackballManipulator>

int main()
{
    osg::ref_ptr<osg::Texture2D> texture1 = new osg::Texture2D;
    static unsigned char bytes[16] = {
        0xff, 0x00, 0x00, 0xff,
        0x00, 0xff, 0x00, 0xff,
        0x00, 0x00, 0xff, 0xff,
        0xff, 0x00, 0xff, 0xff,
    };
    osg::ref_ptr<osg::Image> imageRGB = new osg::Image;
    imageRGB->setImage(3, 1, 1, GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, &bytes[0], 
osg::Image::NO_DELETE, 1);
    osg::ref_ptr<osg::Image> imageRed = new osg::Image;
    imageRed->setImage(1, 1, 1, GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, &bytes[0], 
osg::Image::NO_DELETE, 1);
    osg::ref_ptr<osg::Image> imageGreen = new osg::Image;
    imageGreen->setImage(1, 1, 1, GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, 
&bytes[4], osg::Image::NO_DELETE, 1);
    osg::ref_ptr<osg::Image> imageBlue = new osg::Image;
    imageBlue->setImage(1, 1, 1, GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, 
&bytes[8], osg::Image::NO_DELETE, 1);


    osg::ref_ptr<osg::Geode> geode = new osg::Geode();
    osg::ref_ptr<osg::Geometry> geom = new osg::Geometry();
    geode->addDrawable(geom.get());

    osg::ref_ptr<osg::Vec3Array> pVertices = new osg::Vec3Array;
    pVertices->push_back( osg::Vec3(0, 0, 0) );
    pVertices->push_back( osg::Vec3(0, 0, 1) );
    pVertices->push_back( osg::Vec3(1, 0, 1) );
    pVertices->push_back( osg::Vec3(1, 0, 0) );
    geom->setVertexArray(pVertices.get());

    osg::ref_ptr<osg::Vec2Array> pTexCoords = new osg::Vec2Array;
    pTexCoords->push_back( osg::Vec2(0, 0) );
    pTexCoords->push_back( osg::Vec2(0, 1) );
    pTexCoords->push_back( osg::Vec2(1, 1) );
    pTexCoords->push_back( osg::Vec2(1, 0) );
    geom->setTexCoordArray(0, pTexCoords.get());
    osg::ref_ptr<osg::DrawArrays> pDrawArrays = new osg::DrawArrays(GL_QUADS, 
0, 4);
    geom->addPrimitiveSet(pDrawArrays.get());

    osg::StateSet* stateset = new osg::StateSet();
    stateset->setMode(GL_LIGHTING, osg::StateAttribute::OFF);
    stateset->setTextureAttributeAndModes(0, texture1.get(), 
osg::StateAttribute::ON);
    geode->setStateSet( stateset );
    texture1->setImage(imageGreen.get());
    texture1->setWrap(osg::Texture::WRAP_S, osg::Texture::CLAMP_TO_EDGE);
    texture1->setWrap(osg::Texture::WRAP_T, osg::Texture::CLAMP_TO_EDGE);
    texture1->setResizeNonPowerOfTwoHint(false);
    texture1->setFilter( osg::Texture::MAG_FILTER, osg::Texture::NEAREST );
    texture1->setFilter( osg::Texture::MIN_FILTER, osg::Texture::NEAREST );


    osg::ref_ptr<osgViewer::Viewer> viewer1 = new osgViewer::Viewer;
    osg::ref_ptr<osgViewer::Viewer> viewer2 = new osgViewer::Viewer;
    viewer1->setUpViewInWindow(20, 50, 200, 200);
    viewer2->setUpViewInWindow(240, 300, 200, 200);
    viewer1->setThreadingModel(osgViewer::ViewerBase::SingleThreaded);
    viewer2->setThreadingModel(osgViewer::ViewerBase::SingleThreaded);

    viewer1->setSceneData( geode.get() );
    viewer2->setSceneData( geode.get() );

    viewer1->setCameraManipulator(new osgGA::TrackballManipulator());
    viewer2->setCameraManipulator(new osgGA::TrackballManipulator());

    int nFrame = 0;
    while( viewer1.get() || viewer2.get() )
    {
        if( viewer1.get() )
        {
            if( !viewer1->done() )
                viewer1->frame();
            else
                viewer1 = 0;
        }

        texture1->setImage(imageRGB.get());
        if( viewer2.get() )
        {
            if( !viewer2->done() )
                viewer2->frame();
            else
                viewer2 = 0;
        }

        ++nFrame;
    }

    return 0;
}

_______________________________________________
osg-users mailing list
[email protected]
http://lists.openscenegraph.org/listinfo.cgi/osg-users-openscenegraph.org

Reply via email to