Stellar 7 is a first-person tank game, similar in style to the arcade game Battlezone. Written by Damon Slye and published in 1983 for the Apple II and Commodore 64, it features wireframe 3D animation.
The game was successful enough to spawn a couple of sequels, including Arcticfox (written for the Amiga and ported to the Apple II).
There are two different versions of the game floating around. The first is the official release, the second looks like a pre-release evaluation version: the backgrounds and fonts are slightly different, there's no title screen, the first level is set up differently, and in the mission briefing the various units don't zoom into view.
This disassembly is based on the 4am crack of the official release, with one exception: the initial program loader, which was made part of the DOS tracks in the official release, was called "ROCK3" in the early version. It doesn't appear to have changed in any meaningful way, so a disassembly of ROCK3 is included here.
Stellar 7 for the Apple II was published by Penguin Software, and is copyright 1983 Dynamix.
Components (click links for HTML disassembly listing or converted image):
If the player chooses to view the mission briefing, the game loads BRIEF, BRIEF.ST, and BRIEFING, then calls into the briefing code. If the player chooses to start the mission, the game loads PANEL and PLAYGAME, and calls into the game code, which loads OBJ1/LEV1/DYN1.
You can download the project set - all project files and associated binaries (requires SourceGen v1.6 or later).
See Stellar 7 Objects for more details about how objects are defined and manipulated.
See Hacks & Cheats for some ways to modify the game.
The goal is to get to the 7th system, Arcturus, and destroy the tank driven by Gir Draxon.
The player's tank is controlled with the keyboard, a joystick, or an Atari joystick. On the joystick, button 0 fires the cannon, while button 1 engages the cloaking device. The blue meter is shields, the purple meter is fuel; if either empties completely, the game is over.
On each level you have to kill a certain number of units or survive for a certain length of time. Once either condition is met, a Warplink will appear. Bumping into it takes you to the next level. On the 7th level, Arcturus, the boss tank appears instead.
Keyboard movement:
U I O \ | / J K L / | \ M , .
A full tank of fuel has 37,631 units. Each frame this is reduced by 2 units when idling, 3 units when moving in reverse, and 4 units when moving forward. With the cloak active, consumption increases by 40 units per frame. This works out to about 15.5 minutes at 10fps while driving forward, or 1.25 minutes with the cloak enabled. Firing the cannon costs 25 units per shot. Warplinks restore 7680 units (about 20%).
The cloaking device deactivates after 225 frames. Every time you trigger the cloaking device the countdown is reset. There is no way to manually de-cloak before the timer runs out, but it will deactivate if the fuel tank drops below 2048 units. This means that enabling the cloak will drain at least 40*225=9000 units of fuel, or just under a quarter tank.
Full shields have (147*256-1)=37,631 units, although most things in the game operate on the high byte only, so we can treat full shields as 146. Warplinks restore 30. Damage from incoming fire varies by projectile type (see table below).
The play area is a square, 8192 units on a side, that wraps around at the edges. The radar is 28x28, and covers a 7168x7168 area, so about 25% of the arena is off-radar at any given time.
Capabilities for "active" units, from the tables starting at $8591.
Num | Img | Name | Weapon | Shots | Armor | Fwd Spd | Rev Spd | Rot Spd | Score | Notes |
---|---|---|---|---|---|---|---|---|---|---|
0 | (player) | $15 (Thunder Cannon) | 2 | * | 180 | 100 | 2 | - | ||
1 | Sandsled | $0f (Low Laser) | 2 | 1 | 200 | 40 | 1 | 20 | ||
2 | Laser Tank | $10 (Medium Laser) | 1 | 2 | 128 | 64 | 2 | 35 | ||
3 | Hovercraft | $12 (Light Cannon) | 1 | 1 | 192 | 64 | 3 | 20 | ||
4 | Prowler | $12 (Light Cannon) | 1 | 2 | 160 | 80 | 2 | 30 | ||
5 | Heavy Tank | $13 (Medium Cannon) | 2 | 3 | 120 | 60 | 2 | 75 | ||
6 | Stalker | $10 (Medium Laser) | 1 | 2 | 160 | 100 | 3 | 90 | cloaks | |
7 | Gir Draxon | $14 (Heavy Cannon) | 3 | 5 | 200 | 120 | 3 | 2000 | boss; cloaks | |
8 | Laser Battery | $11 (High Laser) | 2 | 2 | - | - | 1 | 25 | ||
9 | Gun Battery | $14 (Heavy Cannon) | 1 | 4 | - | - | 1 | 30 | ||
10 | Pulsar | $10 (Medium Laser) | 3 | 1 | - | - | - | 40 | ||
11 | Skimmer | $12 (Light Cannon) | 1 | 1 | 240 | 100 | 2 | 50 | ||
12 | Stinger | $0f (Low Laser) | 1 | 1 | 320 | 160 | 2 | 60 | ||
13 | Guiser | $00 (bomb) | 0 | 1 | - | - | - | 5 | explodes on contact | |
14 | Seeker | $00 (bomb) | 0 | 1 | 128 | 40 | - | 10 | explodes on contact; levitates |
The forward/reverse speeds are expressed in KPH, as in the mission briefing. Internally the value divided by 4 determines the number of movement units per second in the 8192x8192 arena. Fliers and Seekers don't move backward, so the reverse speed determines the rate at which they climb and dive.
The rotation speed determines how quickly a unit can change its facing, which is divided into 256 angles. Pulsars and Seekers appear to rotate constantly, but still have a notion of "front".
Score is multiplied by the mission number. Pulsars, when first encountered on Rigel (mission 3), will be worth 120 points.
Num | Name | Damage | Speed | TTL | Range |
---|---|---|---|---|---|
13 | Guiser | 32 | - | - | 0 |
14 | Seeker | 32 | - | - | 0 |
15 | Low Laser | 10 | 500 | 18 | 2250 |
16 | Medium Laser | 16 | 500 | 22 | 2750 |
17 | High Laser | 20 | 500 | 28 | 3500 |
18 | Light Cannon | 14 | 380 | 20 | 1900 |
19 | Medium Cannon | 18 | 380 | 24 | 2280 |
20 | Heavy Cannon | 26 | 380 | 28 | 2660 |
21 | Thunder Cannon | * | 420 | 24 | 2520 |
Speed is in KPH (units/second * 4). TTL is the time-to-live, in frames. The range can be determined by multiplying (speed / 4) * TTL, so e.g. the Thunder Cannon has a range of (420/4*24)=2520, which is a bit over 1/4 of the arena. This is of interest because it means that many mobile enemies can be out-ranged, but none of the turrets can. The map wraps around but your vision doesn't, so objects first appear when they are half the arena (4096 units) away.
Damage indicates how much the impact reduces the player's shields. There is no meaningful value for the Thunder Cannon since the player cannot shoot themselves. (One semi-meaningful comparison: 5 shots from the player will kill Gir Draxon, and 5 shots from Gir Draxon will leave the player with just 11% shields remaining.)
All units except the Pulsar have a cooldown that prevents them from firing all of their shots in consecutive frames. To mix things up a bit, there's an 18.75% chance that a unit that is ready to fire will have an additional cooldown of 1-31 frames applied.
Battles take place across seven systems. The types and locations of the initial set of enemy units is pre-determined, but reinforcements are chosen and placed randomly.
Num | Name | KillReq | KillLim | Initial Units | Reinforcements |
---|---|---|---|---|---|
1 | Sol | 5 | 15 | Sandsled, Skimmer, 4xObstacle | Sandsled(35.3%), Hovercraft(47.1%), Skimmer(17.6%) |
2 | Antares | 9 | 18 | 3xLaser Battery, 2xSeeker, 2xObstacle | Sandsled(25.5%), Prowler(39%), Laser Battery(15.7%), Seeker(19.6%) |
3 | Rigel | 11 | 21 | 3xPulsar, Laser Tank, Fuelbay | Laser Tank(40%), Hovercraft(20%), Pulsar(20%), Stinger(20%) |
4 | Deneb | 13 | 24 | Gun Battery, Heavy Tank, 3xGuiser, 3xObstacle | Prowler(39.2%), Heavy Tank(25.5%), Gun Battery(19.6%), Guiser(15.7%) |
5 | Sirius | 15 | 27 | 3xSkimmer, 3xSeeker | Heavy Tank(31.4%), Laser Battery(23.5%), Skimmer(25.5%), Seeker(19.6%) |
6 | Regulus | 17 | 30 | 2xGun Battery, 2xSeeker, 2xGuiser, Stalker, Fuelbay | Stalker(47.1%), Gun Battery(25.5%), Guiser(7.8%), Seeker(19.6%) |
7 | Arcturus | 21 | 33 | 2xPulsar, Stinger, 2xStalker, Guiser, Obstacle | Stalker(35.3%), Pulsar(27.4%), Stinger(29.4%), Guiser(7.8%) |
"KillReq" is the number of kills required to make the Warplink (or, on Arcturus, Gir Draxon) appear. "KillLim" is the number of kills at which new enemies stop spawning.
All levels will spawn a Warplink after 3300 frames (5.5 minutes at 10fps). The Warplink may not appear immediately regardless of trigger: once ready, there is a 6.25% chance per frame of it appearing.
The timing of reinforcement spawning is randomized. Every 16 frames the game checks a table in the DYN# file ($8550) that gives the chance of a new unit appearing when there are N active enemies. For example, LEV1 uses:
spawn_likelihood .bulk $46,$1e,$00,$00,$00,$00,$00,$00,$00
A random number from 0-255 is generated, and if it's >= the table entry then nothing is spawned that frame. So if there are zero enemy units, every 16 frames there's a $46/$100 = 27% of a new unit spawning. If there's only one enemy there's a 12% chance, and if there are two enemies there is no chance of a third unit appearing. Arcturus, which starts with 7 units in the arena, has a limit of 5. The table serves to both limit the number of enemy units and to randomize the pace at which reinforcements appear.
This can factor into your strategy, e.g. Rigel has a limit of 3, and there are three Pulsars near the Fuelbay. If you kill the initial Laser Tank and one Pulsar, you'll face at most one mobile enemy at a time. (Since time is generally not on your side, it's best to kill all 3 Pulsars so you have a target-rich environment.)
Copyright 2020 by Andy McFadden