Planning the Spontaneous

It's more than just a blueprint.

Renderer: Picking

Posted by Robert Chow on 03/12/2009

Remember that decorator pattern I used for writing to textures?  Also particularly useful for picking too.

Decorate the main drawer class with a picking class.  This allows for the picking class to start off by setting up the render-mode to select mode, and to set the X and Y co-ordinates of the mouse.  Render the image as normal, but because of the render-mode switch, the image is rendered using the select buffer instead of the device context.  After this, the picking class is also able to interpret the picking buffer, and then return the results.

Sounds fairly easy.  But I did run into a problem near the start.

First off was the mouse wasn’t picking where I wanted – it was interpreting the mouse as always in the bottom-left hand corner.  Why so?

I later learnt that when changing the render-mode, it automatically multiplies the projection matrix by some pre-configured matrix so it can do the picking appropriately.  In the original drawer class, I was resetting the projection matrix by loading the identity, and thus wiping what the picker class had set up.  Kind of like defeating itself.  So I had to change this by taking the matrix resets out of the main drawing method, and place them outside – these would have to be called elsewhere – likely to be through the Renderer facade (another GoF pattern), before calling the draw.

So with the matrix set up properly, I did encounter another problem.  And this time it was hardware based.  It would pick appropiately on my supervisor’s computer, yet not on mine.

An example scenario:  there are several images overlapping each other, each with their own pick Id.

My supervisors computer: picks appropriately – returns the object with the nearest Z value (most positive), under mouse (X,Y) .

My computer: picks unappropriately – returns the object with the nearest Z value, under mouse(X,Y) – providing the object has not moved in modelview space in terms of the Z value.  This accounts for transformations, rotations and scales.  So therefore it will sometimes return the correct object, but most of the time, it won’t.  Particularly annoying if you have a scene that is constantly rotating, and you want to pick the nearest item – it will always pick the same item every single time, simply because it was rendered at the front first before it was rotated.

Simple fix:  enable culling.  This means that anything that is not in view won’t be rendered, so technically there is nothing behind the frontmost object – it can be the only one that is picked!

But that’s also particularly annoying when you want to use 2-face rendering.  This is the ability to render shapes clockwise, and counter-clockwise.  Enabling culling in OpenGL will result in all shapes that would originally be drawn clockwise to the screen, not drawn at all.  Not so useful in rotating scenes!


Combining textures and picking, this demo allows the user to pick a quadrant, and that will change accordingly – to texture if off, or to non-texture if on.

Renderer Picking Demo. From top-left, clockwise:  empty canvas; bottom-left quadrant click to turn texture on; top-right quadrant click to turn texture on; top-left quadrant click to turn texture on; bottom-left quadrant click to turn texture off; top-right quadrant click to turn texture off; bottom-right quadrant click to turn texture on; top-left quadrant click to turn texture off.  To achieve the original image from the last step, the user would click bottom-right quadrant, turning the texture off.


One Response to “Renderer: Picking”

  1. […] cube), the scene graph (rotating cube), the camera (viewing the cube, using the scene graph) and picking (turning faces on/off). But what about the […]

Leave a Reply

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out /  Change )

Google+ photo

You are commenting using your Google+ account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )


Connecting to %s

%d bloggers like this: