点精灵实现:
1、创建点集合
osg::Node* PointSpriteImpl::MakeGalaxy(int nVertices) { osg::Geode* geode = new osg::Geode(); osg::Geometry* galaxy = new osg::Geometry(); osg::Vec3Array* vertices = new osg::Vec3Array(); osg::Vec4Array* clors = new osg::Vec4Array(); osg::Vec4 ini(1,1,0,1); osg::Vec4 fin(0,0,1,1); // 生成两个漩涡 for(int i = 0; i < nVertices/2; ++i) { // 等分圆的角度 2/nvertices 份 float val = (i*2/(float)nVertices * 2* osg::PI); float modx1 = rand() / (float)RAND_MAX*2; float mody1 = rand() / (float)RAND_MAX*2; float modx2 = rand() / (float)RAND_MAX*2; float mody2 = rand() / (float)RAND_MAX*2; float modz1 = ((rand() - RAND_MAX/2) / (float)(RAND_MAX))*3/(val+1); float modz2 = ((rand() - RAND_MAX/2) / (float)(RAND_MAX))*3/(val+1); vertices->push_back(osg::Vec3(cos(val)* val + modx1,sin(val) * val + mody1,modz1)); vertices->push_back(osg::Vec3(-cos(val)* val + modx2,-sin(val) * val + mody2,modz2)); clors->push_back(ini + (fin - ini)*(i*2/(float)nVertices)); clors->push_back(ini+ (fin - ini)*(i*2/(float)nVertices)); } galaxy->setVertexArray(vertices); galaxy->setColorArray(clors); galaxy->setColorBinding(osg::Geometry::BIND_PER_VERTEX); galaxy->addPrimitiveSet(new osg::DrawArrays(osg::PrimitiveSet::POINTS,0,nVertices)); geode->addDrawable(galaxy); return geode; }osg::Node* PointSpriteImpl::MakeGalaxy(int nVertices) { osg::Geode* geode = new osg::Geode(); osg::Geometry* galaxy = new osg::Geometry(); osg::Vec3Array* vertices = new osg::Vec3Array(); osg::Vec4Array* clors = new osg::Vec4Array(); osg::Vec4 ini(1,1,0,1); osg::Vec4 fin(0,0,1,1); // 生成两个漩涡 for(int i = 0; i < nVertices/2; ++i) { // 等分圆的角度 2/nvertices 份 float val = (i*2/(float)nVertices * 2* osg::PI); float modx1 = rand() / (float)RAND_MAX*2; float mody1 = rand() / (float)RAND_MAX*2; float modx2 = rand() / (float)RAND_MAX*2; float mody2 = rand() / (float)RAND_MAX*2; float modz1 = ((rand() - RAND_MAX/2) / (float)(RAND_MAX))*3/(val+1); float modz2 = ((rand() - RAND_MAX/2) / (float)(RAND_MAX))*3/(val+1); vertices->push_back(osg::Vec3(cos(val)* val + modx1,sin(val) * val + mody1,modz1)); vertices->push_back(osg::Vec3(-cos(val)* val + modx2,-sin(val) * val + mody2,modz2)); clors->push_back(ini + (fin - ini)*(i*2/(float)nVertices)); clors->push_back(ini+ (fin - ini)*(i*2/(float)nVertices)); } galaxy->setVertexArray(vertices); galaxy->setColorArray(clors); galaxy->setColorBinding(osg::Geometry::BIND_PER_VERTEX); galaxy->addPrimitiveSet(new osg::DrawArrays(osg::PrimitiveSet::POINTS,0,nVertices)); geode->addDrawable(galaxy); return geode; }
2、设置stateset属性
osg::StateSet* PointSpriteImpl::MakeStateSet(int nSize) { osg::StateSet* stateSet = new osg::StateSet(); // set cool blending stateSet->setMode(GL_BLEND,osg::StateAttribute::ON); osg::BlendFunc* fn = new osg::BlendFunc(); fn->setFunction(osg::BlendFunc::SRC_ALPHA,osg::BlendFunc::DST_ALPHA); stateSet->setAttributeAndModes(fn,osg::StateAttribute::ON); // setup point sprit osg::PointSprite* pointsprite = new osg::PointSprite(); stateSet->setTextureAttributeAndModes(0,pointsprite,osg::StateAttribute::ON); // give some size to the points osg::Point* point = new osg::Point(); point->setSize(nSize); stateSet->setAttribute(point); // Disable depth test to avoid sort problems and Lighting stateSet->setMode(GL_DEPTH_TEST,osg::StateAttribute::OFF); stateSet->setMode(GL_LIGHTING,osg::StateAttribute::OFF); /// The texture for the sprites osg::Texture2D* tex = new osg::Texture2D(); tex->setImage(osgDB::readImageFile("Images/particle.rgb")); stateSet->setTextureAttributeAndModes(0,tex,osg::StateAttribute::ON); return stateSet; }
3、绘制结果:
(1) 未设置stateset
(2)设置stateset后:
4、总结:
5、扩展: