       
*
* INITSTAR -- Initialize starfield, etc.
*
* Stars have locations x=-160..160 and y=-100..100
*
INITSTAR 
         JSR INITRAND
         LDY #NSTARS
:LOOP    JSR NEWSTAR
         DEY
         BPL :LOOP
         RTS

NEWSTAR                   ;.Y contains index into star table
         JSR GETRAND
         LDA RANDOM+1
:YLOOP   CMP #100
         BCC :SETY
         CMP #156         ;-100
         BCS :SETY
         AND #%10111111   ;-65..63
:SETY    STA STARY,Y

         AND #$7F         ;Just a dorky selector, hope it
         CMP #64
         BCC :POSX        ;works!
         LDA RANDOM
         CMP #96          ;-160
         BCS :OK1
         ORA #$80
:OK1     STA STARXLO,Y
         LDA #$FF
         STA STARXHI,Y
         RTS

:POSX    LDA RANDOM
         CMP #160
         BCC :OK2
         AND #$1F
:OK2     STA STARXLO,Y
         LDA #00
         STA STARXHI,Y
         RTS

*
* PLOTSTAR -- Plot stars into bitmap!
*
PLOTSTAR 
         LDY #NSTARS
:LOOP    STY TEMP
         LDA STARXLO,Y
         CLC
         ADC #160
         STA TEMP1
         AND #$07
         TAX              ;.X = lower bits
         EOR TEMP1
         STA TEMP1        ;temp1 = column offset
         LDA STARXHI,Y
         ADC #00
         STA TEMP2

         LDA STARY,Y
         CLC
         ADC #100
         TAY
:PLOT    
         LDA BROWLO,Y
         STA BPOINT
         LDA BROWHI,Y
         CLC
         ADC BITMAP
         ADC TEMP2
         STA BPOINT+1
         LDY TEMP1
         LDA XBIT,X
         ORA (BPOINT),Y
         STA (BPOINT),Y

         LDY TEMP
         DEY
         BPL :LOOP
         RTS

*
* STARROTP -- Rotate stars about z-axis, positive.
*
STARROTP 
         LDY #NSTARS
:LOOP    LDA STARXLO,Y
         LDX STARXHI,Y
         BMI :NEGX
:POSX    TAX
         LDA STARYREM,Y   ;y*cos(delta)
         SEC
         SBC SINREM,X     ;-x*sin(delta)
         STA STARYREM,Y
         LDA STARY,Y
         SBC SINDEL,X
         LDX STARY,Y
         STA STARY,Y      ;y=-x*sd + y*cd
         BMI :NEGY        ;LDX sets flag

:POSY    LDA STARXREM,Y
         CLC
         ADC SINREM,X     ;x*cos(theta) + y*sin(theta)
         STA STARXREM,Y
         LDA STARXLO,Y
         ADC SINDEL,X
         STA STARXLO,Y
         TAX
         LDA STARXHI,Y
         ADC #00
         STA STARXHI,Y
         BMI :NEGCHK

:POSCHK  BNE :NEW
         CPX #160
         BCS :NEW
:YCHK    LDA STARY,Y
         BMI :NEGYCHK
         CMP #100
         BCS :NEW
         DEY
         BPL :LOOP
         RTS

:NEGYCHK CMP #156         ;-100
         BCS :NOTNEW
:NEW     JSR NEWSTAR
:NOTNEW  DEY
         BPL :LOOP
         RTS

:NEGCHK  CPX #96          ;-160
         SBC #$FF
         BCS :YCHK
         BCC :NEW

:NEGX    EOR #$FF
         TAX
         INX
         LDA STARYREM,Y   ;y*cos(delta)
         CLC
         ADC SINREM,X     ;-x*sin(delta)
         STA STARYREM,Y
         LDA STARY,Y
         ADC SINDEL,X
         LDX STARY,Y
         STA STARY,Y      ;y=-x*sd + y*cd
         BPL :POSY        ;LDX sets flag

:NEGY    TXA
         EOR #$FF
         TAX
         INX
         LDA STARXREM,Y
         SEC
         SBC SINREM,X     ;x*cos(theta) + y*sin(theta)
         STA STARXREM,Y
         LDA STARXLO,Y
         SBC SINDEL,X
         STA STARXLO,Y
         TAX
         LDA STARXHI,Y
         SBC #00
         STA STARXHI,Y
         BPL :POSCHK
         BMI :NEGCHK

