Track files in Ultimate Stunts are simple text files with the extension .track, and they are usually located in the tracks subdirectory of the data files. You can simply open them in your favourite text editor, modify and save them. Note that the tracks that are provided with the standard data files are UNIX-style text files, which means that opening them in windows notepad might give problems. Windows users can open them with wordpad. Saving as DOS-style text is not a problem, as Ultimate Stunts can read both types of text files. I don't think it can read Macintosh-style text files, so Apple-users should save either in UNIX-style or in DOS-style.
TRACKFILE 4 5 1The first four lines of the file should always look like this. The TRACKFILE text is used to check if the loaded file really is an Ultimate Stunts track. The next three lines define the length, width and height of the track. These numbers should always be consistent with the track description in the rest of the file. If you change the sizes of the track, then you should also change these numbers to match the new size.
#properties: length width heigthThis is just a comment, it is ignored by the track loader. Actually, you could write anything here, because the loader will ignore anything until it reads BEGIN.
BEGIN textures/grass2.jpg textures/road2.jpg textures/concrete1.jpg textures/startfinish.jpg ENDThis section describes which textures are loaded. Textures should always be of a recognised file format (e.g. *.jpg or *.png), and their sizes should always be powers of 2 (4, 8, 16 etc.). Textures with alpha channel are also supported.
BEGIN sky = environment/sky3.rgb horizon = environment/kyoto-horizon.png envmap = environment/spheremap.rgb lightdir = -0.69,-0.7,-0.2 lightcol = 0.2,0.2,0.5 ambientcol = 0.0,0.0,0.0 skycol = 0.1,0.1,0.5 ENDIn this section, the environment settings are loaded. The lines (which should all be present) have the following meanings:
BEGIN tiles/empty.glb 0 tiles/horiz.glb 0 tiles/corner.glb 0 1 tiles/roadhoriz.glb 0 1 tiles/startfinish.glb:sf 0 1 2 3 ENDHere, the tiles are loaded. Every line consists of the tile filename and a list of numbers. These numbers refer to the textures that should be used by the tile. 0 is the first texture, 1 the second etc.. For example, the horizontal plane tiles/horiz.glb is loaded with the grass texture on it. The straight road tile tiles/roadhoriz.glb is loaded with a grass and a road texture. The order in which you refer to the textures does matter. For instance, if you change "tiles/roadhoriz.glb 0 1" to "tiles/roadhoriz.glb 1 0", then it would become a completely asphalted tile with a band of grass in the middle of it.
Be aware that if you point to too few textures for a tile, that a memory access fault, or a segmentation fault, can occur. The same thing can happen if you point to a texture that does not exist, for example if you point to nr 10 while you only loaded 5 textures.
The last line of this section shows something interesting: after the tile filename, it says ":sf". This means that this tile is used as a start/finish tile.
#tile_id/rotation/heigthJust another comment. As you can see, you can write comments between END and BEGIN. Now the most important section begins:
BEGIN 1/0/0 1/0/0 1/0/0 1/0/0 1/0/0 2/3/0 2/2/0 1/0/0 1/0/0 3/0/0 4/0/0 1/0/0 1/0/0 2/0/0 2/1/0 1/0/0 1/0/0 1/0/0 1/0/0 1/0/0 ENDHere the track itself is described. Every tile location is described by a set of three numbers. The whole section is a "top-view" of the map. As you can see, this track has 5 lines of 4 tiles, which is exactly the size mentioned at the begin of the file. It is important that before each tile there is whitespace consisting of exactly one tab. Anything else, like spaces, is wrong. You should check if your text editor converts tabs to spaces, and disable that feature if possible.
The first of the three numbers refers to one of the loaded tiles. 0 refers to the first tile, 1 to the second etc.. As you can see, the tiles at the edges of the track all have a 1, which is the horizontal plane without roads. In the middle 3x2 tiles you can see four times a 2, which is the sharp corner tile, one time a 3 (straight road) and a 4 (start/finish). Now you should have an idea of what the track looks like.
The second number defines the rotation. 0 is a non-rotated tile, 1 means a 90 degree counterclockwise rotation, 2 a 180 degree rotation, and 3 is a 270 degree counterclockwise rotation, which of course equals 90 degree clockwise. As you can see, the straight road and the start/finish tile have their original orientation. The corner tiles each have another orientation of course. Sometimes trial and error is the quickest way to find the correct orientation.
The third number is the vertical position of the tile. As this is a simple track, every tile is located at the same height.
BEGIN 2,2,0:0.0 2,1,0:2.0 1,1,0:4.0 1,2,0:6.0 1,3,0:8.0 2,3,0:10.0 2,2,0:12.0 ENDThis section describes the route that cars should follow. If cars do not follow this route, then they will get penalty time.
Every entry in this section consists of three indices (separated by commas), a ":", and then a time. The three indices point to a certain tile, and the time is used to calculate penalty time. See also the track format definition.
BEGIN 1/0/0 1/0/0 1/0/0 1/0/0 1/0/0 2/3/0 2/2/0 1/0/0 1/0/0 3/0/0 3/0/0 1/0/0 1/0/0 3/0/0 3/0/0 1/0/0 1/0/0 3/0/0 3/0/0 1/0/0 1/0/0 3/0/0 3/0/0 1/0/0 1/0/0 3/0/0 3/0/0 1/0/0 1/0/0 3/0/0 4/0/0 1/0/0 1/0/0 2/0/0 2/1/0 1/0/0 1/0/0 1/0/0 1/0/0 1/0/0 ENDNow you should also alter the numbers at the beginning of the file to:
TRACKFILE 4 10 1This adds some straight road tiles. That should not be too difficult to understand. Now we advance to the next level:
BEGIN tiles/empty.glb 0 tiles/horiz.glb 0 tiles/corner.glb 0 1 tiles/roadhoriz.glb 0 1 tiles/startfinish.glb:sf 0 1 2 3 tiles/diag2.glb 0 tiles/roaddiag.glb 0 1 ENDdiag2.glb is a slope without a road, and roaddiag.glb is a slope with a road on it. Now we can change the track section to:
BEGIN 1/0/0 1/0/0 1/0/0 1/0/0 1/0/0 2/3/0 2/2/0 1/0/0 1/0/0 3/0/0 3/0/0 1/0/0 5/2/0 6/2/0 6/2/0 5/2/0 1/0/1 3/0/1 3/0/1 1/0/1 5/0/0 6/0/0 6/0/0 5/0/0 1/0/0 3/0/0 3/0/0 1/0/0 1/0/0 3/0/0 4/0/0 1/0/0 1/0/0 2/0/0 2/1/0 1/0/0 1/0/0 1/0/0 1/0/0 1/0/0 ENDThis has a lot of changes compared to the previous example, so I'll try to explain it here. First of all, the tile ID numbers. The new numbers 5 and 6 refer to the new tiles diag2.glb and roaddiag.glb. You can see that I replaced the 1's with 5's and the 3's with 6's to get the slopes. Next, the rotation number. The "south" slope has rotation 0, because the slope tiles just happen to have the right orientation for that slope. The "north" slope has exactly the opposite orientation, so the 180 degree rotation is used.
Last, but not least, I'd like to explain the height number. Although the slopes are higher than the ground, they still have a height number of 0. That's because height 0 means that the tile geometry is between 0 and 12 meter above the ground, and height 1 means between 12 and 24 meter, and so on. The slope is in the range 0..12 meter, so its height number is 0. The height number does change for the tiles in the middle of the hill. As the ground level of these tiles is at the bottom of the tile, it needs to be lifted 1 tile unit (12 meter) in order to match the top height of the slopes. Try setting it to 0, if you don't understand me. You'll see what happens.
So, how is it done? The basic idea is to define more than one track section. This is an example:
TRACKFILE 4 10 2 #properties: length width heigth BEGIN textures/grass2.jpg textures/road2.jpg textures/concrete1.jpg textures/startfinish.jpg END BEGIN sky = environment/sky3.rgb horizon = environment/kyoto-horizon.png envmap = environment/spheremap.rgb lightdir = -0.69,-0.7,-0.2 lightcol = 0.2,0.2,0.5 ambientcol = 0.0,0.0,0.0 skycol = 0.1,0.1,0.5 END BEGIN tiles/empty.glb 0 tiles/horiz.glb 0 tiles/corner.glb 0 1 tiles/roadhoriz.glb 0 1 tiles/startfinish.glb:sf 0 1 2 3 END #tile_id/rotation/heigth BEGIN 1/0/0 1/0/0 1/0/0 1/0/0 1/0/0 2/3/0 2/2/0 1/0/0 1/0/0 3/0/0 3/0/0 1/0/0 1/0/0 3/0/0 3/0/0 1/0/0 1/0/0 3/0/0 3/0/0 1/0/0 1/0/0 3/0/0 3/0/0 1/0/0 1/0/0 3/0/0 3/0/0 1/0/0 1/0/0 3/0/0 4/0/0 1/0/0 1/0/0 2/0/0 2/1/0 1/0/0 1/0/0 1/0/0 1/0/0 1/0/0 END BEGIN 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 ENDFirst of all, take a look at the height number at the start of the file. It is now 2, because we have 2 layers. In your own tracks, you can use any number of layers, as long as it matches the number at the beginning of the file.
As you can see, I've filled the second layer with empty tiles (0 referring to tiles/empty.glb). When you work with multiple layers, you will use the empty tile many times, because you'll only need the extra layers at some locations. Recent Ultimate Stunts versions have an optimalisation that stops rendering once a tile ID of 0 is found. This means that the track builder needs to take care of two things:
We will use this knowledge to build a tunnel. But before we can do that, we need to load a texture for the walls of the tunnel, and the tunnel tiles themselves:
BEGIN textures/grass2.jpg textures/road2.jpg textures/concrete1.jpg textures/startfinish.jpg textures/bricks2.jpg textures/road1.jpg END BEGIN sky = environment/sky3.rgb horizon = environment/kyoto-horizon.png envmap = environment/spheremap.rgb lightdir = -0.69,-0.7,-0.2 lightcol = 0.2,0.2,0.5 ambientcol = 0.0,0.0,0.0 skycol = 0.1,0.1,0.5 END BEGIN tiles/empty.glb 0 tiles/horiz.glb 0 tiles/corner.glb 0 1 tiles/roadhoriz.glb 0 1 tiles/startfinish.glb:sf 0 1 2 3 tiles/tunnelin1.glb 0 5 4 2 tiles/tunnelhoriz.glb 5 4 2 tiles/diag2.glb 0 ENDWe've loaded an extra texture for the walls (bricks2.jpg), and one for the road inside the tunnel (road1.jpg), which is slightly different from the one used outside the tunnel. The new tiles are tunnelin1.glb, which is the tunnel entrance tile, tunnelhoriz.glb, which is a normal straight tunnel tile, and diag2.glb, which we already know. Now we can define the first layer:
BEGIN 1/0/0 1/0/0 1/0/0 1/0/0 1/0/0 2/3/0 2/2/0 1/0/0 1/0/0 3/0/0 3/0/0 1/0/0 7/2/0 5/2/0 5/2/0 7/2/0 1/0/1 6/0/0 6/0/0 1/0/1 7/0/0 5/0/0 5/0/0 7/0/0 1/0/0 3/0/0 3/0/0 1/0/0 1/0/0 3/0/0 4/0/0 1/0/0 1/0/0 2/0/0 2/1/0 1/0/0 1/0/0 1/0/0 1/0/0 1/0/0 ENDWe've made two slopes with tunnel entrances, and the tunnel inside. We've also added the horizontal plane ground on top of the hill, on the left and the right. Now you can see why we need two layers: we also want grass above the tunnels. That's done in the second layer:
BEGIN 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 1/0/1 1/0/1 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 0/0/10 ENDThat's the trick! Now you can create viaducts, loopings, and all other sorts of things that require multiple layers. The only thing you need to find out now is what sorts of tiles are available. It might help to take a look inside test.track. Test.track is used as a "test-site" for new tiles, so most tiles are used in that track.