NMLTutorial/32 bit base graphics

From TTWiki
Jump to navigationJump to search

In this example we'll look into a small base graphics replacement, for both 8 bit and 32 bit graphics. We'll be replacing some level crossings in temperate and actic climate.


Example graphics

There will be three sets of graphics: regular 8 bit sprites, 32 bit sprites for the normal zoom level and an accompanying mask file. These graphics will be replacing sprites 1370 to 1373. The sprites for the arctic climate will occupy the same slots.


Here are the 8 bit sprites. Note that they're neatly ordered, so that we can use a template later on.

levelcrossings8.png - Level crossing sprites in open and closed state, for two climates. 8 bit.


The 32 bit sprites are very similar, but with a transparent instead of blue background. The pink bits are just to indicate the sprite borders.

levelcrossings32.png - Level crossing sprites in open and closed state, for two climates. 32 bit.


In order to get animation for the crossing lights with the 32 bit version, we need an additional mask file. This mask just contains the crossing lights in the exact positions as in the 32 bit file. This is an 8 bit file, so we have to use the blue background to indicate transparency.

levelcrossingsmask.png - Mask file for 32 bit sprites. 8 bit.


Replace

Let's start with the replace blocks for the 8 bit sprites. We'll add the 32 bit sprites later.

replace replace_levelcrossings_temperate(1370, "gfx/levelcrossings.png") {
    //realsprites go here
}

We've chosen the identifier replace_levelcrossings_temperate. It's not mandatory for 8 bit sprites alone, but we need it if we want to attach 32 bit sprites later. So why not add it straight away, right? The 1370 is the sprite number of the first sprite we want to replace.

Template

As stated before, we want to template these sprites. There are four sprites for each climate, all with the same offsets because all sprite boxes are the same size, so the template will be pretty straightforward:

template template_levelcrossing(x, y) {
    //[left_x, upper_y, width, height, offset_x, offset_y]
    [x    , y, 64, 42, -31, -11]
    [x+80 , y, 64, 42, -31, -11]
    [x+160, y, 64, 42, -31, -11]
    [x+240, y, 64, 42, -31, -11]
}

The x and y position are variable in the template, because we have the sprites for both climates in one file. Now it's just a matter of referencing our template inside the replace block and filling in the correct position of the top left pixel of the first sprite:

replace replace_levelcrossings_temperate(1370, "gfx/levelcrossings.png") {
    template_levelcrossing(0, 0)
}

Other climate

The procedure for the actic climate will be identical, but we need to select the correct sprites depending on the selected climate. This means guarding the two replace blocks with if-statements. Let's look at those if-statements first:

if (climate == CLIMATE_TEMPERATE) {
    //replace block for temperate to go here
}
if (climate == CLIMATE_ARCTIC) {
    //replace block for temperate to go here
}

You may use an else in front of the second if block, but that's not really necessary in this case. From here it's just a matter of adding the replace block for the temperate climate and writing a similar one for the arctic climate. The one for the arctic climate will of course get a different identifier and different template parameters:

if (climate == CLIMATE_TEMPERATE) {
    replace replace_levelcrossings_temperate(1370, "gfx/levelcrossings.png") {
        template_levelcrossing(0, 0)
    }
}
if (climate == CLIMATE_ARCTIC) {
    replace replace_levelcrossings_arctic(1370, "gfx/levelcrossings.png") {
        template_levelcrossing(0, 320)
    }
}

And this is actually all there is to it, if you just want 8 bit sprites. We'll leave adding a grf block and the language file over to you. It's no different than for the road vehicle.

32 bit graphics

Adding the 32 bit sprites is as you know done through alternative_sprites blocks. The identifiers used must be the same as for the equivalent 8 bit sprites. In our case the 32 bit sprites are for the normal zoom level, so we have to indicate ZOOM_LEVEL_NORMAL and of course BIT_DEPTH_32BPP.

For the temperate climate replace block, we'll end up with the following alternative_sprites block, simply by filling in all the information we already know:

alternative_sprites(replace_levelcrossings_temperate, ZOOM_LEVEL_NORMAL, BIT_DEPTH_32BPP, "levelcrossings32.png", "levelcrossingsmask.png") {

Because the graphics files for our 32 bit sprites are ordered exactly the same as the 8 bit sprites, we can use the very same template also for the alternative_sprites block:

alternative_sprites(replace_levelcrossings_temperate, ZOOM_LEVEL_NORMAL, BIT_DEPTH_32BPP, "levelcrossings32.png", "levelcrossingsmask.png") {
    template_levelcrossing(0, 0)
}

Similarly, we can write the alternative_sprites block for the arctic climate:

alternative_sprites(replace_levelcrossings_arctic, ZOOM_LEVEL_NORMAL, BIT_DEPTH_32BPP, "levelcrossings32.png", "levelcrossingsmask.png") {
    template_levelcrossing(0, 320)
}

Adding to the existing code

Now, where to put these alternative_sprites blocks, you may ask? Should you put them inside the if-statements, or after them? The answer is that it doesn't matter. If you like to keep things together, put them in the if block they belong to. If you like to keep an overview of the structure of the if-statements, add them after it.

Those of you used to programming, will probably prefer the first option. Those of you not used to programming, will probably prefer the latter. We're used to programming, and we want you to get used to it too, so we'll go with the first option. This will give us the following complete code:

template template_levelcrossing(x, y) {
    //[left_x, upper_y, width, height, offset_x, offset_y]
    [x    , y, 64, 42, -31, -11]
    [x+80 , y, 64, 42, -31, -11]
    [x+160, y, 64, 42, -31, -11]
    [x+240, y, 64, 42, -31, -11]
}

if (climate == CLIMATE_TEMPERATE) {
    replace replace_levelcrossings_temperate(1370, "gfx/levelcrossings.png") {
        template_levelcrossing(0, 0)
    }
    alternative_sprites(replace_levelcrossings_temperate, ZOOM_LEVEL_NORMAL, BIT_DEPTH_32BPP, "levelcrossings32.png", "levelcrossingsmask.png") {
        template_levelcrossing(0, 0)
    }
}
if (climate == CLIMATE_ARCTIC) {
    replace replace_levelcrossings_arctic(1370, "gfx/levelcrossings.png") {
        template_levelcrossing(0, 320)
    }
    alternative_sprites(replace_levelcrossings_arctic, ZOOM_LEVEL_NORMAL, BIT_DEPTH_32BPP, "levelcrossings32.png", "levelcrossingsmask.png") {
        template_levelcrossing(0, 320)
    }
}

And with that we conclude this example and in fact the whole series! Feel free to read the conclusion. Or not.


NML Tutorial: 32 bit base graphics