Back to tutorial index page

Making a Q3 level out of models

(A discussion on a 'modern' approach to level design for Quake 3 Arena)

After some flirtation with D3/Q3 technology I decided it was time to revisit Quake 3 level design, but with a thoroughly up to date approach.

The first step was to block out a caulk layout in GTKradiant, texture the inside with a simple texture and compile and play it. This gave me an idea of scale and game flow. I made a conscious effort to keep the scale a little too large as I would be building inside the boundries set by layout. One thing to keep in mind is how Q3 controls vis. Each area was 1024 or 512 units square (more or less). Each area of the map will need to be a separate model, as Q3 can not cut up models in the same way that it does brushes to control vis. Therefore if I keep each model roughly the size of each vis block (default 1024, but I planned to reduce that by half), not running into vis issues should be fairly straight forward.

Next I converted my caulk and single texture map into an ase model using q3map2. This was imported into blender to be used as my 'guide' when creating my map mesh.

The next stage was the fun bit...building the map.
Mapping in blender has both advantages and disadvantages to GTK. The main advantage is the freedom is gives. I can create any shape I like and not be hindered by the grid or the 3 basic view points. The big down side is the slowness of texture mapping and the time consuming process of exporting the map to take a quick look at it in-game.
Here is the completed mesh:

The next stage was breaking up the mesh into sections to export into GTK.
Now, there may be better approaches to this, but I broke the complete mesh up and saved it as six separate .blend files.
The big problem would have been if I needed to alter any inter connecting areas...luckily that problem did not arrise. Each new mesh was triangulated then being careful here to keep the mesh snapped to the grid as I repositioned it, I then recentred each part over the point of origin. The next step was to separate the mesh by materials (each material corresponding to and linked to an in game texture). I was then ready to export each section as an ase model and reconstruct the entire map in GTK.
A section of mesh ready to go:

The laborious part of the process is hand hacking the ase files to edit the texture paths for Q3. Q4 require only a single alteration. Q3 requires 3 per material, and a mixture of \ and / in the pathways. It's not too bad if your mesh has only a single texture, but if it contains something like ten, it's a right pain in the arse.

Having got the models into GTK they all aligned perfectly. I used my original blocked out map (now all caulk) as a caulk hull to fit each mesh into. At this point I was rather pleased with myself...over draw is my bitch ;)
As smoothing is not supported on models in Q3 I had previously written shaders for each of my model's textures, so that phong shading would be applied. The models were flagged to be lightmapped and given a high resolution lightmap scale.
I did not set autoclipping on the meshes deliberately as I want bots to be able to play the level.
This created yet more work as I had to tightly weap clip the level to make it solid and easy for the bots to navigate (or more precisely for bspc to compile a bot file). I clipped out each model as I added it, rather than having a huge task to do at the end.
Detailing, item placement and lighting were still to do, but the majority of the work was done at this point.
The shot below shows a section of my map 'in-game'

The same area is shown below with the wire frame on, showing what is being drawn at this time:

Although r_speeds are actually quite high from this view point (I got carried away with eye candy), you can see how/where the level is being culled. There is a large area below the floor in the fore ground that is not being rendered.

Hope this brief description of my work flow is helpful in some way. For more precise details don't hesitate to ask :)