smashtv/BAKGND.ASM

789 lines
19 KiB
NASM
Raw Normal View History

2021-04-06 15:09:56 -07:00
.FILE 'BAKGND.ASM'
; SHELL PROGRAM - DO NOT MODIFY!
; MARK TURMELL - MAY 24, 1989
;
.TITLE "BACKGROUND HANDLERS"
**************************************************************************
* *
* COPYRIGHT (C) 1988 WILLIAMS ELECTRONICS GAMES, INC. *
* ALL RIGHTS RESERVED. *
* *
**************************************************************************
.OPTION B,D,L
.MNOLIST
* GET THE SYSTEM STUFF
.INCLUDE "MPROC.EQU" ;MPROC EQUATES
.INCLUDE "DISP.EQU" ;DISPLAY PROCESSOR EQUATES
.INCLUDE "\VIDEO\SYS\GSP.INC" ;GSP ASSEMBLER EQUATES
.INCLUDE "\VIDEO\SYS\SYS.INC" ;ZUNIT SYSTEM EQUATES
.INCLUDE "\VIDEO\SYS\MACROS.HDR" ;MACROS, YEAH!
.INCLUDE "BGNDTBL.GLO" ;BACKGROUND EQUATES
;*BACKGROUND SYSTEM STUFF
.GLOBAL BAKBITS,BAKMODS,BAKLST,BGND_UD1
*GLOBALS IN THIS FILE
*RAM EQUATES
.GLOBL FREEPAL,GETBPAL
.BSS BGNDPALTBL,32,1
.BSS MOD_POS,32,1
.BSS BAKBITS,10000
; .BSS BAK2BITS,1000
.BSS BAKMODS,32
; .BSS BAK2MODS,32
.TEXT
*BACKGROUND UPDATER EQUATES
BLSTSTRT .EQU >8000
BLSTEND .EQU >8001
************* LOCAL CONSTANTS FOR UPD **************
;DISP_PAD .SET >00300030 ; Y:X
DISP_PAD .SET >00000000 ; Y:X
WIDEST_BLOCK .SET 250
;* MUST KEEP THE SIZE OF THESE STRUCTURES A MULTIPLE OF 16
MAP_ZFLAGSPAL .SET 0
MAP_PAL .SET 0 ;SIZE 4 - PALETTE SELECT
MAP_FLAGS .SET 4 ;SIZE 4 - BIT 0 HFLIP, BIT 1 YFLIP
MAP_Z .SET 8 ;SIZE 8
MAP_X .SET 16 ;SIZE 16
MAP_Y .SET 32 ;SIZE 16
MAP_HDR .SET 48 ;SIZE 16 - OFFSET IN LONG WORDS FROM BLOCK_HDR_TBL
; BITS 12-15 ARE BITS 4-7 OF PAL
; MAP_HDR SET TO >FFFF IF BLOCK IS NOT ALLOCATED
BLOCK_SIZE .SET 64 ;* IF CHANGED MUST GET RID OF SHIFTS BY 6
;* Offsets for a BLOCK HDR structure
MAP_SIZE .SET 0
MAP_W .SET 0 ;SIZE 16 ; THESE FIELDS CAN'T BE CHANGED
MAP_H .SET 16 ;SIZE 16 ; BECAUSE THEY ARE USED AS THE
MAP_DATAPTR .SET 32 ;SIZE 32 ;
BLOCK_HDR_SIZE .SET 64
;* OFFSETS FOR A BLOCK HDR STRUCTURE
;MAP_SIZE .SET 0
;MAP_W .SET 0 ;SIZE 16 ; THESE FIELDS CAN'T BE CHANGED
;MAP_H .SET 16 ;SIZE 16 ; BECAUSE THEY ARE USED AS THE
;MAP_ANIMOFF .SET 32 ;SIZE 32 ; OIMG BLOCK HEADER
;MAP_DATAPTR .SET 64 ;SIZE 32 ;
;BLOCK_HDR_SIZE .SET 96
************************************************************************
BGNDHGHT:
;PARMS A0 - XPOS FOR WHICH HEIGHT OF BACKGROUND NEEDS TO BE DETERMINED
;RETURNS A0 -
; MINIMUM YPOS (MAX HEIGHT) OF PRIMARY BACKGROUND WHICH OVERLAPS
; SPECIFIED XPOS
; A0 = 0 IF XPOS IS INVALID
;* SCAN A MODULE LIST TO FIND OUT WHICH MODULE CONTAINS BLOCKS
;* WHICH NEED TO BE CHECKED
MMTM SP,A1,A2,A3,A4,A7,A8,A9,A10,A11
MOVE A0,A1
CLR A10 ;INIT PACKED Y:X STARTING POSITION
CLR A11
MOVE @BAKMODS,A0,L ;* A0- PTR TO THE MODULE LIST
MODLP0:
MOVE *A0+,A8,L ;LOAD MODULE PTR
CMPI >FFFFFFFF,A8
JRZ MODX0 ;END OF THE MODULE TBL
MOVE *A8+,A9,L ;LOAD PACKED Y:X SIZE
MOVE *A0+,A3,W ;X START POSITION
ZEXT A3,W
CMPI BLSTSTRT,A3
JRNZ NOTLSTSTRTX
MOVE A11,A3
SUBXY A9,A3
JRUC GOTNEWX0
NOTLSTSTRTX:
CMPI BLSTEND,A3
JRNZ GOTNEWX0
MOVE A11,A3
GOTNEWX0:
MOVE *A0+,A4,W ;Y START POSITION
ZEXT A4,W
CMPI BLSTSTRT,A4
JRNZ NOTLSTSTRTY
MOVE A11,A4
SUBXY A9,A4
JRUC GOTNEWY0
NOTLSTSTRTY:
CMPI BLSTEND,A4
JRNZ NOTLSTENDY
MOVE A11,A4
JRUC GOTNEWY0
NOTLSTENDY:
SLL 16,A4
GOTNEWY0:
MOVY A4,A3
MOVE A3,A10
; CMPXY A10,A1
; JRV MODX0 ;JUMP TO EXIT LOOP IF MOD START X > X SOUGHT
;IF MOD END X < X SOUGHT KEEP SEARCHING MOD LIST
MOVE A10,A11
ADDXY A9,A11 ;A11 IS MODULE Y:X END
MOVE *A8+,A9,W ;LOAD # OF BLOCKS
ADD A9,A7 ;A7 IS NEW BAKBITS PTR
CMPXY A11,A1
JRNV MODLP0 ;SKIP IF AX < BX
MOVE A10,A0
SRL 16,A0
JRUC GOTHGHT
MODX0:
CLR A0
GOTHGHT:
MMFM SP,A1,A2,A3,A4,A7,A8,A9,A10,A11
RETS
************************************************************************
**************************** BSRCH1STXB ********************************
BSRCH1STXB:
;*** PARMS
; A0 - X COORDINATE OF A BLOCK
; A1 - START OF BACKGROUND BLOCK TABLE
; A2 - END OF BLOCK TABLE
;*** RETURNS
; A0 - ADDRESS OF FIRST BLOCK WITH X COORDINATE >= PARM
; IF NEW X IS HIGHEST RETURNS NEXT EMPTY BLOCK
; IF NO BLOCKS WITH >= X, RETURN 0
;* A0 = X VAL BEING SEARCHED FOR
;* A1 = BLOCK TABLE BASE + OFFSET TO X VAL
;* A14 - THRESHHOLD FOR SWITCHING FROM BINARY TO LINEAR SEARCH
;* A9 = LOW # -- # GREATEST BACKGROUND BLOCK
;* A10 = MID # -- (HIGH + LOW) >> 1
;* A2 = HIGH # -- # OF LOWEST BACKGROUND BLOCK
MMTM SP,A1,A2,A8,A9,A10
CLR A9 ;* SET LOW = 0
SUB A1,A2
SRL 6,A2 ;* DIV BY SIZE OF BLOCK (64)
ADDI MAP_X,A1 ;* BLOCK TBL BASE + X OFFSET
MOVK 5,A14 ;* THRESHHOLD FOR SWITCHING FROM BINARY TO LINEAR SEARCH
BSRCH:
MOVE A2,A10
SUB A9,A10 ;* IF (HIGH - LOW) <= 5 FINISH WITH LINEAR SEARCH
CMP A14,A10
JRLE LSRCH
SRL 1,A10
ADD A9,A10
;* GET MID->X
MOVE A10,A8
SLL 6,A8 ;* MULTIPLY BY BLOCK SIZE (64)
ADD A1,A8
MOVE *A8,A8,W ;* GET X COOR OF THE BLOCK
CMP A0,A8
JRLT BLOW
MOVE A10,A2 ;* HIGH = MID
JRUC BSRCH
BLOW:
MOVE A10,A9 ;* LOW = MID
JRUC BSRCH
LSRCH:
;* FINISH WITH A LINEAR SEARCH OF BLOCK TABLE FROM LOW TO HIGH
;* ENDING WITH FIRST BLOCK X COOR THAT IS >= A0
;* A0 = X VAL BEING SEARCHED FOR
;* A9 = LOW ADDRESS -- PTS TO X OFFSET OF BLOCK
;* A2 = HIGH ADDRESS -- PTS TO X OFFSET OF BLOCK
SLL 6,A9 ;* LOW BLOCK # TO LOW BLOCK OFFSET
SLL 6,A2 ;* HIGH BLOCK # TO HIGH BLOCK OFFSET
ADD A1,A9
ADD A1,A2
MOVI BLOCK_SIZE,A8
LSRCHLP:
MOVE *A9,A10,W ;* X COOR
CMP A0,A10
JRGE GOTB ;* IF LOW->X >= A0 GOTO FOUND
ADD A8,A9
CMP A2,A9
JRLE LSRCHLP
;* BLOCK NOT FOUND, RETURN 0
CLR A0
JRUC BSRCHDONE
GOTB:
;* RETURN A PTR TO THE BLOCK
MOVE A9,A0
SUBI MAP_X,A0
BSRCHDONE:
MMFM SP,A1,A2,A8,A9,A10
RETS
**************************** BSRCH1STXB ********************************
*********************** BAK END *******************************
;* SCAN A MODULE LIST AND RETURN THE PACKED Y:X END POINT
;PARMS
;A0 - MODULE LIST
;RETURNS
;A0 - PACKED Y:X END OF WAVE
BAK_END:
MMTM SP,A3,A4,A8,A9,A10,A11
CLR A10 ;CLR PACKED Y:X STARTING POSITION
CLR A11
WEMODLP:
MOVE *A0+,A8,L ;LOAD MODULE PTR
CMPI >FFFFFFFF,A8
JRZ WEMODX ;END OF THE MODULE TBL
MOVE *A8+,A9,L ;LOAD PACKED Y:X SIZE
MOVE *A0+,A3,W ;X START POSITION
ZEXT A3,W
CMPI BLSTSTRT,A3
JRNZ WENOTLASTSTARTX
MOVE A11,A3
SUBXY A9,A3
JRUC WEGOTNEWX
WENOTLASTSTARTX:
CMPI BLSTEND,A3
JRNZ WEGOTNEWX
MOVE A11,A3
WEGOTNEWX:
MOVE *A0+,A4,W ;Y START POSITION
ZEXT A4,W
CMPI BLSTSTRT,A4
JRNZ WENOTLASTSTARTY
MOVE A11,A4
SUBXY A9,A4
JRUC WEGOTNEWY
WENOTLASTSTARTY:
CMPI BLSTEND,A4
JRNZ WENOTLASTENDY
MOVE A11,A4
JRUC WEGOTNEWY
WENOTLASTENDY:
SLL 16,A4
WEGOTNEWY:
MOVY A4,A3
MOVE A3,A10
MOVE A10,A11
ADDXY A9,A11 ;A11 IS MODULE Y:X END
JRUC WEMODLP
WEMODX:
MOVE A11,A0
MMFM SP,A3,A4,A8,A9,A10,A11
RETS
***********************************************************************
*********************** BAK START *******************************
;* SCAN A MODULE LIST AND RETURN THE PACKED Y:X STARTING POINT
;PARMS
;A0 - MODULE LIST
;RETURNS
;A0 - PACKED Y:X START OF WAVE
BAK_STRT:
MMTM SP,A3,A4,A8,A9,A11
CLR A11
MOVE *A0+,A8,L ;LOAD MODULE PTR
CMPI >FFFFFFFF,A8
JRZ WSMODX ;END OF THE MODULE TBL
MOVE *A8+,A9,L ;LOAD PACKED Y:X SIZE
MOVE *A0+,A3,W ;X START POSITION
ZEXT A3,W
CMPI BLSTSTRT,A3
JRNZ WSNOTLASTSTARTX
MOVE A11,A3
SUBXY A9,A3
JRUC WSGOTNEWX
WSNOTLASTSTARTX:
CMPI BLSTEND,A3
JRNZ WSGOTNEWX
MOVE A11,A3
WSGOTNEWX:
MOVE *A0+,A4,W ;Y START POSITION
ZEXT A4,W
CMPI BLSTSTRT,A4
JRNZ WSNOTLASTSTARTY
MOVE A11,A4
SUBXY A9,A4
JRUC WSGOTNEWY
WSNOTLASTSTARTY:
CMPI BLSTEND,A4
JRNZ WSNOTLASTENDY
MOVE A11,A4
JRUC WSGOTNEWY
WSNOTLASTENDY:
SLL 16,A4
WSGOTNEWY:
MOVY A4,A3
MOVE A3,A0
WSMODX:
MMFM SP,A3,A4,A8,A9,A11
RETS
***********************************************************************
**************** U P D A T E D I S P L I S T **********************
;* DELETES ALL DISPLAY OBJECTS WHICH ARE NOT ON THE SCREEN
;* INSURES ALL BACKGROUND BLOCKS ON SCREEN ARE ON THE DISP LIST
BGND_UD1: ;* CALL TO UPDATE MAIN BACKGROUND
;* INPUT, WORLDTL, SCRNTL, SCRNLR, BAKLST, BAKBITS, BAKMODS
;* THIS PROTECTS DISP_MOD AND DISP_DEL TOO!
MMTM SP,A0,A1,A2,A3,A4,A5,A6,A7,A8,A9,A10,A11,A12,A13,A14
MMTM SP,B0
;* GET COORS OF AREA TO BE PUT ON DISPLAY LIST.
MOVE @WORLDTL,A3,1
MOVE A3,A4
MOVE @SCRNTL,A0,1
ADDXY A0,A3
MOVE @SCRNLR,A0,1
ADDXY A0,A4
MOVI DISP_PAD,A0
SUBXY A0,A3 ;A3 - DISP_TL
ADDXY A0,A4 ;A4 - DISP_LR
MOVI BAKLST,A8 ;A8 - BAKGROUND LIST
CALLR DISP_DEL
;* DETERMINE WHICH MODULE
MOVE @BAKMODS,A0,L ;A0- PTR TO THE MODULE LIST
MOVI INSBOBJ,B0 ;B0 - WHICH INSERT ROUTINE
MOVI BAKBITS,A7 ;A7 - BIT TABLE FOR BLOCK BEING ON DISP LIST
CALLR DISP_MOD
MMFM SP,B0
MMFM SP,A0,A1,A2,A3,A4,A5,A6,A7,A8,A9,A10,A11,A12,A13,A14
RETS
;BGND_UD2: ;* CALL TO UPDATE SECONDARY BACKGROUND
;* INPUT, BAK2TLX, BAK2TLY, SCRNTL, SCRNLR, BAK2LST, BAK2BITS, BAK2MODS
; MMTM SP,A0,A1,A2,A3,A4,A5,A6,A7,A8,A9,A10,A11,A12,A13,A14
; MMTM SP,B0
; ;* GET COORS OF AREA TO BE PUT ON DISPLAY LIST.
; MOVE @BAK2TLX+16,A3,W
; MOVE @BAK2TLY+16,A0,W
; SLL 16,A0
; MOVY A0,A3
; MOVE A3,A4
; MOVE @SCRNTL,A0,L
; ADDXY A0,A3
; MOVE @SCRNLR,A0,L
; ADDXY A0,A4
; MOVI DISP_PAD,A0
; SUBXY A0,A3 ;A3 = DISP_TL
; ADDXY A0,A4 ;A4 = DISP_LR
; MOVI BAK2LST,A8 ;A8 - BAKGROUND LIST
; CALLR DISP_DEL
; MOVI INSB2OBJ,B0 ;B0 - WHICH INSERT ROUTINE
; MOVE @BAK2MODS,A0,L ;* A0- PTR TO THE MODULE LIST
; MOVI BAK2BITS,A7
; CALLR DISP_MOD
; MMFM SP,B0
; MMFM SP,A0,A1,A2,A3,A4,A5,A6,A7,A8,A9,A10,A11,A12,A13,A14
; RETS
***********************************************************************
*********************** D I S P M O D *******************************
;* SCAN A MODULE LIST TO FIND OUT WHICH MODULES CONTAIN BLOCKS
;* WHICH NEED TO BE CHECKED FOR ADDITION TO THE DISPLAY LIST.
; B0 - WHICH INSERT ROUTINE
; A0 - MODULE LIST
; A3 - DISP_TL
; A4 - DISP_LR
; A7 - BAKBITS ;A7 - BIT TABLE FOR BLOCK BEING ON DISP LIST
;PARMS FOR DISP_ADD
; A1 - BACKGROUND BLOCK TABLE
; A2 - END OF BACKGROUND BLOCK TABLE
; A5 - BACKGROUND HDR TABLE
; A9 - MODULE START POSITION Y:X
; A10 - PTR TO PALETTE TABLE FOR NEW BLOCK
; ;PASSED FROM ABOVE
; A3 - DISP_TL
; A4 - DISP_LR
; A6 - WHICH BAKGROUND INSERT ROUTINE PRIMARY|SECONDARY
; A7 - BIT TABLE FOR BLOCK BEING ON DISP LIST
;* CALLER IS RESPONSIBLE FOR PUSHING AND POPPING ALL A-REGISTERS
DISP_MOD:
CLR A9 ;INIT Y:X STARTING POSITION
CLR A11 ;ENDING Y:X POS
MOVE A7,A6 ;A6 WILL POINT TO BAKBITS AFTER MOD
MODLP:
SKDADD:
MOVE A6,A7
MOVE *A0+,A8,L ;LOAD MODULE PTR
CMPI >FFFFFFFF,A8
JRZ MODX ;END OF THE MODULE TBL
MOVE *A8+,A10,L ;LOAD Y:X SIZE
MOVE *A0+,A14,W ;X START POSITION
ZEXT A14,W
CMPI BLSTSTRT,A14
JRNZ NOTLASTSTARTX
MOVE A11,A14
SUBXY A10,A14
JRUC GOTNEWX
NOTLASTSTARTX:
CMPI BLSTEND,A14
JRNZ GOTNEWX
MOVE A11,A14
GOTNEWX:
MOVE *A0+,A5,W ;Y START POSITION
ZEXT A5,W
CMPI BLSTSTRT,A5
JRNZ NOTLASTSTARTY
MOVE A11,A5
SUBXY A10,A5
JRUC GOTNEWY
NOTLASTSTARTY:
CMPI BLSTEND,A5
JRNZ NOTLASTENDY
MOVE A11,A5
JRUC GOTNEWY
NOTLASTENDY:
SLL 16,A5
GOTNEWY:
MOVY A5,A14
MOVE A14,A9
MOVE A9,A11
ADDXY A10,A11 ;A11 IS MODULE Y:X END
MOVE *A8+,A10,W ;LOAD # OF BLOCKS
ADD A10,A6 ;A6 IS NEW BAKBITS PTR
; CMPXY A9,A4
; JRXLE MODX ;JUMP TO EXIT LOOP IF MOD START X > SCREEN END X
CMPXY A3,A11
JRXLT SKDADD ;SKIP IF MOD X END < TL X
JRYLT SKDADD ;SKIP IF MOD Y END < TL Y
CMPXY A9,A4
JRXLT SKDADD ;USE THIS IF MODULES AREN'T SORTED LEFT TO RIGHT
;JUMP TO IF MOD START X > SCREEN END X
JRYLT SKDADD ;SKIP IF MOD Y START > BR Y
MOVE *A8+,A1,L ;A1-BLOCK TABLE
MOVE A10,A2
SLL 6,A2 ;EACH BLOCK IS 4 WORDS LONG
ADD A1,A2 ;A2-BLOCK TABLE END
MOVE *A8+,A5,L ;A5-HDRS
MOVE *A8+,A10,L ;A10-PAL TBL
SUBXY A9,A3
SUBXY A9,A4
CALLR DISP_ADD
ADDXY A9,A3
ADDXY A9,A4
JRUC MODLP
MODX:
RETS
***********************************************************************
*********************** D I S P A D D *******************************
;* THIS FUNCTION ADDS ALL MODULE BLOCKS IN THE GIVEN RANGE OF MODULE
;* RELATIVE COORS TO THE DISPLAY LIST.
;* THE BOUNDRIES ARE INCLUDED IN THE GROUP TO ADD.
DISP_ADD:
;*** PARMS:
; B0 - WHICH BAKGROUND INSERT ROUTINE PRIMARY|SECONDARY
; A5 - BACKGROUND HDR TABLE
; A7 - BIT TABLE FOR BLOCK BEING ON DISP LIST
; A9 - MODULE START POSITION Y:X
; A10 - PTR TO PALETTE TABLE FOR NEW BLOCK
; A1 - BACKGROUND BLOCK TABLE
; A2 - END OF BACKGROUND BLOCK TABLE
; A3 - DISP_TL - RELATIVE TO THE MODULE START POS
; A4 - DISP_LR - "
;*** RETURNS NOTHING
;THRASHES A1,A8,A14
MMTM SP,A0,A6,A7,A11
;* FIND FIRST UNIVERSE BLOCK WITH AN X COOR >= A9
MOVX A3,A0
SEXT A0,W
SUBI WIDEST_BLOCK,A0
;A0 - X COORDINATE OF A BLOCK
;A1 - START OF BACKGROUND BLOCK TABLE
;A2 - END OF BLOCK TABLE
CALLR BSRCH1STXB
;A0 IS NOW THE ADDRESS OF A BLOCK
JRZ DADONE ;* NO BLOCKS WITH GTR XCOOR
MOVI BLOCK_SIZE,A6
MOVE A0,A8
SUB A1,A8 ;* SUBTRACT OFF START OF TABLE
SRL 6,A8 ;* DIVIDE BY BLOCK SIZE (64)
ADD A7,A8 ;* A8 - PTR TO BIT WHICH INDICATES BLOCK ON LIST
SUBK 8,A8 ;* AFTER INC A8, USE MOVB *A8 TO LOAD SIGN BIT
SUB A6,A0 ;SUBTRACT BLOCK SIZE
BSCANLP0:
INC A8
ADD A6,A0 ;* GET NEXT BLOCK
;* CHECK IF THERE ARE NO MORE BGND BLOCKS
CMP A2,A0
JRGE DADONE
;* IF BLOCK ALREADY ON DISPLAY LIST TRY AGAIN
MOVB *A8,A11
JRN BSCANLP0
;* CHECK IF X TO BIG
MOVE *A0(MAP_X),A11,W
CMPXY A3,A11
JRXGE BSCAN1 ;* JUMP IF BLOCKX >= TL X
;* LOAD MAP HEADER
MOVE *A0(MAP_HDR),A14,W
SLL 20,A14 ;* ONLY WANT BOTTOM 12 BITS, TOP 4 ARE PAL BITS
SRL 15,A14 ;* LEAVES B9 << 5 == LONG WORD OFFSET
ADD A5,A14 ;* A14 NOW PTS TO BLOCK HDR
;* CHECK IF RIGHT END OF BLOCK HANGS ONTO SCREEN
MOVE *A14,A1,W ;A1 IS NOW THE WIDTH OF THE BLOCK
ADD A11,A1
CMPXY A3,A1 ;* RIGHT END OF BLOCK DOESN'T HANG ON TO SCREEN
JRXLT BSCANLP0 ;* JUMP IF BLOCK X+W < TL X
;* IF YCOOR TO BIG TRY AGAIN
MOVE *A0(MAP_Y),A1,0
SLL 16,A1
CMPXY A1,A4
JRYLT BSCANLP0 ;* JUMP IF BLOCK Y > BR Y
;* IF YCOOR+HEIGHT TO SMALL TRY AGAIN
MOVE *A14(MAP_H),A11,0
SLL 16,A11
ADD A11,A1
CMPXY A3,A1
JRYLT BSCANLP0 ;* JUMP IF BLOCK Y+H < TL Y
MOVE A0,A7
CALLR ADDBLOCK ;THRASHES A1,A14
JRNC BSCANLP0
JRUC DADONE ;* WAS UNABLE TO ADD BLOCK - NO BLOCKS LEFT
BSCAN1:
DEC A8 ;* BIT PTR FOR BLOCK ON DISP LIST
SUB A6,A0 ;SUBTRACT OFF BLOCK SIZE
BSCANLP1:
INC A8
ADD A6,A0 ;GET NEXT BLOCK
;* CHECK IF THERE ARE NO MORE BGND BLOCKS
CMP A2,A0
JRGE DADONE
;* IF BLOCK ALREADY ON DISPLAY LIST TRY AGAIN
MOVB *A8,A11
JRN BSCANLP1
;* IF YCOOR TO BIG TRY AGAIN
MOVE *A0(MAP_Y),A1,W
SLL 16,A1
CMPXY A1,A4
JRYLT BSCANLP1 ;* JUMP IF BLOCK Y > BR Y
;* IF YCOOR+HEIGHT TO SMALL TRY AGAIN
MOVE *A0(MAP_HDR),A14,W
SLL 20,A14 ;* ONLY WANT BOTTOM 12 BITS, TOP 4 ARE PAL BITS
SRL 15,A14 ;* LEAVES B9 << 5 == LONG WORD OFFSET
ADD A5,A14 ;* B9 NOW PTS TO BLOCK HDR
MOVE *A14(MAP_H),A11,W
SLL 16,A11
ADD A11,A1
CMPXY A3,A1
JRYLT BSCANLP1 ;* JUMP IF BLOCK Y+H < TL Y
;* IF XCOOR TO BIG QUIT
MOVE *A0(MAP_X),A1,W
CMPXY A1,A4
JRXLT DADONE ;* JUMP IF BLOCK X > BR X
MOVE A0,A7
CALLR ADDBLOCK
JRNC BSCANLP1
DADONE:
MMFM SP,A0,A6,A7,A11
RETS
***********************************************************************
***********************************************************************
ADDBLOCK:
;* PARMS
; B0 - WHICH INS ROUTINE
; A5 - BASE OF BACKGROUND BLOCK HDR
; A7 - PTR TO BACKGROUND BLOCK
; A8 - PTR TO BIT MAP FOR BLOCK ON DISP LIST
; A9 - MODULE START POSITION Y:X
; A10 - PTR TO PALETTE TABLE FOR NEW BLOCK
;* RETURNS CARRY SET IF GETOBJ FAILS...
;* ALSO DESTROYS A1,A14 BUT THEY ARE USED AS TEMPS IN DISP_ADD
MMTM SP,A0,A2,A3,A4
CALLA GETOBJ
JRZ ADDX
;* SET BIT IN BITMAP FOR BLOCK ON LIST
MOVB *A8,A14
ORI >80,A14
MOVB A14,*A8
MOVE A8,*A0(OPLINK),L ;SET OPLINK TO BE A PTR TO THE DISP LIST BIT
MOVE *A7(MAP_X),A1,L ;A1 YPOS:XPOS OF BLOCK FROM MOD BASE
ADDXY A9,A1 ;ADD IN MODULE BASE POSITION
MOVE A1,*A0(OXPOS),W
SRL 16,A1
MOVE A1,*A0(OYPOS),W
MOVE *A7,A4,W ;A4 - MAP_Z,8:MAP_FLAGS,4:MAP_PAL,4
MOVE A4,A3
ZEXT A3
SRL 8,A3
** SLL 24,A3
** SRL 8,A3
MOVE A3,*A0(OZPOS),W
MOVE *A7(MAP_HDR),A1,W
MOVX A1,A14
SLL 16,A14
SRL 28,A14
SLL 4,A14 ;* BITS 12-15 ARE BITS 4-7 OF PAL INDEX
SLL 20,A1 ;* BITS 0-11 ARE HDR PTR;
SRL 15,A1 ;* A1-LONG WORD OFFSET INTO BLOCK HDR TBL
ADD A5,A1 ;* A1 - PTR TO OIMG HDR - INPUT TO GSAGOF
;A4 - MAP_Z,8:MAP_FLAGS,4:MAP_PAL,4
MOVE A4,A3
SLL 28,A4 ;* LAST FOUR BITS FOR PAL
SRL 28,A4
ADD A14,A4
SLL 5,A4 ;* A4 IS LWORD PTR FROM PAL TBL
ADD A10,A4 ;* ADD IN PAL TBL
MOVE A0,A2 ;SAVE A0
MOVE *A4,A0,L ;* GET PALETTE
CALLA GETBPAL
JRNZ BSETPAL
CLR A0
BSETPAL:
MOVE A0,*A2(OPAL),W
MOVE A2,A0 ;RESTORE A0
MOVI >8002,A4 ;>8000 DMA GO, 2
SRL 4,A3 ;* REMOVE PALETTE BITS
SLL 30,A3
JRC SKIP0 ;* CARRY BIT IS THE TRANSPARENCY BIT
ADDK 1,A4
SKIP0:
SRL 26,A3 ;* LINE UP FLIP H,V BITS
ADD A3,A4 ;A4 - FLAGS FOR GSAGOF
MOVE A1,*A0(OIMG),L
*A1=DATA BLOCK POINTER
*A4=OBJECT FLAGS
calla BKGSAGOF ;USES ISAG->20 FOR ISAG
; CALLA GSAGOF
*A2=RETURNED WITH NEW OSIZE
*A3=RETURNED WITH NEW SAG
*A4=RETURNED WITH NEW OFFSET:OFLAGS
MOVE A0,A1
ADDI OSIZE+>20,A1
MMTM A1,A2,A3,A4 ;STUFF OSIZE,OSAG,OFFSET,OFLAGS
CALL B0
CLRC
MMFM SP,A0,A2,A3,A4
RETS
ADDX: ;FAILURE TO GET OBJECT
SETC
MMFM SP,A0,A2,A3,A4
RETS
**********************************************************************
************************ D I S P D E L *****************************
;* THIS FUNCTION DELETES ALL OBJS OUTSIDE THE GIVEN RANGE
;* OF COORS FROM THE DISPLAY LIST.
;* THE BOUNDRIES ARE NOT INCLUDED IN THE GROUP TO DELETE.
DISP_DEL:
;*** PARMS:
; A8 - BAK LIST
; A3 - DISP_TL
; A4 - DISP_LR
;*** RETURNS NOTHING
;THRASHES A0,A6,A7,A8,A9 ;ALL OF WHICH ARE PUSHED BY CALLER
DEL_LOOP:
MOVE A8,A9 ; PTR TO PREV IN A9
MOVE *A9,A8,L ; PTR TO NEXT IN A8
JRZ DEL_DONE ; QUIT IF AT END OF LIST
;IF X > XMAX CONTINUE
MOVE *A8(OXPOS),A7,W
CMPXY A7,A4
JRXLT DEL_IT ;* JUMP IF BR X < BLOCK X
;IF Y > YMAX CONTINUE
MOVE *A8(OYPOS),A0,W
SLL 16,A0
CMPXY A0,A4
JRYLT DEL_IT ;* JUMP IF BR Y < BLOCK Y
MOVE *A8(OIMG),A1,L
;IF X+WIDTH < XMIN CONTINUE
MOVE *A1,A6,W ;A6 BLOCK WIDTH
ADD A6,A7
CMPXY A3,A7
JRXLT DEL_IT ;* JUMP IF TL X > BLOCK X+W
;IF Y+HEIGHT < YMIN CONTINUE
MOVE *A1(MAP_H),A7,0 ;A7 BLOCK HEIGHT
SLL 16,A7
ADD A7,A0
CMPXY A3,A0
JRYLT DEL_IT ;* JUMP IF TL Y > BLOCK Y+H
JRUC DEL_LOOP
DEL_IT: ;* DELETE THE OBJ
;* FREE THE PALETTE
MOVE *A8(OPAL),A0,W
JRZ NOFREEP
CALLA FREEPAL
NOFREEP:
;* UNSET THE ON DISPLAY LIST BIT
MOVE *A8(OPLINK),A0,L
MOVB *A0,A7
ANDI >7F,A7
MOVB A7,*A0
MOVE *A8,*A9,L ; PUT NEXT LINK IN PREV OBJ
MOVE @OFREE,A0,L
MOVE A0,*A8,L
MOVE A8,@OFREE,L ; RETURN DELETED BLOCK TO FREE STACK
MOVE A9,A8 ;A1- POINTS TO LAST OBJ
JRUC DEL_LOOP
DEL_DONE:
RETS
.END