Viadeo Twitter Google Bookmarks ! Facebook Digg del.icio.us MySpace Yahoo MyWeb Blinklist Netvouz Reddit Simpy StumbleUpon Bookmarks Windows Live Favorites 
Logo Documentation Qt ·  Page d'accueil  ·  Toutes les classes  ·  Classes principales  ·  Annotées  ·  Classes groupées  ·  Modules  ·  Fonctions  · 

QGLBuilder Class

The QGLBuilder class constructs geometry for efficient display. More...

 #include <QGLBuilder>

This class was introduced in Qt 4.8.

Public Functions

QGLBuilder(QGLMaterialCollection * materials = 0)
QGLBuilder(QSharedPointer<QGLMaterialCollection> materials)
virtual ~QGLBuilder()
void addPane(qreal size = 1.0f)
void addPane(QSizeF size)
void addQuadStrip(const QGeometryData & strip)
void addQuads(const QGeometryData & quads)
void addQuadsInterleaved(const QGeometryData & top, const QGeometryData & bottom)
void addTriangleFan(const QGeometryData & fan)
void addTriangleStrip(const QGeometryData & strip)
void addTriangles(const QGeometryData & triangles)
void addTriangulatedFace(const QGeometryData & face)
QGLSceneNode * currentNode()
QGLSceneNode * finalizedSceneNode()
QGLSceneNode * newNode()
void newSection(QGL::Smoothing smooth = QGL::Smooth)
QSharedPointer<QGLMaterialCollection> palette()
QGLSceneNode * popNode()
QGLSceneNode * pushNode()
QGLSceneNode * sceneNode()

Related Non-Members

enum Smoothing { NoSmoothing, Smooth, Faceted }

Detailed Description

The QGLBuilder class constructs geometry for efficient display.

Use a QGLBuilder to build up vertex, index, texture and other data during application initialization. The finalizedSceneNode() function returns an optimized scene which can be efficiently and flexibly displayed during frames of rendering. It is suited to writing loaders for 3D models, and for programatically creating geometry.

Geometry Building

QGLBuilder makes the job of getting triangles on the GPU simple. It calculates indices and normals for you, then uploads the data. While it has addQuads() and other functions to deal with quads, all data is represented as triangles for portability.

The simplest way to use QGLBuilder is to send a set of geometry values to it using QGeometryData in the constructor:

 MyView::MyView() : QGLView()
 {
     // in the constructor construct a builder on the stack
     QGLBuilder builder;
     QGeometryData triangle;
     QVector3D a(2, 2, 0);
     QVector3D b(-2, 2, 0);
     QVector3D c(0, -2, 0);
     triangle.appendVertex(a, b, c);

     // When adding geometry, QGLBuilder automatically creates lighting normals
     builder << triangle;

     // obtain the scene from the builder
     m_scene = builder.finalizedSceneNode();

     // apply effects at app initialization time
     QGLMaterial *mat = new QGLMaterial;
     mat->setDiffuseColor(Qt::red);
     m_scene->setMaterial(mat);
 }

Then during rendering the scene is used to display the results:

 MyView::paintGL(QGLPainter *painter)
 {
     m_scene->draw(painter);
 }

QGLBuilder automatically generates index values and normals on-the-fly during geometry building. During building, simply send primitives to the builder as a sequence of vertices, and vertices that are the same will be referenced by a single index automatically.

Primitives will have standard normals generated automatically based on vertex winding.

Consider the following code for OpenGL to draw a quad with corner points A, B, C and D :

 float vertices[12] =
 {
     -1.0, -1.0, -1.0,   // A
     1.0, -1.0, -1.0,    // B
     1.0, 1.0, 1.0,      // C
     -1.0, 1.0, 1.0      // D
 };
 float normals[12] = { 0.0f };
 for (int i = 0; i < 12; i += 3)
 {
     normals[i] = 0.0;
     normals[i+1] = -sqrt(2.0);
     normals[i+2] = sqrt(2.0);
 }
 GLuint indices[6] = {
     0, 1, 2,     // triangle A-B-C
     0, 2, 3      // triangle A-C-D
 };
 glEnableClientState(GL_VERTEX_ARRAY);
 glEnableClientState(GL_NORMAL_ARRAY);
 glVertexPointer(3, GL_FLOAT, 0, vertices);
 glNormalPointer(3, GL_FLOAT, 0, normals);
 glDrawElements(GL_TRIANGLES, 6, GL_UNSIGNED_INT, indices);

