Elite on the BBC Micro and NES

# Version analysis of Main flight loop (Part 2 of 16)

This code appears in the following versions (click to see it in the source code):

Code variations between these versions are shown below.

```       Name: Main flight loop (Part 2 of 16)
Type: Subroutine
Category: Main loop
Summary: Calculate the alpha and beta angles from the current pitch and
roll of our ship
Deep dive: Program flow of the main game loop
Pitching and rolling

The main flight loop covers most of the flight-specific aspects of Elite. This
section covers the following:

* Calculate the alpha and beta angles from the current pitch and roll

```

Code variation 1 of 6A variation in the comments only

This variation is blank in the Electron version.

```Cassette, Flight, 6502SP, Master Here we take the current rate of pitch and roll, as set by the joystick or
keyboard, and convert them into alpha and beta angles that we can use in the
```
``` matrix functions to rotate space around our ship. The alpha angle covers
roll, while the beta angle covers pitch (there is no yaw in this version of
Elite). The angles are in radians, which allows us to use the small angle
approximation when moving objects in the sky (see the MVEIT routine for more
on this). Also, the signs of the two angles are stored separately, in both
the sign and the flipped sign, as this makes calculations easier.

LDX JSTX               \ Set X to the current rate of roll in JSTX

JSR cntr               \ Apply keyboard damping twice (if enabled) so the roll
JSR cntr               \ rate in X creeps towards the centre by 2

\ The roll rate in JSTX increases if we press ">" (and
\ the RL indicator on the dashboard goes to the right)
\
\ This rolls our ship to the right (clockwise), but we
\ actually implement this by rolling everything else
\ to the left (anti-clockwise), so a positive roll rate
\ in JSTX translates to a negative roll angle alpha

TXA                    \ Set A and Y to the roll rate but with the sign bit
EOR #%10000000         \ flipped (i.e. set them to the sign we want for alpha)
TAY

```

Code variation 2 of 6Minor and very low-impact

Tap on a block to expand it, and tap it again to revert.

```Cassette, Flight, 6502SP, MasterElectron AND #%10000000         \ Extract the flipped sign of the roll rate and store
STA ALP2               \ in ALP2 (so ALP2 contains the sign of the roll angle
\ alpha)
AND #%10000000         \ Extract the flipped sign of the roll rate

JMP P%+11              \ This skips over the following block of bytes, which
\ appear to be unused; it isn't clear what they do

EQUB &A1, &BB          \ These bytes appear to be unused
EQUB &80, &00
EQUB &90, &01
EQUB &D6, &F1

STA ALP2               \ Store the flipped sign of the roll rate in ALP2 (so
\ ALP2 contains the sign of the roll angle alpha)
```
``` STX JSTX               \ Update JSTX with the damped value that's still in X

EOR #%10000000         \ Extract the correct sign of the roll rate and store
STA ALP2+1             \ in ALP2+1 (so ALP2+1 contains the flipped sign of the
\ roll angle alpha)

TYA                    \ Set A to the roll rate but with the sign bit flipped

BPL P%+7               \ If the value of A is positive, skip the following
\ three instructions

EOR #%11111111         \ A is negative, so change the sign of A using two's
CLC                    \ complement so that A is now positive and contains
ADC #1                 \ the absolute value of the roll rate, i.e. |JSTX|

LSR A                  \ Divide the (positive) roll rate in A by 4
LSR A

```

Code variation 3 of 6Other (e.g. bug fix, optimisation)

The cassette has an extra CLC that isn't needed and could be culled.

Tap on a block to expand it, and tap it again to revert.

