diff --git a/src/osgText/Font.cpp b/src/osgText/Font.cpp index d2585c5bd..6eca7196d 100644 --- a/src/osgText/Font.cpp +++ b/src/osgText/Font.cpp @@ -34,6 +34,13 @@ using namespace std; static osg::ApplicationUsageProxy Font_e0(osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE,"OSG_TEXT_INCREMENTAL_SUBLOADING ","ON | OFF"); +#if (!defined(OSG_GLES2_AVAILABLE) && !defined(OSG_GLES3_AVAILABLE)) + #define GLSL_VERSION_STR "330 core" + #define GLYPH_CMP "r" +#else + #define GLSL_VERSION_STR "300 es" + #define GLYPH_CMP "a" +#endif osg::ref_ptr& Font::getDefaultFont() { @@ -240,7 +247,109 @@ Font::Font(FontImplementation* implementation): _texenv = new osg::TexEnv; _stateset = new osg::StateSet; + _stateset->setRenderingHint(osg::StateSet::TRANSPARENT_BIN); + _stateset->setMode(GL_LIGHTING, osg::StateAttribute::OFF); + _stateset->setMode(GL_BLEND, osg::StateAttribute::ON); + +#if defined(OSG_GL_FIXED_FUNCTION_AVAILABLE) + + OSG_INFO<<"Font::Font() Fixed function pipeline"<setTextureMode(0, GL_TEXTURE_2D, osg::StateAttribute::ON); +#endif + +#if defined(OSG_GL3_AVAILABLE) || defined(OSG_GLES3_AVAILABLE) + { + + OSG_INFO<<"Font::Font() Setting up GL3 compatible shaders"<=0.0) color = vertexColor * vec4(1.0, 1.0, 1.0, texture(glyphTexture, texCoord)." GLYPH_CMP ");\n" + " else color = vertexColor;\n" + "}\n" + }; + + osg::ref_ptr program = new osg::Program; + program->addShader(new osg::Shader(osg::Shader::VERTEX, gl3_TextVertexShader)); + program->addShader(new osg::Shader(osg::Shader::FRAGMENT, gl3_TextFragmentShader)); + _stateset->setAttributeAndModes(program.get()); + _stateset->addUniform(new osg::Uniform("glyphTexture", 0)); + + } +#elif defined(OSG_GL2_AVAILABLE) || defined(OSG_GLES2_AVAILABLE) + { + OSG_INFO<<"Font::Font() Setting up GL2 compatible shaders"<=0.0) gl_FragColor = vertexColor * vec4(1.0, 1.0, 1.0, texture2D(glyphTexture, texCoord).a);\n" + " else gl_FragColor = vertexColor;\n" + "}\n" + }; + + osg::ref_ptr program = new osg::Program; + program->addShader(new osg::Shader(osg::Shader::VERTEX, gl2_TextVertexShader)); + program->addShader(new osg::Shader(osg::Shader::FRAGMENT, gl2_TextFragmentShader)); + _stateset->setAttributeAndModes(program.get()); + _stateset->addUniform(new osg::Uniform("glyphTexture", 0)); + + } +#endif char *ptr; if( (ptr = getenv("OSG_MAX_TEXTURE_SIZE")) != 0) diff --git a/src/osgViewer/StatsHandler.cpp b/src/osgViewer/StatsHandler.cpp index d1e11d4e1..b9ee81f23 100644 --- a/src/osgViewer/StatsHandler.cpp +++ b/src/osgViewer/StatsHandler.cpp @@ -28,6 +28,12 @@ namespace osgViewer { +#if (!defined(OSG_GLES2_AVAILABLE) && !defined(OSG_GLES3_AVAILABLE)) + #define GLSL_VERSION_STR "330 core" +#else + #define GLSL_VERSION_STR "300 es" +#endif + StatsHandler::StatsHandler(): _keyEventTogglesOnScreenStats('s'), @@ -49,10 +55,98 @@ StatsHandler::StatsHandler(): _characterSize(20.0f), _lineHeight(1.5f) { + OSG_INFO<<"StatsHandler::StatsHandler()"<getOrCreateStateSet()->setGlobalDefaults(); _camera->setRenderer(new Renderer(_camera.get())); _camera->setProjectionResizePolicy(osg::Camera::FIXED); + +#if defined(OSG_GL3_AVAILABLE) || defined(OSG_GLES3_AVAILABLE) + { + OSG_NOTICE<<"StatsHandler::StatsHandler() Setting up GL3 compatible shaders"< program = new osg::Program; + program->addShader(new osg::Shader(osg::Shader::VERTEX, gl3_StatsVertexShader)); + program->addShader(new osg::Shader(osg::Shader::FRAGMENT, gl3_StatsFragmentShader)); + _camera->getOrCreateStateSet()->setAttributeAndModes(program.get()); + } +#elif defined(OSG_GL2_AVAILABLE) || defined(OSG_GLES2_AVAILABLE) + { + + OSG_NOTICE<<"StatsHandler::StatsHandler() Setting up GL2 compatible shaders"< program = new osg::Program; + program->addShader(new osg::Shader(osg::Shader::VERTEX, gl2_StatsVertexShader)); + program->addShader(new osg::Shader(osg::Shader::FRAGMENT, gl2_StatsFragmentShader)); + _camera->getOrCreateStateSet()->setAttributeAndModes(program.get()); + } +#else + { + OSG_INFO<<"StatsHandler::StatsHandler() Fixed pipeline"<getCameras(cameras); } bool StatsHandler::handle(const osgGA::GUIEventAdapter& ea, osgGA::GUIActionAdapter& aa) @@ -77,7 +171,7 @@ bool StatsHandler::handle(const osgGA::GUIEventAdapter& ea, osgGA::GUIActionAdap { if (ea.getKey()==_keyEventTogglesOnScreenStats) { - if (viewer->getViewerStats()) + if (viewer && viewer->getViewerStats()) { if (!_initialized) { @@ -90,7 +184,7 @@ bool StatsHandler::handle(const osgGA::GUIEventAdapter& ea, osgGA::GUIActionAdap if (_statsType==LAST) _statsType = NO_STATS; osgViewer::ViewerBase::Cameras cameras; - viewer->getCameras(cameras); + collectWhichCamerasToRenderStatsFor(viewer, cameras); switch(_statsType) { @@ -195,7 +289,7 @@ bool StatsHandler::handle(const osgGA::GUIEventAdapter& ea, osgGA::GUIActionAdap } if (ea.getKey()==_keyEventPrintsOutStats) { - if (viewer->getViewerStats()) + if (viewer && viewer->getViewerStats()) { OSG_NOTICE< StatsList; @@ -235,6 +329,7 @@ bool StatsHandler::handle(const osgGA::GUIEventAdapter& ea, osgGA::GUIActionAdap } return true; } + break; } case(osgGA::GUIEventAdapter::RESIZE): setWindowSize(ea.getWindowWidth(), ea.getWindowHeight()); @@ -654,6 +749,7 @@ struct BlockDrawCallback : public virtual osg::Drawable::DrawCallback unsigned int vi = 0; double beginValue, endValue; + double minWidth = .0002; for(int i = startFrame; i <= endFrame; ++i) { if (_stats->getAttribute( i, _beginName, beginValue) && @@ -662,10 +758,15 @@ struct BlockDrawCallback : public virtual osg::Drawable::DrawCallback (*vertices)[vi++].x() = _xPos + (beginValue - referenceTime) * _statsHandler->getBlockMultiplier(); (*vertices)[vi++].x() = _xPos + (beginValue - referenceTime) * _statsHandler->getBlockMultiplier(); (*vertices)[vi++].x() = _xPos + (endValue - referenceTime) * _statsHandler->getBlockMultiplier(); + + + if (endValue - beginValue < minWidth) endValue = beginValue + minWidth; (*vertices)[vi++].x() = _xPos + (endValue - referenceTime) * _statsHandler->getBlockMultiplier(); } } + vertices->dirty(); + osg::DrawArrays* drawArrays = static_cast(geom->getPrimitiveSet(0)); drawArrays->setCount(vi); @@ -744,33 +845,41 @@ protected: const osg::Vec4& color, float max, const std::string& nameBegin, const std::string& nameEnd = "") { setUseDisplayList(false); + setDataVariance(osg::Object::DYNAMIC); - setVertexArray(new osg::Vec3Array); + osg::ref_ptr vbo = new osg::VertexBufferObject; + vbo->setUsage(GL_DYNAMIC_DRAW); + vbo->getProfile()._size = (width)*12; + + osg::ref_ptr vertices = new osg::Vec3Array; + vertices->setBufferObject(vbo.get()); + vertices->reserve(width); + + setVertexArray(vertices.get()); osg::Vec4Array* colors = new osg::Vec4Array; colors->push_back(color); setColorArray(colors, osg::Array::BIND_OVERALL); - setDrawCallback(new GraphUpdateCallback(pos, width, height, viewerStats, stats, max, nameBegin, nameEnd)); + addPrimitiveSet(new osg::DrawArrays(GL_LINE_STRIP, 0, 0)); + + setDrawCallback(new GraphUpdateCallback(this, pos, width, height, viewerStats, stats, max, nameBegin, nameEnd)); } }; struct GraphUpdateCallback : public osg::Drawable::DrawCallback { - GraphUpdateCallback(const osg::Vec3& pos, float width, float height, osg::Stats* viewerStats, osg::Stats* stats, + GraphUpdateCallback(osg::Geometry* geometry, const osg::Vec3& pos, float width, float height, osg::Stats* viewerStats, osg::Stats* stats, float max, const std::string& nameBegin, const std::string& nameEnd = "") : _pos(pos), _width((unsigned int)width), _height((unsigned int)height), _curX(0), _viewerStats(viewerStats), _stats(stats), _max(max), _nameBegin(nameBegin), _nameEnd(nameEnd) { + _vertices = dynamic_cast(geometry->getVertexArray()); + _drawArrays = dynamic_cast(geometry->getPrimitiveSet(0)); } virtual void drawImplementation(osg::RenderInfo& renderInfo,const osg::Drawable* drawable) const { - osg::Geometry* geometry = const_cast(drawable->asGeometry()); - if (!geometry) return; - osg::Vec3Array* vertices = dynamic_cast(geometry->getVertexArray()); - if (!vertices) return; - unsigned int frameNumber = renderInfo.getState()->getFrameStamp()->getFrameNumber(); // Get stats @@ -798,24 +907,18 @@ protected: // Add new vertex for this frame. value = osg::clampTo(value, 0.0, double(_max)); - vertices->push_back(osg::Vec3(float(_curX), float(_height) / _max * value, 0)); + _vertices->push_back(osg::Vec3(float(_curX), float(_height) / _max * value, 0)); // One vertex per pixel in X. - int excedent = vertices->size() - _width; + int excedent = _vertices->size() - _width; if (excedent > 0) { - vertices->erase(vertices->begin(), vertices->begin() + excedent); + _vertices->erase(_vertices->begin(), _vertices->begin() + excedent); } - // Create primitive set if none exists. - if (geometry->getNumPrimitiveSets() == 0) - geometry->addPrimitiveSet(new osg::DrawArrays(GL_LINE_STRIP, 0, 0)); - // Update primitive set. - osg::DrawArrays* drawArrays = dynamic_cast(geometry->getPrimitiveSet(0)); - if (!drawArrays) return; - drawArrays->setFirst(0); - drawArrays->setCount(vertices->size()); + _drawArrays->setFirst(0); + _drawArrays->setCount(_vertices->size()); // Make the graph scroll when there is enough data. // Note: We check the frame number so that even if we have @@ -826,24 +929,25 @@ protected: { // We know the exact layout of this part of the scene // graph, so this is OK... - osg::MatrixTransform* transform = - geometry->getParent(0)->getParent(0)->asTransform()->asMatrixTransform(); + osg::MatrixTransform* transform = const_cast(drawable->getParent(0)->getParent(0)->asTransform()->asMatrixTransform()); if (transform) { //osg::Matrix matrix = transform->getMatrix(); //matrix.setTrans(-(*vertices)[0].x(), matrix.getTrans().y(), matrix.getTrans().z()); - transform->setMatrix(osg::Matrix::translate(_pos + osg::Vec3(-(*vertices)[0].x(), 0, 0))); + transform->setMatrix(osg::Matrix::translate(_pos + osg::Vec3(-(*_vertices)[0].x(), 0, 0))); } } + _vertices->dirty(); + _curX++; GraphUpdateCallback::_frameNumber = frameNumber; - geometry->dirtyBound(); - drawable->drawImplementation(renderInfo); } + osg::ref_ptr _vertices; + osg::ref_ptr _drawArrays; const osg::Vec3 _pos; const unsigned int _width; const unsigned int _height; @@ -865,24 +969,34 @@ osg::Geometry* StatsHandler::createGeometry(const osg::Vec3& pos, float height, osg::Geometry* geometry = new osg::Geometry; geometry->setUseDisplayList(false); + geometry->setDataVariance(osg::Object::DYNAMIC); osg::Vec3Array* vertices = new osg::Vec3Array; geometry->setVertexArray(vertices); vertices->reserve(numBlocks*4); + osg::DrawElementsUShort* primitives = new osg::DrawElementsUShort(GL_TRIANGLES); for(unsigned int i=0; isize(); vertices->push_back(pos+osg::Vec3(i*20, height, 0.0)); vertices->push_back(pos+osg::Vec3(i*20, 0.0, 0.0)); vertices->push_back(pos+osg::Vec3(i*20+10.0, 0.0, 0.0)); vertices->push_back(pos+osg::Vec3(i*20+10.0, height, 0.0)); + + primitives->push_back(vi); + primitives->push_back(vi+1); + primitives->push_back(vi+2); + primitives->push_back(vi); + primitives->push_back(vi+2); + primitives->push_back(vi+3); } osg::Vec4Array* colours = new osg::Vec4Array; colours->push_back(colour); geometry->setColorArray(colours, osg::Array::BIND_OVERALL); - geometry->addPrimitiveSet(new osg::DrawArrays(GL_QUADS, 0, numBlocks*4)); + geometry->addPrimitiveSet(primitives); return geometry; } @@ -924,6 +1038,8 @@ struct FrameMarkerDrawCallback : public virtual osg::Drawable::DrawCallback } } + vertices->dirty(); + drawable->drawImplementation(renderInfo); } @@ -1020,6 +1136,7 @@ osg::Geometry* StatsHandler::createFrameMarkers(const osg::Vec3& pos, float heig osg::Geometry* geometry = new osg::Geometry; geometry->setUseDisplayList(false); + geometry->setDataVariance(osg::Object::DYNAMIC); osg::Vec3Array* vertices = new osg::Vec3Array; geometry->setVertexArray(vertices); @@ -1045,6 +1162,7 @@ osg::Geometry* StatsHandler::createTick(const osg::Vec3& pos, float height, cons osg::Geometry* geometry = new osg::Geometry; geometry->setUseDisplayList(false); + geometry->setDataVariance(osg::Object::DYNAMIC); osg::Vec3Array* vertices = new osg::Vec3Array; geometry->setVertexArray(vertices); @@ -1082,7 +1200,7 @@ void StatsHandler::setUpScene(osgViewer::ViewerBase* viewer) // collect all the relevant cameras ViewerBase::Cameras validCameras; - viewer->getCameras(validCameras); + collectWhichCamerasToRenderStatsFor(viewer, validCameras); ViewerBase::Cameras cameras; for(ViewerBase::Cameras::iterator itr = validCameras.begin(); @@ -1146,8 +1264,14 @@ void StatsHandler::setUpScene(osgViewer::ViewerBase* viewer) frameRateLabel->setFont(_font); frameRateLabel->setCharacterSize(_characterSize); frameRateLabel->setPosition(pos); +#ifdef _DEBUG + osg::Vec4 colorDFR(1.0f, 0.0f, 0.0f, 1.0f); + frameRateLabel->setColor(colorDFR); + frameRateLabel->setText("DEBUG Frame Rate: "); +#else + frameRateLabel->setColor(colorFR); frameRateLabel->setText("Frame Rate: "); - +#endif pos.x() = frameRateLabel->getBoundingBox().xMax(); osg::ref_ptr frameRateValue = new osgText::Text; @@ -1158,6 +1282,7 @@ void StatsHandler::setUpScene(osgViewer::ViewerBase* viewer) frameRateValue->setCharacterSize(_characterSize); frameRateValue->setPosition(pos); frameRateValue->setText("0.0"); + frameRateValue->setDataVariance(osg::Object::DYNAMIC); frameRateValue->setDrawCallback(new AveragedValueTextDrawCallback(viewer->getViewerStats(),"Frame rate",-1, true, 1.0)); @@ -1356,6 +1481,7 @@ void StatsHandler::setUpScene(osgViewer::ViewerBase* viewer) averageValue->setCharacterSize(_characterSize); averageValue->setPosition(pos); averageValue->setText("1000"); + averageValue->setDataVariance(osg::Object::DYNAMIC); pos.x() = averageValue->getBoundingBox().xMax() + 2.0f*_characterSize; @@ -1379,6 +1505,7 @@ void StatsHandler::setUpScene(osgViewer::ViewerBase* viewer) minValue->setCharacterSize(_characterSize); minValue->setPosition(pos); minValue->setText("1000"); + minValue->setDataVariance(osg::Object::DYNAMIC); pos.x() = minValue->getBoundingBox().xMax() + 2.0f*_characterSize; @@ -1401,6 +1528,8 @@ void StatsHandler::setUpScene(osgViewer::ViewerBase* viewer) maxValue->setCharacterSize(_characterSize); maxValue->setPosition(pos); maxValue->setText("1000"); + maxValue->setDataVariance(osg::Object::DYNAMIC); + pos.x() = maxValue->getBoundingBox().xMax(); @@ -1423,6 +1552,8 @@ void StatsHandler::setUpScene(osgViewer::ViewerBase* viewer) requestList->setCharacterSize(_characterSize); requestList->setPosition(pos); requestList->setText("0"); + requestList->setDataVariance(osg::Object::DYNAMIC); + pos.x() = requestList->getBoundingBox().xMax() + 2.0f*_characterSize;; @@ -1445,6 +1576,8 @@ void StatsHandler::setUpScene(osgViewer::ViewerBase* viewer) compileList->setCharacterSize(_characterSize); compileList->setPosition(pos); compileList->setText("0"); + compileList->setDataVariance(osg::Object::DYNAMIC); + pos.x() = maxLabel->getBoundingBox().xMax(); @@ -1529,6 +1662,7 @@ void StatsHandler::setUpScene(osgViewer::ViewerBase* viewer) camStatsText->setCharacterSize(_characterSize); camStatsText->setPosition(pos); camStatsText->setText(""); + camStatsText->setDataVariance(osg::Object::DYNAMIC); camStatsText->setDrawCallback(new CameraSceneStatsTextDrawCallback(*citr, cameraCounter)); // Move camera block to the right @@ -1602,6 +1736,7 @@ void StatsHandler::setUpScene(osgViewer::ViewerBase* viewer) text->setFont(_font); text->setCharacterSize(_characterSize); text->setPosition(pos); + text->setDataVariance(osg::Object::DYNAMIC); text->setDrawCallback(new ViewSceneStatsTextDrawCallback(*it, viewCounter)); pos.x() += 10 * _characterSize + 2 * backgroundMargin + backgroundSpacing; @@ -1635,6 +1770,7 @@ void StatsHandler::createTimeStatsLine(const std::string& lineLabel, value->setCharacterSize(_characterSize); value->setPosition(pos); value->setText("0.0"); + value->setDataVariance(osg::Object::DYNAMIC); if (!timeTakenName.empty()) {