With QGLBuilder this code becomes:

 float vertices[12] =
 {
     -1.0, -1.0, -1.0,   // A
     1.0, -1.0, -1.0,    // B
     1.0, 1.0, 1.0,      // C
     -1.0, 1.0, 1.0      // D
 };
 QGLBuilder quad;
 QGeometryData data;
 data.appendVertexArray(QArray<QVector3D>::fromRawData(
         reinterpret_cast<const QVector3D*>(vertices), 4));
 quad.addQuads(data);

The data primitive is added to the list, as two triangles, indexed to removed the redundant double storage of B & C - just the same as the OpenGL code.

QGLBuilder will also calculate a normal for the quad and apply it to the vertices.

In this trivial example the indices are easily calculated, however in more complex geometry it is easy to introduce bugs by trying to manually control indices. Extra work is required to generate, track and store the index values correctly.

Bugs such as trying to index two vertices with different data - one with texture data and one without - into one triangle can easily result. The picture becomes more difficult when smoothing groups are introduced - see below.

Using indices is always preferred since it saves space on the GPU, and makes the geometry perform faster during application run time.

Removing Epsilon Errors

Where vertices are generated by modelling packages or tools, or during computation in code, very frequently rounding errors will result in several vertices being generated that are actually the same vertex but are separated by tiny amounts. At best these duplications waste space on the GPU but at worst can introduce visual artifacts that mar the image displayed.

Closing paths, generating solids of rotation, or moving model sections out and back can all introduce these types of epsilon errors, resulting in "cracks" or artifacts on display.

QGLBuilder's index generation process uses a fuzzy match that coalesces all vertex values at a point - even if they are out by a tiny amount - and references them with a single index.

Lighting Normals and Null Triangles

QGLBuilder functions calculate lighting normals, when building geometry. This saves the application programmer from having to write code to calculate them. Normals for each triangle (a, b, c) are calculated as the QVector3D::normal(a, b, c).

If lighting normals are explicitly supplied when using QGLBuilder, then this calculation is not done. This may save on build time.

As an optimization, QGLBuilder skips null triangles, that is ones with zero area, where it can. Such triangles generate no fragments on the GPU, and thus do not display but nonetheless can take up space and processing power.

Null triangles can easily occur when calculating vertices results in two vertices coinciding, or three vertices lying on the same line.

This skipping is done using the lighting normals cross-product. If the cross-product is a null vector then the triangle is null.

When lighting normals are specified explicitly the skipping optimization is suppressed, so if for some reason null triangles are required to be retained, then specify normals for each logical vertex.

See the documentation below of the individual addTriangle() and other functions for more details.

Raw Triangle Mode

Where generation of indices and normals is not needed - for example if porting an existing application, it is possible to do a raw import of triangle data, without using any of QGLBuilder's processing.

To do this ensure that indices are placed in the QGeometryData passed to the addTriangles() function, and this will trigger raw triangle mode.

When adding triangles in this way ensure that all appropriate values have been correctly set, and that the normals, indices and other data are correctly calculated, since no checking is done.

When writing new applications, simply leave construction of normals and indices to the QGLBuilder

Rendering and QGLSceneNode items.

QGLSceneNodes are used to manage application of local transformations, materials and effects.

QGLBuilder generates a root level QGLSceneNode, which can be accessed with the sceneNode() function. Under this a new node is created for each section of geometry, and also by using pushNode() and popNode().

To organize geometry for painting with different materials and effects call the newNode() function:

 QGLSceneNode *box = builder.newNode();
 box->setMaterial(wood);

Many nodes may be created this way, but they will be optimized into a small number of buffers under the one scene when the finalizedSceneNode() function is called.

