summaryrefslogtreecommitdiffstats
path: root/doc/src/examples/hellogl_es.qdoc
diff options
context:
space:
mode:
Diffstat (limited to 'doc/src/examples/hellogl_es.qdoc')
-rw-r--r--doc/src/examples/hellogl_es.qdoc124
1 files changed, 124 insertions, 0 deletions
diff --git a/doc/src/examples/hellogl_es.qdoc b/doc/src/examples/hellogl_es.qdoc
new file mode 100644
index 0000000..0293584
--- /dev/null
+++ b/doc/src/examples/hellogl_es.qdoc
@@ -0,0 +1,124 @@
+/*!
+ \example opengl/hellogl_es
+ \title Hello GL ES Example
+
+ The Hello GL ES example is the \l{Hello GL Example} ported to OpenGL ES.
+ It also included some effects from the OpenGL \l{Overpainting Example}.
+
+ \image hellogl-es-example.png
+
+ A complete introduction to OpenGL ES and a description of all differences
+ between OpenGL and OpenGL ES is out of the scope of this document; but
+ we will describe some of the major issues and differences.
+
+ Since Hello GL ES is a direct port of standard OpenGL code, it is a fairly
+ good example for porting OpenGL code to OpenGL ES.
+
+ \tableofcontents
+
+ \section1 Using QGLWidget
+
+ QGLWidget can be used for OpenGL ES similar to the way it is used with
+ standard OpenGL; but there are some differences. We use EGL 1.0 to embedd
+ the OpenGL ES window within the native window manager. In
+ QGLWidget::initializeGL() we initialize OpenGL ES.
+
+ \section1 Using OpenGL ES rendering commands
+
+ To update the scene, we reimplment QGLWidget::paintGL(). We use OpenGL ES
+ rendering commands just like we do with standard OpenGL. Since the OpenGL
+ ES common light profile only supports fixed point functions, we need to
+ abstract it somehow. Hence, we define an abstraction layer in
+ \c{cl_helper.h}.
+
+ \snippet examples/opengl/hellogl_es/cl_helper.h 0
+
+ Instead of \c glFogxv() or \c glFogfv() we use \c q_glFogv() and to
+ convert the coordinates of a vertice we use the macro \c f2vt(). That way,
+ if QT_OPENGL_ES_CL is defined we use the fixed point functions and every
+ float is converted to fixed point.
+
+ If QT_OPENGL_ES_CL is not defined we use the floating point functions.
+
+ \snippet examples/opengl/hellogl_es/cl_helper.h 1
+
+ This way we support OpenGL ES Common and Common Light with the same code
+ and abstract the fact that we use either the floating point functions or
+ otherwise the fixed point functions.
+
+ \section1 Porting OpenGL to OpenGL ES
+
+ Since OpenGL ES is missing the immediate mode and does not support quads,
+ we have to create triangle arrays.
+
+ We create a quad by adding vertices to a QList of vertices. We create both
+ sides of the quad and hardcode a distance of 0.05f. We also compute the
+ correct normal for each face and store them in another QList.
+
+ \snippet examples/opengl/hellogl_es/glwidget.cpp 0
+
+ And then we convert the complete list of vertexes and the list of normals
+ into the native OpenGL ES format that we can use with the OpenGL ES API.
+
+ \snippet examples/opengl/hellogl_es/glwidget.cpp 1
+
+ In \c paintQtLogo() we draw the triangle array using OpenGL ES. We use
+ q_vertexTypeEnum to abstract the fact that our vertex and normal arrays
+ are either in float or in fixed point format.
+
+ \snippet examples/opengl/hellogl_es/glwidget.cpp 2
+
+ \section1 Using QGLPainter
+
+ Since the \c QGLPainter is slower for OpenGL ES we paint the bubbles with
+ the rasterizer and cache them in a QImage. This happends only once during
+ the initialiazation.
+
+ \snippet examples/opengl/hellogl_es/bubble.cpp 0
+
+ For each bubble this QImage is then drawn to the QGLWidget by using the
+ according QPainter with transparency enabled.
+
+ \snippet examples/opengl/hellogl_es/bubble.cpp 1
+
+ Another difference beetwen OpenGL and OpenGL ES is that OpenGL ES does not
+ support glPushAttrib(GL_ALL_ATTRIB_BITS). So we have to restore all the
+ OpenGL states ourselves, after we created the QPainter in
+ GLWidget::paintGL().
+
+ \snippet examples/opengl/hellogl_es/glwidget.cpp 3
+
+ Setting up up the model view matrix and setting the right OpenGL states is
+ done in the same way as for standard OpenGL.
+
+ \snippet examples/opengl/hellogl_es/glwidget.cpp 4
+
+ Now we have to restore the OpenGL state for the QPainter. This is not done
+ automatically for OpenGL ES.
+
+ \snippet examples/opengl/hellogl_es/glwidget.cpp 5
+
+ Now we use the QPainter to draw the transparent bubbles.
+
+ \snippet examples/opengl/hellogl_es/glwidget.cpp 6
+
+ In the end, we calculate the framerate and display it using the QPainter
+ again.
+
+ \snippet examples/opengl/hellogl_es/glwidget.cpp 7
+
+ After we finished all the drawing operations we swap the screen buffer.
+
+ \snippet examples/opengl/hellogl_es/glwidget.cpp 8
+
+ \section1 Summary
+
+ Similar to the \l{Hello GL Example}, we subclass QGLWidget to render
+ a 3D scene using OpenGL ES calls. QGLWidget is a subclass of QWidget.
+ Hence, its \l{QGLWidget}'s subclasses can be placed in layouts and
+ provided with interactive features just like normal custom widgets.
+
+ QGLWidget allows pure OpenGL ES rendering to be mixed with QPainter calls,
+ but care must be taken to maintain the state of the OpenGL ES
+ implementation.
+*/