void OBJWriterNodeVisitor::processGeometry(osg::Geometry* geo, osg::Matrix& m) { _fout << std::endl; _fout << "o " << getUniqueName( geo->getName().empty() ? geo->className() : geo->getName() ) << std::endl; if (geo->containsDeprecatedData()) geo->fixDeprecatedData(); processStateSet(_currentStateSet.get()); processArray("v", geo->getVertexArray(), m, false); processArray("vn", geo->getNormalArray(), m, true); processArray("vt", geo->getTexCoordArray(0)); // we support only tex-unit 0 unsigned int normalIndex = 0; for(unsigned int i = 0; i < geo->getNumPrimitiveSets(); ++i) { osg::PrimitiveSet* ps = geo->getPrimitiveSet(i); ObjPrimitiveIndexWriter pif(_fout, geo, normalIndex, _lastVertexIndex, _lastNormalIndex, _lastTexIndex); ps->accept(pif); if(geo->getNormalArray() && geo->getNormalArray()->getBinding() == osg::Array::BIND_PER_PRIMITIVE_SET) ++normalIndex; } if (geo->getVertexArray()) _lastVertexIndex += geo->getVertexArray()->getNumElements(); if (geo->getNormalArray()) _lastNormalIndex += geo->getNormalArray()->getNumElements(); if(geo->getTexCoordArray(0)) _lastTexIndex += geo->getTexCoordArray(0)->getNumElements(); }
void WriterNodeVisitor::createListTriangle(osg::Geometry * geo, ListTriangle & listTriangles, bool & texcoords, unsigned int & drawable_n) { const osg::Array * basevecs = geo->getVertexArray(); if (!basevecs || basevecs->getNumElements()==0) return; // Texture coords const osg::Array * basetexvecs = geo->getNumTexCoordArrays()>=1 ? geo->getTexCoordArray(0) : NULL; if (basetexvecs) { unsigned int nb = basetexvecs->getNumElements(); if (nb != geo->getVertexArray()->getNumElements()) { OSG_NOTIFY(osg::FATAL) << "There are more/less texture coords than vertices (corrupted geometry)" << std::endl; _succeeded = false; return; } texcoords = true; } int material = processStateSet(_currentStateSet.get()); for(unsigned int i = 0; i < geo->getNumPrimitiveSets(); ++i) //Fill the Triangle List { osg::PrimitiveSet* ps = geo->getPrimitiveSet(i); PrimitiveIndexWriter pif(geo, listTriangles, drawable_n, material); ps->accept(pif); } }
void DXFWriterNodeVisitor::processGeometry(osg::Geometry* geo, osg::Matrix& m) { // We only want to create a new layer for geometry with something to draw if (geo->getVertexArray() && geo->getVertexArray()->getNumElements() ) { if ( _firstPass ) { // Must have unique layer names _layer._name = getLayerName( geo->getName().empty() ? geo->getParent(0)->getName() : geo->getName() ); OSG_DEBUG << "adding Layer " << _layer._name << std::endl; // if single colour include in header osg::Array::Binding colorBinding = osg::getBinding(geo->getColorArray()); if ( osg::Array::BIND_OVERALL == colorBinding ) { _layer._color = _acadColor.findColor(getNodeRGB(geo)); // per layer color } else if ( osg::Array::BIND_OFF== colorBinding ) { _layer._color = 0xff; // use white - or can we easily lookup in texture? } else { _layer._color = 0; // per point color } _layers.push_back(_layer); } else { _layer = _layers[_count++]; OSG_DEBUG << "writing Layer " << _layer._name << std::endl; processStateSet(_currentStateSet.get()); if ( geo->getNumPrimitiveSets() ) { for(unsigned int i = 0; i < geo->getNumPrimitiveSets(); ++i) { osg::PrimitiveSet* ps = geo->getPrimitiveSet(i); DxfPrimitiveIndexWriter pif(_fout, geo,_layer,_acadColor,m,_writeTriangleAs3DFace); ps->accept(pif); } } else { // Is array visitor necessary for only dealing with vertex arrays? //processArray(geo->getVertexArray(), _layer,m); if ( geo->getVertexArray() ) { osg::Vec3Array* data=static_cast<osg::Vec3Array*>(geo->getVertexArray()); for (unsigned int ii=0;ii<data->getNumElements();ii++) { osg::Vec3 point = data->at(ii) * m; _fout << "0 \nVERTEX\n 8\n"<<_layer._name<<"\n"; if ( _layer._color ) { _fout << "62\n"<<_layer._color<<"\n"; } else { _fout << "62\n"<<_acadColor.findColor(getNodeRGB(geo,ii))<<"\n"; } _fout<<" 10\n"<<point.x()<<"\n 20\n"<<point.y()<<"\n 30\n"<<point.z()<<"\n"; } } } } } }
void CountStateSets::apply( osg::Node& node ) { if( !processStateSet( node.getStateSet() ) && _removeEmptyStateSets ) { node.setStateSet( NULL ); _removedStateSets++; } traverse( node ); }
void CountStateSets::apply( osg::Geode& node ) { if( !processStateSet( node.getStateSet() ) && _removeEmptyStateSets ) { node.setStateSet( NULL ); _removedStateSets++; } unsigned int idx; for( idx=0; idx<node.getNumDrawables(); idx++ ) { osg::Drawable* draw = node.getDrawable( idx ); if( !processStateSet( draw->getStateSet() ) && _removeEmptyStateSets ) { draw->setStateSet( NULL ); _removedStateSets++; } } traverse( node ); }
void Camera::renderGraph(const Node *graph) { if (!graph || dynamic_cast<const osg::Camera*>(graph)) return; const osg::BoundingSphered &bound = computeBoundsOf(graph); const double r = bound.radius(); const Vec3d view_center = bound.center() * qMatrix.back(); if (-view_center.z() + r < znear || -view_center.z() - r > zfar) return; bool bPopMatrix = false; const osg::StateSet *stateset = graph->getStateSet(); if (stateset) { qStateSet.push_back(qStateSet.back()); processStateSet(stateset, qStateSet.back()); } const PositionAttitudeTransform *ptrans = dynamic_cast<const PositionAttitudeTransform*>(graph); if (ptrans) { const Matrixd mat = Matrixd::translate(-ptrans->getPivotPoint()) * Matrixd::rotate(ptrans->getAttitude()) * Matrixd::scale(ptrans->getScale()) * Matrixd::translate(ptrans->getPosition()); pushMatrix(mat); bPopMatrix = true; } const MatrixTransform *mtrans = dynamic_cast<const MatrixTransform*>(graph); if (mtrans) { pushMatrix(mtrans->getMatrix()); bPopMatrix = true; } const Switch* sgroup = dynamic_cast<const Switch*>(graph); if (sgroup) { for(unsigned int i = 0, nb = sgroup->getNumChildren() ; i < nb ; ++i) if (sgroup->getValue(i)) renderGraph(sgroup->getChild(i)); } else { const Group* group = dynamic_cast<const Group*>(graph); if (group) { for(unsigned int i = 0, nb = group->getNumChildren() ; i < nb ; ++i) renderGraph(group->getChild(i)); } } const Geode *geode = dynamic_cast<const Geode*>(graph); if (geode) { glEnableClientState(GL_VERTEX_ARRAY); CHECK_GL(); bool bParentStateApplied = false; for(unsigned int i = 0, nb = geode->getNumDrawables() ; i < nb ; ++i) { const Geometry * const geom = geode->getDrawable(i)->asGeometry(); if (!geom) { LOG_ERROR() << "[Camera] unsupported drawable : " << geode->getDrawable(i)->className() << std::endl; continue; } const Array * const vtx = geom->getVertexArray(); const Array * const normals = geom->getNormalArray(); const Array * const tcoord = geom->getTexCoordArray(0); if (!vtx) { LOG_ERROR() << "[Camera] no vertex array in Geometry object" << std::endl; continue; } StateSet *local_state = NULL; char tmp[sizeof(StateSet)]; //! Avoid dynamic allocation const osg::StateSet *geom_state = geom->getStateSet(); if (geom_state) { local_state = new(tmp) StateSet(qStateSet.back()); processStateSet(geom_state, *local_state); } if (local_state) { local_state->apply(); bParentStateApplied = false; } else if (!bParentStateApplied) { bParentStateApplied = true; qStateSet.back().apply(); } if (bDoublePrecisionMode) { if (processed_vertex_array.size() < vtx->getNumElements()) processed_vertex_array.resize(vtx->getNumElements()); const void * const ptr = vtx->getDataPointer(); const osg::Matrixd &mat = qMatrix.back() * projectionMatrix; switch(vtx->getDataType()) { case GL_FLOAT: if (vtx->getDataSize() == 4) { const size_t nb = vtx->getNumElements(); for(size_t i = 0 ; i < nb ; ++i) { const Vec4d &p = Vec4d(((const Vec4f*)ptr)[i]) * mat; processed_vertex_array[i] = p / p.w(); } } else if (vtx->getDataSize() == 3) { const size_t nb = vtx->getNumElements(); for(size_t i = 0 ; i < nb ; ++i) { const Vec4d &p = Vec4d(((const Vec3f*)ptr)[i], 1.0) * mat; processed_vertex_array[i] = p / p.w(); } } break; } glEnableClientState(GL_COLOR_ARRAY); CHECK_GL(); if (pContext->hasVBOSupport()) { glBindBuffer(GL_ARRAY_BUFFER, 0); CHECK_GL(); } glColorPointer(4, GL_FLOAT, 0, &(processed_vertex_array.front())); CHECK_GL(); } if (pContext->hasVBOSupport()) { glBindBuffer(GL_ARRAY_BUFFER, pContext->getDataVBOID(vtx->getDataPointer(), vtx->getTotalDataSize())); CHECK_GL(); glVertexPointer(vtx->getDataSize(), vtx->getDataType(), 0, 0); CHECK_GL(); if (normals) { glEnableClientState(GL_NORMAL_ARRAY); CHECK_GL(); glBindBuffer(GL_ARRAY_BUFFER, pContext->getDataVBOID(normals->getDataPointer(), normals->getTotalDataSize())); CHECK_GL(); glNormalPointer(normals->getDataType(), 0, 0); CHECK_GL(); } else { glDisableClientState(GL_NORMAL_ARRAY); CHECK_GL(); } if (tcoord) { glEnableClientState(GL_TEXTURE_COORD_ARRAY); CHECK_GL(); glBindBuffer(GL_ARRAY_BUFFER, pContext->getDataVBOID(tcoord->getDataPointer(), tcoord->getTotalDataSize())); CHECK_GL(); glTexCoordPointer(tcoord->getDataSize(), tcoord->getDataType(), 0, 0); CHECK_GL(); } else { glDisableClientState(GL_TEXTURE_COORD_ARRAY); CHECK_GL(); } const size_t nb_prim_set = geom->getNumPrimitiveSets(); for(size_t j = 0 ; j < nb_prim_set ; ++j) { const PrimitiveSet * const pset = geom->getPrimitiveSet(j); const DrawElements * const elts = pset->getDrawElements(); switch(pset->getType()) { case DrawElements::PrimitiveType: break; case DrawElements::DrawArraysPrimitiveType: glDrawArrays(pset->getMode(), pset->index(0), pset->getNumIndices()); CHECK_GL(); break; case DrawElements::DrawArrayLengthsPrimitiveType: break; case DrawElements::DrawElementsUBytePrimitiveType: glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, pContext->getIndexVBOID(elts->getDataPointer(), elts->getTotalDataSize())); CHECK_GL(); glDrawRangeElements(elts->getMode(), 0, vtx->getNumElements() - 1, elts->getNumIndices(), GL_UNSIGNED_BYTE, 0); CHECK_GL(); break; case DrawElements::DrawElementsUShortPrimitiveType: glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, pContext->getIndexVBOID(elts->getDataPointer(), elts->getTotalDataSize())); CHECK_GL(); glDrawRangeElements(elts->getMode(), 0, vtx->getNumElements() - 1, elts->getNumIndices(), GL_UNSIGNED_SHORT, 0); CHECK_GL(); break; case DrawElements::DrawElementsUIntPrimitiveType: glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, pContext->getIndexVBOID(elts->getDataPointer(), elts->getTotalDataSize())); CHECK_GL(); glDrawRangeElements(elts->getMode(), 0, vtx->getNumElements() - 1, elts->getNumIndices(), GL_UNSIGNED_INT, 0); CHECK_GL(); break; } } } else { glVertexPointer(vtx->getDataSize(), vtx->getDataType(), 0, vtx->getDataPointer()); CHECK_GL(); if (normals) { glEnableClientState(GL_NORMAL_ARRAY); CHECK_GL(); glNormalPointer(normals->getDataType(), 0, normals->getDataPointer()); CHECK_GL(); } else { glDisableClientState(GL_NORMAL_ARRAY); CHECK_GL(); } if (tcoord) { glEnableClientState(GL_TEXTURE_COORD_ARRAY); CHECK_GL(); glTexCoordPointer(tcoord->getDataSize(), tcoord->getDataType(), 0, tcoord->getDataPointer()); CHECK_GL(); } else { glDisableClientState(GL_TEXTURE_COORD_ARRAY); CHECK_GL(); } const size_t nb_prim_set = geom->getNumPrimitiveSets(); for(size_t j = 0 ; j < nb_prim_set ; ++j) { const PrimitiveSet * const pset = geom->getPrimitiveSet(j); const DrawElements * const elts = pset->getDrawElements(); switch(pset->getType()) { case DrawElements::PrimitiveType: break; case DrawElements::DrawArraysPrimitiveType: glDrawArrays(pset->getMode(), pset->index(0), pset->getNumIndices()); CHECK_GL(); break; case DrawElements::DrawArrayLengthsPrimitiveType: break; case DrawElements::DrawElementsUBytePrimitiveType: glDrawRangeElements(elts->getMode(), 0, vtx->getNumElements() - 1, elts->getNumIndices(), GL_UNSIGNED_BYTE, elts->getDataPointer()); CHECK_GL(); break; case DrawElements::DrawElementsUShortPrimitiveType: glDrawRangeElements(elts->getMode(), 0, vtx->getNumElements() - 1, elts->getNumIndices(), GL_UNSIGNED_SHORT, elts->getDataPointer()); CHECK_GL(); break; case DrawElements::DrawElementsUIntPrimitiveType: glDrawRangeElements(elts->getMode(), 0, vtx->getNumElements() - 1, elts->getNumIndices(), GL_UNSIGNED_INT, elts->getDataPointer()); CHECK_GL(); break; } } } if (local_state) local_state->~StateSet(); } } if (bPopMatrix) popMatrix(); if (stateset) qStateSet.pop_back(); }