Here the front can is a set of built geometry and the other two are scene nodes that reference it, without copying any geometry.

 QGLSceneNode *can = buildGeometry();
 canScene->addNode(can);
 {
     // rotate the can around so its label shows; and down
     // so the base is facing down
     QMatrix4x4 mat;
     QQuaternion q1 = QQuaternion::fromAxisAndAngle(1.0f, 0.0f, 0.0f, 270.0f);
     QQuaternion q2 = QQuaternion::fromAxisAndAngle(0.0f, 1.0f, 0.0f, 100.0f);
     mat.rotate(q2 * q1);
     can->setLocalTransform(mat);
 }

 // display a copy of the can to the left
 QGLSceneNode *node = new QGLSceneNode(canScene);
 node->addNode(can);
 {
     QMatrix4x4 mat;
     mat.translate(-2.0f, 0.0f, -2.0f);
     node->setLocalTransform(mat);
 }

 // display a copy of the can to the right
 node = new QGLSceneNode(canScene);
 node->addNode(can);
 {
     QMatrix4x4 mat;
     mat.translate(2.0f, 0.0f, -2.0f);
     node->setLocalTransform(mat);
 }

QGLSceneNodes can be used after the builder is created to cheaply copy and redisplay the whole scene. Or to reference parts of the geometry use the functions newNode() or pushNode() and popNode() to manage QGLSceneNode generation while building geometry.

To draw the resulting built geometry simply call the draw method of the build geometry.

 void BuilderView::paintGL(QGLPainter *painter)
 {
     canScene->draw(painter);
 }

Call the palette() function on the sceneNode() to get the QGLMaterialCollection for the node, and place textures and materials into it.

Built geometry will typically share the one palette. Either create a palette, and pass it to the constructor; or pass no arguments to the constructor and the QGLBuilder will create a palette:

 QGLBuilder builder;
 QGLSceneNode *root = builder.sceneNode();

 QGLMaterial *mat = new QGLMaterial;
 mat->setAmbientColor(Qt::lightGray);
 mat->setDiffuseColor(Qt::lightGray);
 QUrl url;
 url.setPath(QLatin1String(":/images/qt-soup.png"));
 url.setScheme(QLatin1String("file"));
 mat->setTextureUrl(url);
 texture = mat->texture();
 int canMat = root->palette()->addMaterial(mat);
 root->setMaterialIndex(canMat);
 root->setEffect(QGL::LitMaterial);

These may then be applied as needed throughout the building of the geometry using the integer reference, canMat in the above code.

See the QGLSceneNode documentation for more.

Using Sections

During initialization of the QGLBuilder, while accumulating geometry, the geometry data in a QGLBuilder is placed into sections - there must be at least one section.

Call the newSection() function to create a new section:

 // create the flat top lid of the can
 builder.newSection();
 builder.currentNode()->setObjectName(QLatin1String("CanTop"));
 QGeometryData top;
 top.appendVertex(canRim.center());
 top.appendVertexArray(canRim.vertices());
 builder.addTriangulatedFace(top);

 // create the sides of the can
 builder.newSection();
 builder.currentNode()->setObjectName(QLatin1String("CanSides"));
 builder.currentNode()->setMaterialIndex(canMat);
 builder.currentNode()->setEffect(QGL::LitModulateTexture2D);
 QGeometryData canTop = canRim;
 canTop.detach();
 canTop.appendVertex(canTop.vertex(0));       // doubled vert for texture seam
 canTop.generateTextureCoordinates();            // generate x texture coords
 QGeometryData canBase = canTop.translated(canExtrudeVec);  // base has tex.y == 0
 for (int i = 0; i < canTop.count(); ++i)
     canTop.texCoord(i).setY(1.0);                      // top has tex.y == 1
 builder.addQuadsInterleaved(canTop, canBase);

 // create the flat bottom lid of the can
 builder.newSection();
 builder.currentNode()->setObjectName(QLatin1String("CanBottom"));
 builder.currentNode()->setEffect(QGL::LitMaterial);
 QGeometryData rimReversed = canRim.translated(canExtrudeVec).reversed();
 QGeometryData canBottom;
 canBottom.appendVertex(rimReversed.center());
 canBottom.appendVertexArray(rimReversed.vertices());
 builder.addTriangulatedFace(canBottom);

 return builder.finalizedSceneNode();

