2013-04-10

This article concludes our series on what is new in Qt 5.1 with respect to OpenGL. Earlier articles in this series are available at:

Part 1

Part 2

Part 3

Part 4

More shader stages

In Qt 5.0 the QOpenGLShader and QOpenGLShaderProgram classes only had support for Vertex and Fragment shaders. Qt 5.1 will include support for all shader stages supported by OpenGL:

Vertex Shaders

Fragment Shaders

Geometry Shaders (requires OpenGL 3.2)

Tessellation Control and Tessellation Evaluation Shaders (requires OpenGL 4.0)

Compute Shaders (requires OpenGL 4.3)

As long as your platform has support for the required OpenGL version, then Qt 5.1 will work there. The availability of Geometry, Tessellation stage and Compute shaders really opens the doors for some interesting effects and order of magnitude improvements in performance over what is possible with plain OpenGL 2.x.

For the future

As we have seen, Qt 5.1 adds a great deal new functionality and enablers around OpenGL. There is still much to do and we will continue adding more enablers to make it easier and safer to write OpenGL code as we move towards Qt 5.2. Some of the items on the radar include Textures, Texture Images, Samplers, Occlusion Queries, Transform feedback objects, Uniform Buffer Objects, Shader Storage Buffer Objects and Shader Program Pipeline Objects, Object labels for debug output

We are very keen to see OpenGL support in Qt continue to improve and will continue to work to do so. I know many people have been asking about the status of Qt3D. Although not part of the Qt3D module, the improvements described here form a good part of the foundations upon which we will build the Qt3D renderer. If all goes to plan then Qt3D will be released along with Qt 5.2.

An example

For now here is a video of an example written using Qt 5.1 (dev branch) and OpenGL. This gives a small taste of what can easily be done using these two great APIs together:

This scene consists of the following:

Terrain heightmap texture used to render large terrain region in just one function call!

Rendered with GL_PATCHES as we are using tessellation shaders

View frustum clipping performed on GPU (needs improvement to remove artifacts)

Dynamic tessellation levels determined by screen-space error

Wireframe included in single pass using geometry shader

GLSL subroutines to quickly change rendering style without changing shader program

Dynamic normal vector calculation

Texture blending controlled by terrain height, slope, and fragment distance

Very simple fog for depth cueing

Per-pixel directional lighting

As you can see this is quite some features but we have moved much work to the GPU. In fact the entire rendering function for this example is:

Most of the rendering function is just setting uniform variables and could be replaced with the use of a uniform buffer. The complete source code for this example is available at:

terrain_tessellation.tar.xz

terrain_tessellation.zip

Requirements for this example are Qt 5.1 alpha (or a recent build from the stable branch of git) and an OpenGL 4.0 capable system. See the window.cpp file for controls.

There are a number of improvements that could quite easily be made:

Use a compute shader to generate terrain on demand as we move around the world

Use a floating point texture for more vertical resolution

Use a Z-fill pre-pass to reduce fragment shader work load

Compute normal vectors once in compute shader rather than every frame

Add trees, bushes, rocks, grass using instanced geometry rendering

Make the terrain deformable and paintable (e.g. raise/lower land, paint paths, change terrain base color)

Use a density function rather than a simple heightmap to create caves and overhangs

Use a quad-tree tile approach to further reduce distant triangle count

Add more realistic atmospheric scattering

Ambient occlusion and shadows

We will cover some of these in future blog articles and in more depth in our Qt and OpenGL trainings. Happy rendering!

Show more