```Cassette, ElectronFlight, 6502SP, Master CMP #8                 \ If A >= 8, skip the following two instructions
BCS P%+4

LSR A                  \ A < 8, so halve A again

CLC                    \ This instruction has no effect, as we only get here
\ if the C flag is clear (if it is set, we skip this
\ instruction)
CMP #8                 \ If A >= 8, skip the following instruction
BCS P%+3

LSR A                  \ A < 8, so halve A again
```
``` STA ALP1               \ Store A in ALP1, so we now have:
\
\   ALP1 = |JSTX| / 8    if |JSTX| < 32
\
\   ALP1 = |JSTX| / 4    if |JSTX| >= 32
\
\ This means that at lower roll rates, the roll angle is
\ reduced closer to zero than at higher roll rates,
\ which gives us finer control over the ship's roll at
\ lower roll rates
\
\ Because JSTX is in the range -127 to +127, ALP1 is
\ in the range 0 to 31

ORA ALP2               \ Store A in ALPHA, but with the sign set to ALP2 (so
STA ALPHA              \ ALPHA has a different sign to the actual roll rate)

LDX JSTY               \ Set X to the current rate of pitch in JSTY

JSR cntr               \ Apply keyboard damping so the pitch rate in X creeps
\ towards the centre by 1

TXA                    \ Set A and Y to the pitch rate but with the sign bit
EOR #%10000000         \ flipped
TAY

AND #%10000000         \ Extract the flipped sign of the pitch rate into A

STX JSTY               \ Update JSTY with the damped value that's still in X

STA BET2+1             \ Store the flipped sign of the pitch rate in BET2+1

EOR #%10000000         \ Extract the correct sign of the pitch rate and store
STA BET2               \ it in BET2

TYA                    \ Set A to the pitch rate but with the sign bit flipped

BPL P%+4               \ If the value of A is positive, skip the following
\ instruction

EOR #%11111111         \ A is negative, so flip the bits

ADC #4                 \ Add 4 to the (positive) pitch rate, so the maximum
\ value is now up to 131 (rather than 127)

LSR A                  \ Divide the (positive) pitch rate in A by 16
LSR A
LSR A
LSR A

CMP #3                 \ If A >= 3, skip the following instruction
BCS P%+3

LSR A                  \ A < 3, so halve A again

STA BET1               \ Store A in BET1, so we now have:
\
\   BET1 = |JSTY| / 32    if |JSTY| < 48
\
\   BET1 = |JSTY| / 16    if |JSTY| >= 48
\
\ This means that at lower pitch rates, the pitch angle
\ is reduced closer to zero than at higher pitch rates,
\ which gives us finer control over the ship's pitch at
\ lower pitch rates
\
\ Because JSTY is in the range -131 to +131, BET1 is in
\ the range 0 to 8

ORA BET2               \ Store A in BETA, but with the sign set to BET2 (so
STA BETA               \ BETA has the same sign as the actual pitch rate)

```

Code variation 4 of 6Related to an enhanced feature

To use a Bitsik with the enhanced versions, you need to configure it using the "B" option when paused, otherwise it will act like a normal joystick.

This variation is blank in the Cassette and Electron versions.

```Flight, 6502SP, Master LDA BSTK               \ If BSTK = 0 then the Bitstik is not configured, so
```

Code variation 5 of 6Specific to an individual platform

This variation is blank in the Cassette and Electron versions.

Tap on a block to expand it, and tap it again to revert.

```FlightMaster6502SP LDX #3                 \ Call OSBYTE with A = 128 to fetch the 16-bit value
LDA #128               \ from ADC channel 3 (the Bitstik rotation value),
JSR OSBYTE             \ returning the value in (Y X)

TYA                    \ Copy Y to A, so the result is now in (A X)
LDA JOPOS+2            \ Fetch the Bitstik rotation value (high byte) from
\ JOPOS+2, which is constantly updated with the high
\ byte of ADC channel 3 by the interrupt handler IRQ1
LDA KTRAN+10           \ Fetch the Bitstik rotation value (high byte) from the
\ key logger buffer
```

Code variation 6 of 6Related to an enhanced feature

If you configure the enhanced versions to use a Bitstik, then you can change the ship's speed up and down by twisting the stick.

This variation is blank in the Cassette and Electron versions.

```Flight, 6502SP, Master LSR A                  \ Divide A by 4
LSR A

CMP #40                \ If A < 40, skip the following instruction
BCC P%+4

LDA #40                \ Set A = 40, which ensures a maximum speed of 40

STA DELTA              \ Update our speed in DELTA

BNE MA4                \ If the speed we just set is non-zero, then jump to MA4
\ to skip the following, as we don't need to check the
\ keyboard for speed keys, otherwise do check the
\ keyboard (so Bitstik users can still use the keyboard
\ for speed adjustments if they twist the stick to zero)
```