Disappointed with the horizontal scrolling techniques in most Atari ST games, programmer Wayne Smithson created his own Defender-like demo with the working title of It Can't Be Done. This referred to the long-held belief that the Atari ST was incapable of smooth horizontal scrolling due to the limitations of the hardware.
The title was eventually changed to Anarchy and the game was released by Psygnosis in 1990 for both the Atari ST and Amiga.
Although the Amiga version featured far better graphics, it's interesting to see exactly how the Atari ST version achieved its scrolling effect.
Pre-shifting graphics and storing multiple copies in memory is the standard method used in Atari ST games, but many of the comments on forums and on YouTube clips guessed that 16 combinations of the background were made along with tonnes of movem.l instructions to update the display. While this is a reasonable guess, this is not how Wayne achieved the effect.
The screen is 320x200 pixels in size and consists of 4 sections:
- Score and radar (18 pixels high)
- Main display (138 pixels high)
- Ground (32 pixels high)
- Shield (12 pixels high)
The palette is divided into 4 blocks of 4 colours, and the palette is switched at various times to add a little more colour. When a large explosion occurs, the background black colour is altered to light up the entire window (a standard effect in many games).
If you look closely at the looping animation, you will notice a very repetitive background pattern, and a very small parallax section in the bottom section of the screen. Some observations:
- The main portion of the display has a pattern that repeats every 16 pixels.
- Nothing is ever drawn into the small parallax strip at the bottom of the screen.
- The parallax strip consists of 2 layers, the background pattern being 32 pixels wide and the foreground layer 64 pixels wide.
- When the player's ship changes direction, the scrolling never slows down or stops — it instantly begins scrolling in the other direction.
- With the main game area only being 138 pixels high, the ST is only having to draw about 70% of the display to keep it looking smooth.
I personally find the parallax section at the bottom of the screen very disappointing, as it doesn't include large obvious gaps in the front layer that show the background through it. Without a very close look, you'd hardly even notice it's even 2 layers. Because that horizontal slice is never drawn on by the game itself, it would have been the perfect place to swap in a completely different palette and really use it to make the 2 layers different and show the effect off. It was a real wasted opportunity in my opinion.
So, how was it done?
The Atari ST version actually stores 8 entire copies of the display, each offset 2 pixels compared to the previous image. With each screen taking up 32k of memory, these 8 copies use 256k of memory — half of the minimum 512k memory requirement!
Because the background continues to scroll even when the player changes direction, the game will always switch to one of the other 8 screens in memory with each frame update. When travelling left, it will always use the following frame number as that will be indented 2 pixels further to the right. Similarly, when travelling to the right, the previous frame number will be used. The frame will wrap at the edges when all 8 frames have been used in a loop in either direction.
The only remaining question is to determine when the game restores the 8 screens in memory, as at some point it needs a clean copy of the screen to draw the next frame onto. By flying in one direction shooting bullets for 8 frames then examining a snapshot of memory, you can see that the game doesn't bother to restore the screen until just before it needs it:
In the following sequence taken from a memory dump, you can see the previous 7 frames in memory with the bullets still drawn into them, along with the latest frame that was drawn. Therefore the game has to keep a restore buffer of the original pixels that were over-written when it rendered the frame. The game restores the buffer just prior to rendering the new frame over the old one.
The pre-shifting of graphics doesn't end with the 8 copies of the screen. Every single moving image used by the game moves in multiples of 2 pixels and is stored pre-shifted in memory. Almost all objects are tiny, only 16 pixels wide. When the game begins, the objects are expanded from a source image:
If an object is 16 pixels wide by 10 pixels high, the image will be stored in 2 blocks (the leftmost 16x10 pixels, followed by the rightmost 16x10 pixels) 8 times in a row to have every pre-shifted combination. Further down in memory there is also a 1-bitplane mask for every single object, showing which pixels are visible in the image. This acts as a cookie-cutter so as not to obscure the background with black pixels.
If an object is only partially visible at the far right-hand side of the screen, only the left-most pixels of the relevant image need to be drawn. Similarly if an object is partially visible at the left-hand side of the screen, only the right-most pixels need drawing. If an object is completely visible on the screen, both the objects will be drawn.
On the Amiga, the same 16-colour object would only need to be stored once, using 80 bytes of memory and the blitter can be instructed to draw the object into any pixel position. On the Atari ST, the same object uses 80 bytes x 2 (left/right sections) x 8 pre-shifted copies = 1280 bytes! This soon eats away all your memory, meaning that tricks like this can only be used in a very limited number of games such as Defender clones.
Sadly this trick cannot be applied generically to every type of scrolling game, so those hoping to see this kind of scrolling in a conversion of Street Fighter 2 will be very disappointed!
This isn't a full breakdown of all memory but gives you some idea how little memory is left for an actual game:
- $400 - $12f18 = TOS, code etc
- $12f18 - $16a38 = Player ship, bullets, mask, font, status bar etc (length $3b20 = 15,136 bytes)
- $16a38 - $30f38 = Pre-shifted enemies (length $1a500 = 107,776 bytes)
- $30f38 - $37876 = Pre-shifted masks (length $693E = 26,942 bytes)
- $37876 - $3b900 = Code/data/tables
- $3b900 - $7a100 = 8 copies of the screen buffer (length $3e800 = 256,000 bytes)
After the enemies have been expanded, a memory dump will contain 8 copies of each enemy, all offset by 2 pixels compared to the previous image. The mask is a single bitplane object that shows which pixels of the image are used, and prevents a black rectangle obscuring the background below it. On the Amiga, this is referred to as cookie-cutting and is almost always done with the blitter.
If you have any idea what should go in this box, please let me know! :)