*
* STARROTM -- Rotate stars, negative.
*   (sin -> -sin)
*
STARROTM 
         LDY #NSTARS
:LOOP    LDA STARXLO,Y
         LDX STARXHI,Y
         BMI :NEGX
:POSX    TAX
         LDA STARYREM,Y   ;y*cos(delta)
         CLC
         ADC SINREM,X     ;+x*sin(delta)
         STA STARYREM,Y
         LDA STARY,Y
         ADC SINDEL,X
         LDX STARY,Y
         STA STARY,Y      ;y=x*sd + y*cd
         BMI :NEGY        ;LDX sets flag

:POSY    LDA STARXREM,Y
         SEC
         SBC SINREM,X     ;x*cos(theta) - y*sin(theta)
         STA STARXREM,Y
         LDA STARXLO,Y
         SBC SINDEL,X
         STA STARXLO,Y
         TAX
         LDA STARXHI,Y
         SBC #00
         STA STARXHI,Y
         BMI :NEGCHK
:POSCHK  BNE :NEW
         CPX #160
         BCS :NEW
:YCHK    LDA STARY,Y
         BMI :NEGYCHK
         CMP #100
         BCS :NEW
         DEY
         BPL :LOOP
         RTS

:NEGYCHK CMP #156         ;-100
         BCS :NOTNEW
:NEW     JSR NEWSTAR
:NOTNEW  DEY
         BPL :LOOP
         RTS

:NEGCHK  CPX #96
         CMP #$FF
         BCS :YCHK
         BCC :NEW

:NEGX    EOR #$FF
         TAX
         INX
         LDA STARYREM,Y   ;y*cos(delta)
         SEC
         SBC SINREM,X     ;+x*sin(delta)
         STA STARYREM,Y
         LDA STARY,Y
         SBC SINDEL,X
         LDX STARY,Y
         STA STARY,Y      ;y=x*sd + y*cd
         BPL :POSY        ;LDX sets flag

:NEGY    TXA
         EOR #$FF
         TAX
         INX
         LDA STARXREM,Y
         CLC
         ADC SINREM,X     ;x*cos(theta) - y*sin(theta)
         STA STARXREM,Y
         LDA STARXLO,Y
         ADC SINDEL,X
         STA STARXLO,Y
         TAX
         LDA STARXHI,Y
         ADC #00
         STA STARXHI,Y
         BPL :POSCHK
         BMI :NEGCHK

*
* STARADDZ -- Move stars, forwards or backwards.  Idea
*   is that stars move radially outward from the center
*   of the screen, with velocity dependent on the distance
*   from the center of the screen.
*
STARADDZ 
         LDY #NSTARS
:LOOP    
         LDX THETSTEP
         BEQ :RTS
* LDA STARXREM,Y
* STA TEMP1
         LDA STARXHI,Y
         STA TEMP3
         STA TEMP2
         LDA STARXLO,Y
:L1      
* ASL TEMP1
         ASL
         ROL TEMP2
         DEX
         BNE :L1          ;Divide by 128/64/32/16
         CLC
         ADC STARXREM,Y
         STA STARXREM,Y
         LDA TEMP2
         ADC STARXLO,Y    ;x = x + 1/16 x
         STA STARXLO,Y
         TAX
         LDA STARXHI,Y
         ADC TEMP3        ;High byte, 00 or $FF
         STA STARXHI,Y
         BMI :NEGCHK
         BNE :NEW         ;valid high = either 00 or $FF

:POSCHK  CPX #160         ;if x>=160 then need a new star
         BCC :ADDY
:NEW     JSR NEWSTAR
         JMP :NEXT
:NEGCHK  
         CPX #97          ;and if x<=-160
         SBC #$FF         ;(Subtract $FF + 97)
         BCC :NEW

:ADDY    LDX #00          ;Sign
         LDA STARY,Y
         BPL :C1
         DEX
:C1      STX TEMP1
         LDX THETSTEP
:L2      ASL
         ROL TEMP1
         DEX
         BNE :L2
         CLC
         ADC STARYREM,Y
         STA STARYREM,Y
         LDA TEMP1
         ADC STARY,Y
         BVS :NEW
         STA STARY,Y
         BMI :NEGY

:POSY    CMP #100         ;if abs(y)>100 then new
         BCS :NEW
