A Simple C++ OpenGL Shader Loader – Improved

I wrote one back in 2013, but I’ve learnt some things since then, so I’ve re-written it all with some changes. You can still load/compile shaders from strings or files, and then link/validate/use the resulting shader programs, only this time its all a little bit cleaner and more robust.

The main deficiencies of the previous incarnation were:

  • The Shader class wasn’t required for what I was using this stuff for, so I stripped it out – now you just create a ShaderProgram directly,
  • Error logs weren’t shown for any shader or shader program errors,
  • The shader program didn’t get validated,
  • Abuse of exit(-1) rather than throwing unchecked runtime_errors,
  • Inclusion of using clauses in headers, and
  • Possible wonky static declaration and initialisation of const_iterator error in uniform location getter meant that it might have only “got” the uniform location correcty on first run, when the const_iterator was declared – but in practice I haven’t seen any issues, perhaps because I spotted and fixed it but forgot to update article though…

Anyway, below is an improved version that fixes all of the above – here’s how you use it…

Usage

ShaderProgram Class Source Code

Here’s the code for the class itself:

Note: I’m not convinced that the compiler will even consider inlining the use() and disable() methods when the program is built as a hpp – I think I’d have to break it into .h and .cpp files for that… other than that I’m thinking the above code is pretty clean, robust and usable.

How-To: Create A Simple OpenGL 2D Particle Fountain in C++

I was recently asked about some particle systems I’d put together, so in response, this isn’t really a “look what I’ve coded” post – instead, it’s more of a “this is an easy way to set up a particle system framework” post.

To demonstrate the setup of a particle system using OpenGL, I’ve put together some simple starter code which displays a 2D particle fountain. I was going to just dump this code as a zipped project into a reply, but then (as my wife pointed out) it would be pretty much buried in the comments, so if other people starting OpenGL coding wanted to learn the basics of particle systems my code wouldn’t be as visible. As such, I’ve made this into a separate post – and all our example code does is this:

It’s a dirt-simple effect, but what it does isn’t so important right now – it’s deliberately simple. How it does what it does is what we’ll talk about.

Looking at particle systems from a high level – you generally have to choose between two different approaches to the system as a whole:

  1. You have a fixed number of particles (i.e. you have a fixed size array of however many particles) and you reset each particle to “recycle” it, or
  2. You have a dynamic number of particles (i.e. you have a dynamically resizable array) and you destroy each particle and create a new one as required.

I’ve gone with the latter approach for this code using a vector of particles (nothing to do with Vec2/Vec3 math – just the name of resizable array kinda construct). Admittedly, there’s more overhead in the creation and destruction of particles, but on the upside you don’t get that initial rush of particles you get when using fixed size arrays and as soon as you start the program BLAM! All your particles going at once.

To demonstrate what I mean, in the video below I’ve modified the code to instantiate ALL particles up to the particle limit at once, and then as soon as a particle goes off the bottom of the screen it gets destroyed and a new particle is created. The effect of which is that you get a single big burst of particles, and then as they all get destroyed and recreated at different times they turn into a smooth flow within a couple of seconds:

If you’re using a fixed size particle array, you’ll need to implement some mechanism to delay the instantiation or “launch” of the particles – for example, you might give each particle a random framesUntilLaunch value and decrease it by 1 each frame until it gets to 0 and you can let the particle do its thing. I wrote such a delay system for some fireworks code I did a while back if you’d like to see a concrete example.

Anyways, back at this code, our main is using three main classes to encapsulate data and provide methods to manipulate it:

  • Colour4f.hpp – A class to store a colour as red/green/blue/alpha floating point values and manipulate ’em (including interpolation of colours),
  • Vec2.hpp – A templatised class to store two values as a vector (Not a resizable array this time! An actually “euclidian vector” – i.e. two values which represent a direction and magnitude). It also includes lots of overloaded operators so you can add two vectors together (“up” + “right” gives you “up-right” etc.), multiply a vector by a scalar (i.e. moving “up-right” multiplied by 10 means you’re now moving up-right ten times as fast). By templatised, I mean that you can create a Vec2 of ints, or floats, or doubles, or shorts, or whatever numeric type makes sense for your application – take a look at the source below if you want examples, and finally
  • Particle2D.hpp – A particle class which uses the above Colour4f and Vec2 classes to provide powerful movement and colour modification options in a small & easy to use package.

You can download the complete source code as a Code::Blocks project here, if you’d like: PointSprite_Particle_Fountain_2D.zip.

Note: As my OS of choice is GNU/Linux (LMDE, to be specific), the source files provided will have Linux line-endings – so you’ll need to open them with a good text editor like Notepad++ if you’re in in Windows, otherwise each file will look like a single massive block of noise!

Or, if you’d prefer to just browse the source code so you can copy and paste sections, you’ll find it all laid out below.

I love particle systems – you can do some visually stunning things with really simple code, or you can do amazing things if you take it further. Either way, I hope you have a lot of fun with them (there’s lots more particle stuff on this site if you’re looking for inspiration – try Actionscript tag for a start!) – and if you make anything cool or pretty using and you think I’ve helped – please do show me or let me know – I’ve love to see or hear about what you’ve done! =D

Also – if you make this – show me how, okay?

Cheers!