Here separate sections for the rounded outside cylinder and flat top and bottom of the soup can model makes for the appearance of a sharp edge between them. If the sides and top and bottom were in the same section QGLBuilder would attempt to average the normals around the edge resulting in an unrealistic effect.

In 3D applications this concept is referred to as smoothing groups. Within a section (smoothing group) all normals are averaged making it appear as one smoothly shaded surface.

The can has 3 smoothing groups - bottom, top and sides.

This mesh of a Q is a faceted model - it has 0 smoothing groups:

To create geometry with a faceted appearance call newSection() with an argument of QGL::Faceted thus newSection(QGL::Faceted).

Faceted geometry is suitable for small models, where hard edges are desired between every face - a dice, gem or geometric solid for example.

If no section has been created when geometry is added a new section is created automatically. This section will have its smoothing set to QGL::Smooth.

To create a faceted appearance rather than accepting the automatically created section the << operator can also be used:

 QGLBuilder builder;
 QGeometryData triangles;
 triangles.appendVertices(a, b, c);
 builder << QGL::Faceted << triangles;

Geometry Data in a Section

Management of normals and vertices for smoothing, and other data is handled automatically by the QGLBuilder instance.

Within a section, incoming geometry data will be coalesced and indices created to reference the fewest possible copies of the vertex data. For example, in smooth geometry all copies of a vertex are coalesced into one, and referenced by indices.

One of the few exceptions to this is the case where texture data forms a seam and a copy of a vertex must be created to carry the two texture coordinates either side of the seam.

Coalescing has the effect of packing geometry data into the smallest space possible thus improving cache coherence and performance.

Again all this is managed automatically by QGLBuilder and all that is required is to create smooth or faceted sections, and add geometry to them.

Each QGLSection references a contiguous range of vertices in a QGLBuilder.

Finalizing and Retrieving the Scene

Once the geometry has been accumulated in the QGLBuilder instance, the finalizedSceneNode() method must be called to retrieve the optimized scene. This function serves to normalize the geometry and optimize it for display.

While it may be convenient to get pointers to sub nodes in the scene during construction, it is important to retrieve the root of the scene so that the memory consumed by the scene can be recovered. The builder will create a QGLMaterialCollection; and there may be geometry, materials and other resources: these are all parented onto the root scene node. These can easily be recovered by deleting the root scene node:

 MyView::MyView() : QGLView()
 {
     // in the constructor construct a builder on the stack
     QGLBuilder builder;

     // add geometry as shown above
     builder << triangles;

     // obtain the scene from the builder & take ownership
     m_scene = builder.finalizedSceneNode();
 }

 MyView::~MyView()
 {
     // recover all scene resources
     delete m_scene;
 }

Alternatively set the scene's parent to ensure resource recovery m_scene->setParent(this).

Member Function Documentation

QGLBuilder::QGLBuilder(QGLMaterialCollection * materials = 0)

Construct a new QGLBuilder using materials for the palette. If the materials argument is null, then a new palette is created.

QGLBuilder::QGLBuilder(QSharedPointer<QGLMaterialCollection> materials)

QGLBuilder::~QGLBuilder() [virtual]

Destroys this QGLBuilder recovering any resources.

void QGLBuilder::addPane(qreal size = 1.0f)

Convenience method to add a single quad of dimensions size wide by size high in the z = 0 plane, centered on the origin. The quad has texture coordinates of (0, 0) at the bottom left and (1, 1) at the top right. The default value for size is 1.0, resulting in a quad from QVector3D(-0.5, -0.5, 0.0) to QVector3D(0.5, 0.5, 0.0).

void QGLBuilder::addPane(QSizeF size)

Convenience function to create a quad centered on the origin, lying in the Z=0 plane, with width (x dimension) and height (y dimension) specified by size.

void QGLBuilder::addQuadStrip(const QGeometryData & strip)

Adds to this section a set of quads defined by strip.