:NEXT    DEY
         BPL :LOOP
:RTS     RTS
:NEGY    CMP #157
         BCC :NEW
         DEY
         BPL :LOOP
         RTS

STARSUBZ                  ;Same thing but subtract
         LDY #NSTARS
:LOOP    
         LDX THETSTEP
         BEQ :RTS
* LDA STARXREM,Y
* STA TEMP1
         LDA STARXHI,Y
         STA TEMP3
         STA TEMP2
         LDA STARXLO,Y
:L1      
* ASL TEMP1
         ASL
         ROL TEMP2
         DEX
         BNE :L1
         STA TEMP
         LDA STARXREM,Y
         SEC
         SBC TEMP
         STA STARXREM,Y
         LDA STARXLO,Y    ;x = x - 1/16 x
         SBC TEMP2
         STA STARXLO,Y
         TAX
         LDA STARXHI,Y
         SBC TEMP3        ;High byte, 00 or $FF
         STA STARXHI,Y
         BMI :NEGCHK
         BNE :NEW         ;valid high = either 00 or $FF

:POSCHK  CPX #16          ;if abs(x)<16 then need a new star
         BCS :ADDY
:NEW     JSR NEWSTAR
         JMP :NEXT
:NEGCHK  CPX #240
         SBC #$FF
         BCS :NEW

:ADDY    LDX #00          ;Sign
         LDA STARY,Y
         BPL :C2
         DEX
:C2      STX TEMP1
         LDX THETSTEP
:L2      ASL
         ROL TEMP1
         DEX
         BNE :L2
         STA TEMP
         LDA STARYREM,Y
         SEC
         SBC TEMP
         STA STARYREM,Y
         LDA STARY,Y
         SBC TEMP1
         BVS :NEW
         STA STARY,Y
         BMI :NEGY

:POSY    CMP #16          ;if abs(y)<6 then new
         BCC :NEW
:NEXT    DEY
         BPL :LOOP
:RTS     RTS
:NEGY    CMP #240
         BCS :NEW
         DEY
         BPL :LOOP
         RTS


*
* STARADDX, STARSUBX, STARADDY, STARSUBY
*   Routines to move stars right/left/up/down to simulate
*   rotations around x and y axis.
*
ADDTAB   DFB 0,12,24,36,48
STARADDX 
         LDY #NSTARS
         LDX THETSTEP
         BEQ :RTS
         LDA ADDTAB,X
         STA TEMP
:LOOP    LDA STARXLO,Y
         CLC
         ADC TEMP
         STA STARXLO,Y
         TAX
         LDA STARXHI,Y
         ADC #00
         STA STARXHI,Y
         BMI :NEXT

:POSCHK  CPX #160         ;if x>=160 then need a new star
         BCC :NEXT
:NEW     JSR NEWSTAR
:NEXT    DEY
         BPL :LOOP
:RTS     RTS

STARSUBX 
         LDY #NSTARS
         LDX THETSTEP
         BEQ :RTS
         LDA ADDTAB,X
         STA TEMP
:LOOP    LDA STARXLO,Y
         SEC
         SBC TEMP
         STA STARXLO,Y
         TAX
         LDA STARXHI,Y
         SBC #00
         STA STARXHI,Y
         BPL :NEXT

:POSCHK  CPX #96          ;if x<-160 then need a new star
         BCS :NEXT
:NEW     JSR NEWSTAR
:NEXT    DEY
         BPL :LOOP
:RTS     RTS


STARADDY 
         LDY #NSTARS
         LDX THETSTEP
         BEQ :RTS
         LDA ADDTAB,X
         STA TEMP
:LOOP    LDA STARY,Y
         CLC
         ADC TEMP
         BVS :NEW         ;might happen for large temp
         STA STARY,Y
         BMI :NEXT
         CMP #100
         BCC :NEXT
:NEW     JSR NEWSTAR
:NEXT    DEY
         BPL :LOOP
:RTS     RTS

STARSUBY 
         LDY #NSTARS
         LDX THETSTEP
         BEQ :RTS
         LDA ADDTAB,X
         STA TEMP
:LOOP    LDA STARY,Y
         SEC
         SBC TEMP
         BVS :NEW
         STA STARY,Y
         BPL :NEXT
         CMP #156
         BCS :NEXT
:NEW     JSR NEWSTAR
:NEXT    DEY
         BPL :LOOP
:RTS     RTS