Continue reading How-To: Create A Simple OpenGL 2D Particle Fountain in C++

Vec3: A Simple Vector Class in C++

This is really the second post of three updating an earlier post on how to write some simple FPS-type controls for OpenGL – last post we looked at a FpsManager class so we could get frame timings to implement framerate independent movement. This time, we’re looking at a simple Vec3 class which stores 3D coordinates and helps to perform some operations on them. This is going to form part of the Camera class in the final part, but I thought I’d put it here on its own so it can be re-used.

There’s probably about ten million different vector classes out there, but I really wanted to write my own so I understood exactly how it worked, and I’ve commented it pretty heavily in the process – so hopefully if you’re looking for a vector class you might be able to look at this one, see how it works and what it does, and take and modify it for your own work.

Before skipping to the code, let’s just take a quick look at what it does – it packages up 3 values called x, y and z, and allows us to easily manipulate them. Quite what you store in these values is up to you, it could be a vertex position, or a direction vector, or a RGB colour – anything that has three values, really.

If we were dealing with two vertexes, we can do stuff like this:

Seems pretty easy to work with to me…

Here’s the code for the Vec3 class itself as a templatised, header-only C++ .hpp file – just include the Vec3.hpp class and you’re good to go:

Next post, we’re going to be implementing a FPS-style camera class using this Vec3 class to move around a 3D scene – and because of all our hard work in getting this vector class together, it’s going to make moving the camera around a doddle =D

Cheers!

How To: Perform manual frustum culling

The Problem

Be Careful Machine SignWhen you use OpenGL or DirectX or whatever to draw geometry, the API itself does its own vertex culling (i.e. it doesn’t spend time drawing things which will not be visible on the screen – it opts to not draw them), but it has to do this in the only way it can – by testing each vertex against the projected window-coordinates and making a decision from that. This, as you might not be surprised to learn, is not the most efficient way to consider geometry.

Let’s take an example:

If you had a small sphere visible 5 units directly in front of you, and then you move 10 units forward, the sphere’s obviously now 5 units behind you – but your graphics API won’t (and can’t) care – it’ll just test each vertex of the sphere to see if it’s within your viewing frustum. If the sphere has a couple of hundred vertexes, you’re doing a couple of hundred checks, and making the decision not to draw anything a couple of hundred times. What about if you had ten thousand small spheres 5 units in front of you, and then you move 10 units forward? That’s a lot of per-vertex checking, and it’ll put a significant dent in your frame rate, to draw absolutely nothing at all!

Surely there’s a better way?! You betcha =D

The Solution in Theory

We, or you, know a lot more about the nature of your geometry than your graphics API – which knows nothing at all. It can’t make assumptions, it doesn’t have common sense – we have to provide it. So let’s!

frustrum

Any object that you draw can be enclosed in a sphere, where the size of the sphere will vary depending on the size of the longest axis of the object. Drawing a tree? You can enclose the tree in an imaginary sphere which is the height of the tree and centred on the tree. Drawing a person? You can enclose the person in an imaginary sphere of diameter the person’s height and centred on the person. Once we can check whether this bounding-sphere is within the viewing frustum, we can make a conscious choice as to whether we should even attempt to draw the geometry or not. So if the sphere bounding my tree, or person, or whatever doesn’t at least intersect all 6 planes (top/bottom, left/right, near/far) of my viewing frustum – then it’s not on the screen, and I can choose not to draw it in the first place – thus skipping all that per-vertex checking by applying a little bit of common sense. Sound good?

Closer to Practice

To project a vertex position in world coordinates, say, (-10, 15, 3) [i.e. -10 on the X-Axis, 15 on the Y-Axis, 3 on the Z-Axis], into screen/window coordinates, we can multiply the ModelViewProjection matrix by the vertex position (Careful: The MVP matrix multiplied by the vertex is NOT the same as the vertex multiplied by the MVP matrix! They are not commutative!).

If we then add a radius around that vertex (which is the centre of our object, and something you have to provide – i.e. you need to pick a centre point), we can check if the bounding sphere around that central point intersects any of the six planes of our viewing frustum, and if it doesn’t, we simply don’t even try to draw the object, and gain however-many per-vertex checks for our effort. If you’re checking a single 8 vertex cube you’re not going to gain all much, but if you’re checking multiple 5,000 vertex objects, then you’ll save the GPU that many per-vertex checks per frame! :)

The Solution in Practice

Now that you get the concept, here’s comes the code. This is written in C++, but really, it’s just some math about whether a sphere intercepts or is within the boundary of six planes which comprise our viewing frustum. You can adapt it to anything, and I hope you do :)

The function takes the following parameters:

  1. An array of 16 floating point values which specify the ModelViewProjection Matrix
  2. The x position of the central point
  3. The y position of the central point
  4. The z position of the central point
  5. The radius of the bounding sphere

The function returns a simple boolean of true or false to indicate whether the bounding sphere falls even partially within the viewing frustum.

If you’re not sure how to get the ModelViewProjection matrix, you can calculate it by mulitplying the Projection matrix by the ModelView matrix (in that specific order!).

So in OpenGL fixed-pipeline code, you could get it into a 16 element array like this:

While if you were working from the OpenGL SuperBible 5th Edition, you could just throw it into the function like this:

Cheers!