If strip has less than four vertices this function exits without doing anything.

The first quad is formed from the 0'th, 2'nd, 3'rd and 1'st vertices. The second quad is formed from the 2'nd, 4'th, 5'th and 3'rd vertices, and so on, as shown in this diagram:

One normal per quad is calculated if strip does not have normals. For this reason quads should have all four vertices in the same plane. If the vertices do not lie in the same plane, use addTriangles() instead.

Since internally quads are stored as two triangles, each quad is actually divided in half into two triangles.

Degenerate triangles are skipped in the same way as addTriangles().

See also addQuads() and addTriangleStrip().

void QGLBuilder::addQuads(const QGeometryData & quads)

Add quads - a series of one or more quads - to this builder.

If quads has less than four vertices this function exits without doing anything.

One normal per quad is calculated if quads does not have normals. For this reason quads should have all four vertices in the same plane. If the vertices do not lie in the same plane, use addTriangleStrip() to add two adjacent triangles instead.

Since internally quads are stored as two triangles, each quad is actually divided in half into two triangles.

Degenerate triangles are skipped in the same way as addTriangles().

See also addTriangles() and addTriangleStrip().

void QGLBuilder::addQuadsInterleaved(const QGeometryData & top, const QGeometryData & bottom)

Add a series of quads by 'interleaving' top and bottom.

This function behaves like quadStrip(), where the odd-numbered vertices in the input primitive are from top and the even-numbered vertices from bottom.

