Draw triangles with ogre
Mature image engines often encapsulate underlying operations. Users may be able to easily add complex models to the game, but cannot figure out a triangle. This article explains how to draw triangles in ogre. If you have some basic DirectX or OpenGL knowledge, it will be easier to understand.
Ogre uses a tree structure to organize scenarios. All objects to be traversed need to be mounted under the tree node. Such entities with the hook capability must inherit from the movableobject class; if an object wants to be rendered, it must inherit the renderable class. As a result, our triangle class is as follows:
class Triangle : public Ogre::MovableObject, public Ogre::Renderable
The next step is to fill in more than 10 pure virtual methods of the two parent classes. Here we will only pick out the most important ones for illustration.
1. The _ updaterenderqueue () function from movableobject. It is called when the scenario traverses the current object. You can choose to add the object to be rendered to the rendering queue at this time, because our triangle itself inherits from renderable, so we add ourselves to the queue:
void Triangle::_updateRenderQueue(Ogre::RenderQueue* queue){queue->addRenderable(this);}
2. The following is the getrenderoperation () function from renderable. It is called when the rendering queue later traverses every waiting unit. You need to select this time point to render the relevant data (vertex data, organization mode, number, index, etc) it is submitted to the engine in the form of renderoperation data structure. It can be seen that renderoperation determines what you will render. In fact, the core of this article is the customization of renderoperation.
When initializing a triangle, we construct renderoperation data:
Void triangle: _ createbuffers () {// float vertices [3] [3] = {-1.0f, 1.0f, 0.0f, // 0 position1.0f, 1.0f, 0.0f, // 1 position0.0f,-1.0f, 0.0f, // 2 position}; // vertex color ogre: rendersystem * rs = ogre: Root :: getsingleton (). getrendersystem (); ogre: rgba colours [3]; RS-> convertcolourvalue (Ogre: colourvalue (1.0f, 0.0f, 0.0f), & colours [0]); // 0 colourrs-> convertcolourvalue (Ogre: colourvalue (0.0f, 1.0f, 0.0f), & colours [1]); // 1 colourrs-> convertcolourvalue (Ogre :: colourvalue (0.0f, 0.0f, 1.0f), & colours [2]); // 2 color // vertex index ogre: ushort faces [3] = {0, 1, 2, // 0 face}; // create a vertexdata object to manage vertex data. mvertexdata = new ogre: vertexdata (); mvertexdata-> vertexstart = 0; mvertexdata-> vertexcount = 3; ogre:: vertexdeclaration * Decl = mvertexdata-> vertexdeclaration; ogre: vertexbufferbinding * Binding = mvertexdata-> vertexbufferbinding; // sets the vertex declaration, our vertex Declaration has only one data stream and only contains the position, color size_t offset = 0; Decl-> addelement (0, offset, ogre: vet_float3, ogre: ves_position ); offset + = ogre: vertexelement: gettypesize (Ogre: vet_float3); Decl-> addelement (0, offset, ogre: vet_colour, ogre: ves_diffuse ); offset + = ogre: vertexelement: gettypesize (Ogre: vet_colour); // create a vertex cache and fill the vertex data in ogre: hardwarevertexbuffersharedptr vertexbuffer = ogre: hardwarebuffermanager :: getsingleton (). createvertexbuffer (Decl-> getvertexsize (0), 3, ogre: hardwarebuffer: hbu_static_write_only); float * lockptr = static_cast <float *> (vertexbuffer-> lock (0, vertexbuffer-> getsizeinbytes (), ogre: hardwarebuffer: hbl_discard); ogre: rgba * pcol; For (INT I = 0; I <3; ++ I) {* lockptr ++ = vertices [I] [0]; * lockptr ++ = vertices [I] [1]; * lockptr ++ = vertices [I] [2]; pcol = static_cast <ogre: rgba *> (static_cast <void *> (lockptr); * pcol ++ = colours [I]; lockptr = static_cast <float *> (static_cast <void *> (pcol);} vertexbuffer-> unlock (); // bind the vertex cache to the data stream binding No. 0-> setbinding (0, vertexbuffer); // create an indexdata object to manage the vertex index mindexdata = new ogre: indexdata (); mindexdata-> indexstart = 0; mindexdata-> indexcount = 3; // create a vertex index cache and fill in the Data mindexdata-> indexbuffer = ogre: hardwarebuffermanager: getsingleton (). createindexbuffer (Ogre: hardwareindexbuffer: it_16bit, mindexdata-> indexcount, ogre: hardwarebuffer: hbu_static_write_only); mindexdata-> indexbuffer-> writedata (0, mindexdata-> indexbuffer-> getsizeinbytes (), faces, true); // you can specify maabb as the enclosure. merge (Ogre: vector3 (vertices [0] [1], vertices [0] [2], vertices [0] [3]); maabb. merge (Ogre: vector3 (vertices [1] [1], vertices [1] [2], vertices [1] [3]); maabb. merge (Ogre: vector3 (vertices [2] [1], vertices [2] [2], vertices [2] [3]); mboundingradius = ogre: Math:: boundingradiusfromaabb (maabb );}
Then, submit it in the getrenderoperation () function:
void Triangle::getRenderOperation(Ogre::RenderOperation& op){op.operationType = Ogre::RenderOperation::OT_TRIANGLE_LIST;op.useIndexes = true;op.vertexData = mVertexData;op.indexData = mIndexData;}
3. Finally, you need to mention the getmaterial () function from renderable. As the name suggests, the engine learns the material of the object to be merged. Here we create a material that only uses the vertex color of the object:
Ogre::MaterialPtr material = Ogre::MaterialManager::getSingleton().create("TriangleMaterial", Ogre::ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME);material->getTechnique(0)->getPass(0)->setLightingEnabled(false);material->getTechnique(0)->getPass(0)->setCullingMode(Ogre::CULL_NONE);
This material is then assigned to the triangle through the setmaterialname () function for submission during rendering.
After completing the preceding steps, call the following in the main build function:
Ogre::SceneNode* node = mSceneMgr->getRootSceneNode()->createChildSceneNode("TriangleNode");mTriangle = new Triangle();mTriangle->setMaterialName("TriangleMaterial");node->attachObject(mTriangle);
Run the program and you will see a colored triangle.
To some extent, in the 3D world, you learn to draw a triangle, and you will learn to draw anything.
The source code of the project supporting the article can be downloaded here: http://download.csdn.net/source/3562886. the development environment is vs2008+ ogre1.7.3.