It is trivial to do extrusions using this function:

 // create a series of quads for an extruded edge along -Y
 addQuadsInterleaved(topEdge, topEdge.translated(QVector3D(0, -1, 0));

N quad faces are generated where N == min(top.count(), bottom.count() - 1. If top or bottom has less than 2 elements, this functions does nothing.

Each face is formed by the i'th and (i + 1)'th vertices of bottom, followed by the (i + 1)'th and i'th vertices of top.

If the vertices in top and bottom are the perimeter vertices of two polygons then this function can be used to generate quads which form the sides of a prism with the polygons as the prisms top and bottom end-faces.

In the diagram above, the top is shown in orange, and the bottom in dark yellow. The first generated quad, (a, b, c, d) is generated in the order shown by the blue arrow.

To create such a extruded prismatic solid, complete with top and bottom cap polygons, given just the top edge do this:

 QGeometryData top = buildTopEdge();
 QGeometryData bottom = top.translated(QVector3D(0, 0, -1));
 builder.addQuadsInterleaved(top, bottom);
 builder.addTriangulatedFace(top);
 builder.addTriangulatedFace(bottom.reversed());

The bottom QGeometryData must be reversed so that the correct winding for an outward facing polygon is obtained.

void QGLBuilder::addTriangleFan(const QGeometryData & fan)

Adds to this section a set of connected triangles defined by fan.

N triangular faces are generated, where N == fan.count() - 2. Each face contains the 0th vertex in fan, followed by the i'th and i+1'th vertex - where i takes on the values from 1 to fan.count() - 1.

If fan has less than three vertices this function exits without doing anything.

This function is similar to the OpenGL mode GL_TRIANGLE_FAN. It generates a number of triangles all sharing one common vertex, which is the 0'th vertex of the fan.

Normals are calculated as for addTriangle(), given the above ordering. There is no requirement or assumption that all triangles lie in the same plane. Degenerate triangles are skipped in the same way as addTriangles().

See also addTriangulatedFace().

void QGLBuilder::addTriangleStrip(const QGeometryData & strip)

Adds to this section a set of connected triangles defined by strip.

N triangular faces are generated, where N == strip.count() - 2. The triangles are generated from vertices 0, 1, & 2, then 2, 1 & 3, then 2, 3 & 4, and so on. In other words every second triangle has the first and second vertices switched, as a new triangle is generated from each successive set of three vertices.

If strip has less than three vertices this function exits without doing anything.

Normals are calculated as for addTriangle(), given the above ordering.

This function is very similar to the OpenGL mode GL_TRIANGLE_STRIP. It generates triangles along a strip whose two sides are the even and odd vertices.

See also addTriangulatedFace().

void QGLBuilder::addTriangles(const QGeometryData & triangles)

Add triangles - a series of one or more triangles - to this builder.

The data is broken into groups of 3 vertices, each processed as a triangle.

If triangles has less than 3 vertices this function exits without doing anything. Any vertices at the end of the list under a multiple of 3 are ignored.

If no normals are supplied in triangles, a normal is calculated; as the cross-product (b - a) x (c - a), for each group of 3 logical vertices a(triangle, i), b(triangle, i+1), c(triangle, i+2).

In the case of a degenerate triangle, where the cross-product is null, that triangle is skipped. Supplying normals suppresses this behaviour (and means any degenerate triangles will be added to the geometry).

Raw Triangle Mode

If triangles has indices specified then no processing of any kind is done and all the geometry is simply dumped in to the builder.

This raw triangle mode is for advanced use, and it is assumed that the user knows what they are doing, in particular that the indices supplied are correct, and normals are supplied and correct.

Normals are not calculated in raw triangle mode, and skipping of null triangles is likewise not performed. See the section on raw triangle mode in the class documentation above.

See also addQuads() and operator>>().

void QGLBuilder::addTriangulatedFace(const QGeometryData & face)

Adds to this section a polygonal face made of triangular sub-faces, defined by face. The 0'th vertex is used for the center, while the subsequent vertices form the perimeter of the face, which must at minimum be a triangle.

If face has less than four vertices this function exits without doing anything.

This function provides functionality similar to the OpenGL mode GL_POLYGON, except it divides the face into sub-faces around a central point. The center and perimeter vertices must lie in the same plane (unlike triangle fan). If they do not normals will be incorrectly calculated.

Here the sub-faces are shown divided by green lines. Note how this function handles some re-entrant (non-convex) polygons, whereas addTriangleFan will not support such polygons.

If required, the center point can be calculated using the center() function of QGeometryData:

 QGeometryData face;
 face.appendVertex(perimeter.center()); // perimeter is a QGeometryData
 face.appendVertices(perimeter);
 builder.addTriangulatedFace(face);

N sub-faces are generated where N == face.count() - 2.

Each triangular sub-face consists of the center; followed by the i'th and ((i + 1) % N)'th vertex. The last face generated then is (center, face[N - 1], face[0], the closing face. Note that the closing face is automatically created, unlike addTriangleFan().

If no normals are supplied in the vertices of face, normals are calculated as per addTriangle(). One normal is calculated, since a faces vertices lie in the same plane.

Degenerate triangles are skipped in the same way as addTriangles().

See also addTriangleFan() and addTriangles().

QGLSceneNode * QGLBuilder::currentNode()

Returns a pointer to the current scene node, within the current section.

If there is no current section then newSection() will be called to create one.

See also newNode() and newSection().

QGLSceneNode * QGLBuilder::finalizedSceneNode()

Finish the building of this geometry, optimize it for rendering, and return a pointer to the detached top-level scene node (root node).

Since the scene is detached from the builder object, the builder itself may be deleted or go out of scope while the scene lives on:

 void MyView::MyView()
 {
     QGLBuilder builder;
     // construct geometry
     m_thing = builder.finalizedSceneNode();
 }

 void MyView::~MyView()
 {
     delete m_thing;
 }

 void MyView::paintGL()
 {
     m_thing->draw(painter);
 }

The root node will have a child node for each section that was created during geometry building.

This method must be called exactly once after building the scene.

Calling code takes ownership of the scene. In particular take care to either explicitly destroy the scene when it is no longer needed - as shown above.

For more complex applications parent each finalized scene node onto a QObject so it will be implictly cleaned up by Qt. If you use QGLSceneNode::setParent() to do this, you can save an explicit call to addNode() since if setParent() detects that the new parent is a QGLSceneNode it will call addNode() for you:

 // here a top level node for the app is created, and parented to the view
 QGLSceneNode *topNode = new QGLSceneNode(this);

 QGLBuilder b1;
 // build geometry

 QGLSceneNode *thing = b1.finalizedSceneNode();

 // does a QObject::setParent() to manage memory, and also adds to the scene
 // graph, so no need to call topNode->addNode(thing)
 thing->setParent(topNode);

 QGLBuilder b2;
 // build more geometry
 QGLSceneNode *anotherThing = b2.finalizedSceneNode();

 // again parent on get addNode for free
 anotherThing->setParent(topNode);

If this builder is destroyed without calling this method to take ownership of the scene, a warning will be printed on the console and the scene will be deleted. If this method is called more than once, on the second and subsequent calls a warning is printed and NULL is returned.

This function does the following:

  • packs all geometry data from sections into QGLSceneNode instances
  • recalculates QGLSceneNode start() and count() for the scene
  • deletes all QGLBuilder's internal data structures
  • returns the top level scene node that references the geometry
  • sets the internal pointer to the top level scene node to NULL

See also sceneNode().

QGLSceneNode * QGLBuilder::newNode()

Creates a new QGLSceneNode and makes it current. A pointer to the new node is returned. The node is added into the scene at the same level as the currentNode().

The node is set to reference the geometry starting from the next vertex created, such that currentNode()->start() will return the index of this next vertex.

See also newSection().

void QGLBuilder::newSection(QGL::Smoothing smooth = QGL::Smooth)

Creates a new section with smoothing mode set to smooth. By default smooth is QGL::Smooth.

A section must be created before any geometry or new nodes can be added to the builder. However one is created automatically by addTriangle() and the other add functions; and also by newNode(), pushNode() or popNode() if needed.

The internal node stack - see pushNode() and popNode() - is cleared, and a new top-level QGLSceneNode is created for this section by calling newNode().

See also newNode() and pushNode().

QSharedPointer<QGLMaterialCollection> QGLBuilder::palette()

Returns the palette for this builder. This is the QGLMaterialCollection pointer that was passed to the constructor; or if that was null a new QGLMaterialCollection. This function returns the same result as sceneNode()->palette().

See also sceneNode().

QGLSceneNode * QGLBuilder::popNode()

Removes the node from the top of the stack, makes a copy of it, and makes the copy current.

If the stack is empty, behaviour is undefined. In debug mode, calling this function when the stack is empty will cause an assert.

A pointer to the new current node is returned.

The node is set to reference the geometry starting from the next vertex created, such that QGLSceneNode::start() will return the index of this next vertex.

See also pushNode() and newNode().

QGLSceneNode * QGLBuilder::pushNode()

Creates a new scene node that is a child of the current node and, makes it the current node. A pointer to the new node is returned. The previous current node is saved on a stack and it may be made current again by calling popNode().

See also popNode() and newNode().

QGLSceneNode * QGLBuilder::sceneNode()

Returns the root scene node of the geometry created by this builder.

See also newNode() and newSection().

Related Non-Members

enum QGL::Smoothing

This enum defines vertex smoothing treatments.

ConstantValueDescription
QGL::NoSmoothing0No smoothing processing is performed.
QGL::Smooth1Lighting normals averaged for each face for a smooth appearance.
QGL::Faceted2Lighting normals separate for each face for a faceted appearance.

This enum was introduced or modified in Qt 4.8.

Cette page est une traduction d'une page de la documentation de Qt, écrite par Nokia Corporation and/or its subsidiary(-ies). Les éventuels problèmes résultant d'une mauvaise traduction ne sont pas imputables à Nokia. Qt 5.0-snapshot
Copyright © 2012 Developpez LLC. Tous droits réservés Developpez LLC. Aucune reproduction, même partielle, ne peut être faite de ce site et de l'ensemble de son contenu : textes, documents et images sans l'autorisation expresse de Developpez LLC. Sinon, vous encourez selon la loi jusqu'à 3 ans de prison et jusqu'à 300 000 E de dommages et intérêts. Cette page est déposée à la SACD.
Vous avez déniché une erreur ? Un bug ? Une redirection cassée ? Ou tout autre problème, quel qu'il soit ? Ou bien vous désirez participer à ce projet de traduction ? N'hésitez pas à nous contacter ou par MP !
 
 
 
 
Partenaires

Hébergement Web