Diff
checker
Testo
Testo
Immagini
Documenti
Excel
Cartelle
Legal
Enterprise
Applicazione per desktop
Prezzi
Accedi
Scarica Diffchecker Desktop
Confronta il testo
Trova la differenza tra due file di testo
Strumenti
Cronologia
Editor live
Nascondi spazi bianchi
Comprimi invariate
Senza a capo
Layout
Diviso
Unificato
Livello di dettaglio
Intelligente
Parola
Carattere
Stili testo
Modifica aspetto
Evidenziazione sintassi
Scegli sintassi
Ignora
Trasforma testo
Vai alla prima modifica
Modifica input
Diffchecker Desktop
Il modo più sicuro per usare Diffchecker. Ottieni l'app Diffchecker Desktop: i tuoi diff non lasciano mai il tuo computer!
Ottieni Desktop
Untitled diff
Creato
8 anni fa
Il diff non scade mai
Eliminare
Esporta
Condividere
Spiegare
13 rimozioni
Linee
Totale
Rimosso
Caratteri
Totale
Rimosso
Per continuare a utilizzare questa funzione, aggiorna a
Diff
checker
Pro
Visualizza prezzi
891 linee
Copia tutti
2 aggiunte
Linee
Totale
Aggiunto
Caratteri
Totale
Aggiunto
Per continuare a utilizzare questa funzione, aggiorna a
Diff
checker
Pro
Visualizza prezzi
892 linee
Copia tutti
Copia
Copiato
Copia
Copiato
;
Modded /VISUAL/SMOKE.ASM
;
Original
;****************************************************************************
;****************************************************************************
;*
;*
;* SMOKE.ASM
;* SMOKE.ASM
;*
;*
;* Smoke effects generator.
;* Smoke effects generator.
;*
;*
;* 29.11.1992 - KJB
;* 29.11.1992 - KJB
;* 08.02.1993 - KJB - "air" smoke effects added.
;* 08.02.1993 - KJB - "air" smoke effects added.
;*
;*
;****************************************************************************
;****************************************************************************
OPTION M510 ;<<<<< MASM v5.10 <<<<<
OPTION M510 ;<<<<< MASM v5.10 <<<<<
PUBLIC MakeSmokeEffect
PUBLIC MakeSmokeEffect
PUBLIC ScanSmoke
PUBLIC ScanSmoke
EXTRN RandX:FAR
EXTRN RandX:FAR
EXTRN CalcGndHeight:FAR
EXTRN CalcGndHeight:FAR
EXTRN DrawSmoke:NEAR
EXTRN DrawSmoke:NEAR
EXTRN LastFrame:WORD
EXTRN LastFrame:WORD
EXTRN DeltaTime:WORD
EXTRN DeltaTime:WORD
;============================================================================
;============================================================================
INCLUDE VISDATA.INC
INCLUDE VISDATA.INC
INCLUDE PALETTES.INC
INCLUDE PALETTES.INC
INCLUDE \LIB8086\USEFUL.INC
INCLUDE \LIB8086\USEFUL.INC
;============================================================================
;============================================================================
DATA SEGMENT PARA PUBLIC 'DATA'
DATA SEGMENT PARA PUBLIC 'DATA'
NextSmokePtr DW OFFSET SmokeBuffer
NextSmokePtr DW OFFSET SmokeBuffer
TMP_SMOKE SMOKE <>
TMP_SMOKE SMOKE <>
;* init smoke effect switch
;* init smoke effect switch
InitSmoke DW InitCrater1 ;SMOKE_CRATER1
InitSmoke DW InitCrater1 ;SMOKE_CRATER1
DW InitCrater2 ;SMOKE_CRATER2
DW InitCrater2 ;SMOKE_CRATER2
DW InitCrater3 ;SMOKE_CRATER3
DW InitCrater3 ;SMOKE_CRATER3
DW InitBurning ;SMOKE_BURNING
DW InitBurning ;SMOKE_BURNING
DW InitKickUp ;SMOKE_KICK_UP
DW InitKickUp ;SMOKE_KICK_UP
DW InitAirExplo ;SMOKE_AIR_EXPLO
DW InitAirExplo ;SMOKE_AIR_EXPLO
DW InitAirTrail ;SMOKE_AIR_TRAIL
DW InitAirTrail ;SMOKE_AIR_TRAIL
;* control smoke switch
;* control smoke switch
CtrlSmoke DW CtrlNull ;STYPE_NULL
CtrlSmoke DW CtrlNull ;STYPE_NULL
DW CtrlGnd1 ;STYPE_GND1
DW CtrlGnd1 ;STYPE_GND1
DW CtrlAir1 ;STYPE_AIR1
DW CtrlAir1 ;STYPE_AIR1
DATA ENDS
DATA ENDS
;============================================================================
;============================================================================
SMOKEDATA SEGMENT PARA PUBLIC 'DATA'
SMOKEDATA SEGMENT PARA PUBLIC 'DATA'
;* cyclic buffer for smoke
;* cyclic buffer for smoke
SmokeBuffer LABEL SMOKE
SmokeBuffer LABEL SMOKE
SMOKE NUM_SMOKE DUP(<>)
SMOKE NUM_SMOKE DUP(<>)
SmokeBufEnd LABEL SMOKE
SmokeBufEnd LABEL SMOKE
SMOKEDATA ENDS
SMOKEDATA ENDS
;============================================================================
;============================================================================
VISCODE SEGMENT BYTE PUBLIC 'CODE'
VISCODE SEGMENT BYTE PUBLIC 'CODE'
ASSUME CS:VISCODE
ASSUME CS:VISCODE
ASSUME DS:DATA
ASSUME DS:DATA
;* MakeSmokeEffect
;* MakeSmokeEffect
;*
;*
;* pass: bx = smoke effect type (see VISDATA.INC)
;* pass: bx = smoke effect type (see VISDATA.INC)
;* si -> VIEWPOINT data block
;* si -> VIEWPOINT data block
;* ret : nothing
;* ret : nothing
;* kill: assume all
;* kill: assume all
MakeSmokeEffect PROC FAR
MakeSmokeEffect PROC FAR
;-----------------------
;-----------------------
;* copy viewpoint origin
;* copy viewpoint origin
;-----------------------
;-----------------------
mov ax,[si].VP_XSEC
mov ax,[si].VP_XSEC
mov TMP_SMOKE.SMOKE_XSEC,ax
mov TMP_SMOKE.SMOKE_XSEC,ax
mov ax,[si].VP_YSEC
mov ax,[si].VP_YSEC
mov TMP_SMOKE.SMOKE_YSEC,ax
mov TMP_SMOKE.SMOKE_YSEC,ax
mov ax,[si].VP_XFT
mov ax,[si].VP_XFT
mov TMP_SMOKE.SMOKE_XFT,ax
mov TMP_SMOKE.SMOKE_XFT,ax
mov ax,[si].VP_YFT
mov ax,[si].VP_YFT
mov TMP_SMOKE.SMOKE_YFT,ax
mov TMP_SMOKE.SMOKE_YFT,ax
mov ax,WORD PTR [si].VP_ZFT_LO
mov ax,WORD PTR [si].VP_ZFT_LO
mov WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax
mov WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax
mov ax,WORD PTR [si].VP_ZFT_HI
mov ax,WORD PTR [si].VP_ZFT_HI
mov WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,ax
mov WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,ax
;-------------------
;-------------------
;* init smoke effect
;* init smoke effect
;-------------------
;-------------------
call InitSmoke[bx]
call InitSmoke[bx]
ret
ret
MakeSmokeEffect ENDP
MakeSmokeEffect ENDP
;----------------------------------------------------------------------------
;----------------------------------------------------------------------------
;* MakeSingleSmoke
;* MakeSingleSmoke
;*
;*
;* pass: NextSmokePtr
;* pass: NextSmokePtr
;* TMP_SMOKE data block
;* TMP_SMOKE data block
;* ret : NextSmokePtr
;* ret : NextSmokePtr
;* kill: assume all
;* kill: assume all
MakeSingleSmoke PROC NEAR
MakeSingleSmoke PROC NEAR
mov ax,SMOKEDATA
mov ax,SMOKEDATA
mov es,ax
mov es,ax
mov si,OFFSET TMP_SMOKE
mov si,OFFSET TMP_SMOKE
mov di,NextSmokePtr
mov di,NextSmokePtr
mov cx,SMOKE_REC_SIZE
mov cx,SMOKE_REC_SIZE
FAST_MOVE
FAST_MOVE
mov ax,DATA
mov ax,DATA
mov es,ax
mov es,ax
cmp di,OFFSET SmokeBufEnd ;end of buffer?
cmp di,OFFSET SmokeBufEnd ;end of buffer?
jb @F ;no ->
jb @F ;no ->
mov di,OFFSET SmokeBuffer ;wrap around
mov di,OFFSET SmokeBuffer ;wrap around
@@: mov NextSmokePtr,di
@@: mov NextSmokePtr,di
ret
ret
MakeSingleSmoke ENDP
MakeSingleSmoke ENDP
;----------------------------------------------------------------------------
;----------------------------------------------------------------------------
;* RND_SMOKE_COL - set random smoke colour
;* RND_SMOKE_COL - set random smoke colour
;*
;*
;* pass: nothing
;* pass: nothing
;* ret : TMP_SMOKE.SMOKE_COL
;* ret : TMP_SMOKE.SMOKE_COL
;* kill: ax, flags
;* kill: ax, flags
RND_SMOKE_COL MACRO
RND_SMOKE_COL MACRO
call RandX
call RandX
and al,1
and al,1
add al,COL_SMOKE_GREY1
add al,COL_SMOKE_GREY1
mov TMP_SMOKE.SMOKE_COL,al
mov TMP_SMOKE.SMOKE_COL,al
ENDM
ENDM
;----------------------------------------------------------------------------
;----------------------------------------------------------------------------
;* InitGnd1 - init ground smoke type 1 effects
;* InitGnd1 - init ground smoke type 1 effects
;*
;*
;* InitCrater1 - init smoke for SMOKE_CRATER1 effect
;* InitCrater1 - init smoke for SMOKE_CRATER1 effect
;* InitCrater2 - init smoke for SMOKE_CRATER2 effect
;* InitCrater2 - init smoke for SMOKE_CRATER2 effect
;* InitCrater3 - init smoke for SMOKE_CRATER3 effect
;* InitCrater3 - init smoke for SMOKE_CRATER3 effect
;* InitBurning - init smoke for SMOKE_BURNING effect
;* InitBurning - init smoke for SMOKE_BURNING effect
;* InitKickUp - init smoke for SMOKE_KICK_UP effect
;* InitKickUp - init smoke for SMOKE_KICK_UP effect
;*
;*
;* pass: si -> VIEWPOINT data block
;* pass: si -> VIEWPOINT data block
;* TMP_SMOKE
;* TMP_SMOKE
;* ret : TMP_SMOKE
;* ret : TMP_SMOKE
;* kill: assume all
;* kill: assume all
;---------------------------
;---------------------------
InitCrater1 LABEL NEAR
InitCrater1 LABEL NEAR
;---------------------------
;---------------------------
mov TMP_SMOKE.SMOKE_SIB_CNTR,0
mov TMP_SMOKE.SMOKE_SIB_CNTR,0
mov cx,1 ;number of additional smokes
mov cx,1 ;number of additional smokes
jmp InitGnd1
jmp InitGnd1
;---------------------------
;---------------------------
InitCrater2 LABEL NEAR
InitCrater2 LABEL NEAR
;---------------------------
;---------------------------
mov TMP_SMOKE.SMOKE_SIB_CNTR,0
mov TMP_SMOKE.SMOKE_SIB_CNTR,0
mov cx,3 ;number of additional smokes
mov cx,3 ;number of additional smokes
jmp InitGnd1
jmp InitGnd1
;---------------------------
;---------------------------
InitCrater3 LABEL NEAR
InitCrater3 LABEL NEAR
;---------------------------
;---------------------------
mov TMP_SMOKE.SMOKE_SIB_CNTR,0
mov TMP_SMOKE.SMOKE_SIB_CNTR,0
mov cx,7 ;number of additional smokes
mov cx,7 ;number of additional smokes
jmp InitGnd1
jmp InitGnd1
;---------------------------
;---------------------------
InitBurning LABEL NEAR
InitBurning LABEL NEAR
;---------------------------
;---------------------------
mov TMP_SMOKE.SMOKE_SIB_CNTR,10
mov TMP_SMOKE.SMOKE_SIB_CNTR,10
mov cx,9 ;number of additional smokes
mov cx,9 ;number of additional smokes
jmp InitGnd1
jmp InitGnd1
;---------------------------
;---------------------------
InitKickUp LABEL NEAR
InitKickUp LABEL NEAR
;---------------------------
;---------------------------
mov TMP_SMOKE.SMOKE_SIB_CNTR,0
mov TMP_SMOKE.SMOKE_SIB_CNTR,0
mov cx,3 ;number of additional smokes
mov cx,3 ;number of additional smokes
;---------------------------
;---------------------------
InitGnd1 PROC NEAR
InitGnd1 PROC NEAR
;---------------------------
;---------------------------
;------------------
;------------------
;* init first smoke (always at viewpoint datum)
;* init first smoke (always at viewpoint datum)
;------------------
;------------------
mov TMP_SMOKE.SMOKE_TYPE,STYPE_GND1
mov TMP_SMOKE.SMOKE_TYPE,STYPE_GND1
RND_SMOKE_COL
RND_SMOKE_COL
mov TMP_SMOKE.SMOKE_FLAGS,0
mov TMP_SMOKE.SMOKE_FLAGS,0
mov TMP_SMOKE.SMOKE_ZFINE,0
mov TMP_SMOKE.SMOKE_ZFINE,0
mov TMP_SMOKE.SMOKE_RFT,0
mov TMP_SMOKE.SMOKE_RFT,0
mov TMP_SMOKE.SMOKE_TIME,0
mov TMP_SMOKE.SMOKE_TIME,0
call RandX
call RandX
Copia
Copiato
Copia
Copiato
add ax,
8 ;
128
add ax,
128
mov TMP_SMOKE.SMOKE_EXP_TIME,ax
mov TMP_SMOKE.SMOKE_EXP_TIME,ax
push cx
push cx
push si
push si
call MakeSingleSmoke
call MakeSingleSmoke
pop si
pop si
pop cx
pop cx
;------------------------
;------------------------
;* init additional smokes
;* init additional smokes
;------------------------
;------------------------
jcxz InitGnd1Exit ;no additional smokes ->
jcxz InitGnd1Exit ;no additional smokes ->
AddSmokeLoop: push cx
AddSmokeLoop: push cx
RND_SMOKE_COL
RND_SMOKE_COL
call RandX
call RandX
Copia
Copiato
Copia
Copiato
add ax,
8;
128
add ax,
128
mov TMP_SMOKE.SMOKE_EXP_TIME,ax
mov TMP_SMOKE.SMOKE_EXP_TIME,ax
;* offset xft from origin (keep within sector)
;* offset xft from origin (keep within sector)
call RandX
call RandX
cbw
cbw
sar ax,1 ;-64ft .. +63ft offset
sar ax,1 ;-64ft .. +63ft offset
add ax,[si].VP_XFT
add ax,[si].VP_XFT
cmp ax,8191
cmp ax,8191
jle @F
jle @F
mov ax,8191
mov ax,8191
@@: cmp ax,-8192
@@: cmp ax,-8192
jge @F
jge @F
mov ax,-8192
mov ax,-8192
@@: mov TMP_SMOKE.SMOKE_XFT,ax
@@: mov TMP_SMOKE.SMOKE_XFT,ax
;* offset yft from origin (keep within sector)
;* offset yft from origin (keep within sector)
call RandX
call RandX
cbw
cbw
sar ax,1 ;-64ft .. +63ft offset
sar ax,1 ;-64ft .. +63ft offset
add ax,[si].VP_YFT
add ax,[si].VP_YFT
cmp ax,8191
cmp ax,8191
jle @F
jle @F
mov ax,8191
mov ax,8191
@@: cmp ax,-8192
@@: cmp ax,-8192
jge @F
jge @F
mov ax,-8192
mov ax,-8192
@@: mov TMP_SMOKE.SMOKE_YFT,ax
@@: mov TMP_SMOKE.SMOKE_YFT,ax
push si
push si
call MakeSingleSmoke
call MakeSingleSmoke
pop si
pop si
pop cx
pop cx
loop AddSmokeLoop
loop AddSmokeLoop
InitGnd1Exit: ret
InitGnd1Exit: ret
InitGnd1 ENDP
InitGnd1 ENDP
;----------------------------------------------------------------------------
;----------------------------------------------------------------------------
;* InitAir1 - init air smoke type 1 effects
;* InitAir1 - init air smoke type 1 effects
;*
;*
;* InitAirExplo - init smoke for SMOKE_AIR_EXPLO effect
;* InitAirExplo - init smoke for SMOKE_AIR_EXPLO effect
;* InitAirTrail - init smoke for SMOKE_AIR_TRAIL effect
;* InitAirTrail - init smoke for SMOKE_AIR_TRAIL effect
;*
;*
;* pass: si -> VIEWPOINT data block
;* pass: si -> VIEWPOINT data block
;* TMP_SMOKE
;* TMP_SMOKE
;* ret : TMP_SMOKE
;* ret : TMP_SMOKE
;* kill: assume all
;* kill: assume all
;---------------------------
;---------------------------
InitAirExplo LABEL NEAR
InitAirExplo LABEL NEAR
;---------------------------
;---------------------------
mov cx,15 ;number of additional smokes
mov cx,15 ;number of additional smokes
jmp InitAir1
jmp InitAir1
;---------------------------
;---------------------------
InitAirTrail LABEL NEAR
InitAirTrail LABEL NEAR
;---------------------------
;---------------------------
mov cx,3 ;number of additional smokes
mov cx,3 ;number of additional smokes
;---------------------------
;---------------------------
InitAir1 PROC NEAR
InitAir1 PROC NEAR
;---------------------------
;---------------------------
push cx
push cx
push si
push si
call CalcGndHeight
call CalcGndHeight
pop si
pop si
pop cx
pop cx
mov bp,ax ;bp = ground height
mov bp,ax ;bp = ground height
;------------------
;------------------
;* init first smoke (always at viewpoint datum)
;* init first smoke (always at viewpoint datum)
;------------------
;------------------
mov TMP_SMOKE.SMOKE_TYPE,STYPE_AIR1
mov TMP_SMOKE.SMOKE_TYPE,STYPE_AIR1
RND_SMOKE_COL
RND_SMOKE_COL
mov TMP_SMOKE.SMOKE_FLAGS,0
mov TMP_SMOKE.SMOKE_FLAGS,0
mov TMP_SMOKE.SMOKE_ZFINE,0
mov TMP_SMOKE.SMOKE_ZFINE,0
mov TMP_SMOKE.SMOKE_RFT,0
mov TMP_SMOKE.SMOKE_RFT,0
mov TMP_SMOKE.SMOKE_TIME,0
mov TMP_SMOKE.SMOKE_TIME,0
mov TMP_SMOKE.SMOKE_SIB_CNTR,0
mov TMP_SMOKE.SMOKE_SIB_CNTR,0
call RandX
call RandX
Copia
Copiato
Copia
Copiato
add ax,
8;
128
add ax,
128
mov TMP_SMOKE.SMOKE_EXP_TIME,ax
mov TMP_SMOKE.SMOKE_EXP_TIME,ax
call CheckAirPos
call CheckAirPos
push cx
push cx
push si
push si
push bp
push bp
call MakeSingleSmoke
call MakeSingleSmoke
pop bp
pop bp
pop si
pop si
pop cx
pop cx
;------------------------
;------------------------
;* init additional smokes
;* init additional smokes
;------------------------
;------------------------
jcxz InitAir1Exit ;no additional smokes ->
jcxz InitAir1Exit ;no additional smokes ->
AirSmokeLoop: push cx
AirSmokeLoop: push cx
RND_SMOKE_COL
RND_SMOKE_COL
call RandX
call RandX
Copia
Copiato
Copia
Copiato
add ax,
8;
128
add ax,
128
mov TMP_SMOKE.SMOKE_EXP_TIME,ax
mov TMP_SMOKE.SMOKE_EXP_TIME,ax
;* offset xft from origin (keep within sector)
;* offset xft from origin (keep within sector)
call RandX
call RandX
cbw
cbw
sar ax,1 ;-64ft .. +63ft offset
sar ax,1 ;-64ft .. +63ft offset
add ax,[si].VP_XFT
add ax,[si].VP_XFT
cmp ax,8191
cmp ax,8191
jle @F
jle @F
mov ax,8191
mov ax,8191
@@: cmp ax,-8192
@@: cmp ax,-8192
jge @F
jge @F
mov ax,-8192
mov ax,-8192
@@: mov TMP_SMOKE.SMOKE_XFT,ax
@@: mov TMP_SMOKE.SMOKE_XFT,ax
;* offset yft from origin (keep within sector)
;* offset yft from origin (keep within sector)
call RandX
call RandX
cbw
cbw
sar ax,1 ;-64ft .. +63ft offset
sar ax,1 ;-64ft .. +63ft offset
add ax,[si].VP_YFT
add ax,[si].VP_YFT
cmp ax,8191
cmp ax,8191
jle @F
jle @F
mov ax,8191
mov ax,8191
@@: cmp ax,-8192
@@: cmp ax,-8192
jge @F
jge @F
mov ax,-8192
mov ax,-8192
@@: mov TMP_SMOKE.SMOKE_YFT,ax
@@: mov TMP_SMOKE.SMOKE_YFT,ax
;* offset zft from origin
;* offset zft from origin
call RandX
call RandX
cbw
cbw
sar ax,1 ;-64ft .. +63ft offset
sar ax,1 ;-64ft .. +63ft offset
cwd
cwd
add ax,WORD PTR [si].VP_ZFT_LO
add ax,WORD PTR [si].VP_ZFT_LO
adc dx,WORD PTR [si].VP_ZFT_HI
adc dx,WORD PTR [si].VP_ZFT_HI
jns @F
jns @F
xor ax,ax
xor ax,ax
xor dx,dx
xor dx,dx
@@: mov WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax
@@: mov WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax
mov WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,dx
mov WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,dx
call CheckAirPos
call CheckAirPos
push si
push si
push bp
push bp
call MakeSingleSmoke
call MakeSingleSmoke
pop bp
pop bp
pop si
pop si
pop cx
pop cx
loop AirSmokeLoop
loop AirSmokeLoop
InitAir1Exit: ret
InitAir1Exit: ret
InitAir1 ENDP
InitAir1 ENDP
;----------------------------------------------------------------------------
;----------------------------------------------------------------------------
;* CheckAirPos - check air smoke does not penetrate ground
;* CheckAirPos - check air smoke does not penetrate ground
;*
;*
;* pass: TMP_SMOKE
;* pass: TMP_SMOKE
;* bp = ground height
;* bp = ground height
;* ret : TMP_SMOKE
;* ret : TMP_SMOKE
;* kill: ax, dx, flags
;* kill: ax, dx, flags
CheckAirPos PROC NEAR
CheckAirPos PROC NEAR
;* if zft < 65536 then
;* if zft < 65536 then
;*
;*
;* zdiff = zft - ground height
;* zdiff = zft - ground height
;*
;*
;* if zdiff < 0 then
;* if zdiff < 0 then
;* zft = ground height + 32
;* zft = ground height + 32
;* expand time = 128
;* expand time = 128
;* else
;* else
;* if zdiff < expand time / 4 then
;* if zdiff < expand time / 4 then
;* expand time = zdiff * 4
;* expand time = zdiff * 4
;* if expand time < 128 then
;* if expand time < 128 then
;* zft = ground height + 32
;* zft = ground height + 32
;* expand time = 128
;* expand time = 128
;* endif
;* endif
;* endif
;* endif
;* endif
;* endif
;* endif
;* endif
cmp WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0
cmp WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0
ja ExitAirPos
ja ExitAirPos
mov ax,WORD PTR TMP_SMOKE.SMOKE_ZFT_LO
mov ax,WORD PTR TMP_SMOKE.SMOKE_ZFT_LO
sub ax,bp
sub ax,bp
jb SetMinSize
jb SetMinSize
mov dx,TMP_SMOKE.SMOKE_EXP_TIME
mov dx,TMP_SMOKE.SMOKE_EXP_TIME
REPT 2
REPT 2
shr dx,1
shr dx,1
ENDM
ENDM
cmp ax,dx
cmp ax,dx
jae ExitAirPos
jae ExitAirPos
REPT 2
REPT 2
shl ax,1
shl ax,1
ENDM
ENDM
Copia
Copiato
Copia
Copiato
cmp ax,
8;
128
cmp ax,
128
jae @F
jae @F
SetMinSize: mov ax,bp
SetMinSize: mov ax,bp
Copia
Copiato
Copia
Copiato
add ax,
8;
32
add ax,
32
mov WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax
mov WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax
Copia
Copiato
Copia
Copiato
mov ax,
8;
128
mov ax,
128
@@: mov TMP_SMOKE.SMOKE_EXP_TIME,ax
@@: mov TMP_SMOKE.SMOKE_EXP_TIME,ax
ExitAirPos: ret
ExitAirPos: ret
CheckAirPos ENDP
CheckAirPos ENDP
;----------------------------------------------------------------------------
;----------------------------------------------------------------------------
;* ScanSmoke - scan smoke buffer and draw smoke
;* ScanSmoke - scan smoke buffer and draw smoke
;*
;*
;* pass: nothing
;* pass: nothing
;* ret : nothing
;* ret : nothing
;* kill: assume all
;* kill: assume all
;*
;*
;* note: Smoke circles are low priority objects and could possibly clog the
;* note: Smoke circles are low priority objects and could possibly clog the
;* object buffer. Therefore call this routine "later on" in the visual
;* object buffer. Therefore call this routine "later on" in the visual
;* drawing order.
;* drawing order.
ScanSmoke PROC NEAR
ScanSmoke PROC NEAR
;-----------
;-----------
;* scan loop
;* scan loop
;-----------
;-----------
mov cx,NUM_SMOKE
mov cx,NUM_SMOKE
mov si,OFFSET SmokeBuffer
mov si,OFFSET SmokeBuffer
mov ax,SMOKEDATA
mov ax,SMOKEDATA
mov ds,ax
mov ds,ax
SmokeLoop: cmp [si].SMOKE_TYPE,STYPE_NULL ;smoke active?
SmokeLoop: cmp [si].SMOKE_TYPE,STYPE_NULL ;smoke active?
jne SortSmoke ;yes ->
jne SortSmoke ;yes ->
NextSmoke: add si,SMOKE_REC_SIZE
NextSmoke: add si,SMOKE_REC_SIZE
loop SmokeLoop
loop SmokeLoop
mov ax,DATA
mov ax,DATA
mov ds,ax
mov ds,ax
ret
ret
;-----------------------------------
;-----------------------------------
;* copy smoke data into working copy
;* copy smoke data into working copy
;-----------------------------------
;-----------------------------------
SortSmoke: push cx ;store loop count
SortSmoke: push cx ;store loop count
push si ;store smoke ptr
push si ;store smoke ptr
mov di,OFFSET TMP_SMOKE
mov di,OFFSET TMP_SMOKE
mov cx,SMOKE_REC_SIZE
mov cx,SMOKE_REC_SIZE
FAST_MOVE
FAST_MOVE
mov ax,DATA
mov ax,DATA
mov ds,ax
mov ds,ax
;--------------
;--------------
;* update smoke
;* update smoke
;--------------
;--------------
mov bx,TMP_SMOKE.SMOKE_TYPE
mov bx,TMP_SMOKE.SMOKE_TYPE
call CtrlSmoke[bx]
call CtrlSmoke[bx]
jc @F ;smoke cleared ->
jc @F ;smoke cleared ->
;------------
;------------
;* draw smoke
;* draw smoke
;------------
;------------
mov si,OFFSET TMP_SMOKE
mov si,OFFSET TMP_SMOKE
call DrawSmoke
call DrawSmoke
;-----------------------------------
;-----------------------------------
;* copy smoke data from working copy
;* copy smoke data from working copy
;-----------------------------------
;-----------------------------------
@@: pop di ;smoke ptr
@@: pop di ;smoke ptr
push di
push di
mov cx,SMOKE_REC_SIZE
mov cx,SMOKE_REC_SIZE
mov si,OFFSET TMP_SMOKE
mov si,OFFSET TMP_SMOKE
mov ax,SMOKEDATA
mov ax,SMOKEDATA
mov es,ax
mov es,ax
FAST_MOVE
FAST_MOVE
mov ax,DATA
mov ax,DATA
mov es,ax
mov es,ax
;-------------------------------
;-------------------------------
;* prepare to re-enter scan loop
;* prepare to re-enter scan loop
;-------------------------------
;-------------------------------
mov ax,SMOKEDATA
mov ax,SMOKEDATA
mov ds,ax
mov ds,ax
pop si ;restore smoke ptr
pop si ;restore smoke ptr
pop cx ;restore loop count
pop cx ;restore loop count
jmp NextSmoke
jmp NextSmoke
ScanSmoke ENDP
ScanSmoke ENDP
;----------------------------------------------------------------------------
;----------------------------------------------------------------------------
;* CtrlNull
;* CtrlNull
;*
;*
;* pass: nothing
;* pass: nothing
;* ret : cf = 1 = smoke cleared
;* ret : cf = 1 = smoke cleared
;* kill: nothing
;* kill: nothing
CtrlNull PROC NEAR
CtrlNull PROC NEAR
stc
stc
ret
ret
CtrlNull ENDP
CtrlNull ENDP
;----------------------------------------------------------------------------
;----------------------------------------------------------------------------
;* CtrlGnd1 - control routine for ground smoke type 1
;* CtrlGnd1 - control routine for ground smoke type 1
;*
;*
;* pass: TMP_SMOKE
;* pass: TMP_SMOKE
;* ret : TMP_SMOKE
;* ret : TMP_SMOKE
;* cf = 0 = smoke ok
;* cf = 0 = smoke ok
;* cf = 1 = smoke cleared
;* cf = 1 = smoke cleared
;* kill: assume all (except cf)
;* kill: assume all (except cf)
;*
;*
;* note: Phase 1: Expand radius keeping base of smoke on crater base.
;* note: Phase 1: Expand radius keeping base of smoke on crater base.
;* Phase 2: Contract radius and drift upwards until radius is zero.
;* Phase 2: Contract radius and drift upwards until radius is zero.
CtrlGnd1 PROC NEAR
CtrlGnd1 PROC NEAR
;--------------
;--------------
;* update timer
;* update timer
;--------------
;--------------
mov ax,TMP_SMOKE.SMOKE_TIME
mov ax,TMP_SMOKE.SMOKE_TIME
add ax,LastFrame
add ax,LastFrame
mov TMP_SMOKE.SMOKE_TIME,ax
mov TMP_SMOKE.SMOKE_TIME,ax
;------------
;------------
;* sort phase
;* sort phase
;------------
;------------
mov dx,TMP_SMOKE.SMOKE_EXP_TIME
mov dx,TMP_SMOKE.SMOKE_EXP_TIME
cmp ax,dx ;expand phase?
cmp ax,dx ;expand phase?
jbe Gnd1Phase1 ;yes ->
jbe Gnd1Phase1 ;yes ->
sub ax,dx
sub ax,dx
shl dx,1 ;contract phase is double expand phase
shl dx,1 ;contract phase is double expand phase
cmp ax,dx ;contract phase?
cmp ax,dx ;contract phase?
jbe Gnd1Phase2 ;yes ->
jbe Gnd1Phase2 ;yes ->
;-------------------
;-------------------
;* end of smoke life
;* end of smoke life
;-------------------
;-------------------
mov TMP_SMOKE.SMOKE_TYPE,STYPE_NULL
mov TMP_SMOKE.SMOKE_TYPE,STYPE_NULL
stc ;cf = 1 = smoke cleared
stc ;cf = 1 = smoke cleared
ret
ret
;---------------------------
;---------------------------
Gnd1Phase1 LABEL NEAR ;expand radius
Gnd1Phase1 LABEL NEAR ;expand radius
;---------------------------
;---------------------------
Copia
Copiato
Copia
Copiato
REPT
3;
2 ;radius = time / 4
REPT
2 ;radius = time / 4
shr ax,1
shr ax,1
ENDM
ENDM
mov dx,TMP_SMOKE.SMOKE_RFT
mov dx,TMP_SMOKE.SMOKE_RFT
mov TMP_SMOKE.SMOKE_RFT,ax
mov TMP_SMOKE.SMOKE_RFT,ax
;* reset base zft
;* reset base zft
sub WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,dx
sub WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,dx
sbb WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0
sbb WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0
;* set centre zft wrt radius
;* set centre zft wrt radius
add WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax
add WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax
adc WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0
adc WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0
clc ;cf = 0 = smoke ok
clc ;cf = 0 = smoke ok
ret
ret
;---------------------------
;---------------------------
Gnd1Phase2 LABEL NEAR ;contract radius and drift upwards
Gnd1Phase2 LABEL NEAR ;contract radius and drift upwards
;---------------------------
;---------------------------
;* reproduce sibling?
;* reproduce sibling?
test TMP_SMOKE.SMOKE_FLAGS,SFLG_REPRO ;already reproduced?
test TMP_SMOKE.SMOKE_FLAGS,SFLG_REPRO ;already reproduced?
_JNZ SkipRepro ;yes ->
_JNZ SkipRepro ;yes ->
cmp TMP_SMOKE.SMOKE_SIB_CNTR,0 ;reproduce any more?
cmp TMP_SMOKE.SMOKE_SIB_CNTR,0 ;reproduce any more?
_JE SkipRepro ;no ->
_JE SkipRepro ;no ->
;* reproduce
;* reproduce
push ax
push ax
push dx
push dx
dec TMP_SMOKE.SMOKE_SIB_CNTR
dec TMP_SMOKE.SMOKE_SIB_CNTR
push WORD PTR TMP_SMOKE.SMOKE_COL ;(col + flags)
push WORD PTR TMP_SMOKE.SMOKE_COL ;(col + flags)
push WORD PTR TMP_SMOKE.SMOKE_ZFT_LO
push WORD PTR TMP_SMOKE.SMOKE_ZFT_LO
push WORD PTR TMP_SMOKE.SMOKE_ZFT_HI
push WORD PTR TMP_SMOKE.SMOKE_ZFT_HI
push TMP_SMOKE.SMOKE_ZFINE
push TMP_SMOKE.SMOKE_ZFINE
push TMP_SMOKE.SMOKE_RFT
push TMP_SMOKE.SMOKE_RFT
push TMP_SMOKE.SMOKE_TIME
push TMP_SMOKE.SMOKE_TIME
push TMP_SMOKE.SMOKE_EXP_TIME
push TMP_SMOKE.SMOKE_EXP_TIME
mov ax,TMP_SMOKE.SMOKE_RFT
mov ax,TMP_SMOKE.SMOKE_RFT
sub WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax ;reset base zft
sub WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax ;reset base zft
sbb WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0
sbb WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0
RND_SMOKE_COL
RND_SMOKE_COL
mov TMP_SMOKE.SMOKE_FLAGS,0
mov TMP_SMOKE.SMOKE_FLAGS,0
mov TMP_SMOKE.SMOKE_ZFINE,0
mov TMP_SMOKE.SMOKE_ZFINE,0
mov TMP_SMOKE.SMOKE_RFT,0
mov TMP_SMOKE.SMOKE_RFT,0
mov TMP_SMOKE.SMOKE_TIME,0
mov TMP_SMOKE.SMOKE_TIME,0
call RandX
call RandX
Copia
Copiato
Copia
Copiato
add ax,
8;
128
add ax,
128
mov TMP_SMOKE.SMOKE_EXP_TIME,ax
mov TMP_SMOKE.SMOKE_EXP_TIME,ax
call MakeSingleSmoke
call MakeSingleSmoke
pop TMP_SMOKE.SMOKE_EXP_TIME
pop TMP_SMOKE.SMOKE_EXP_TIME
pop TMP_SMOKE.SMOKE_TIME
pop TMP_SMOKE.SMOKE_TIME
pop TMP_SMOKE.SMOKE_RFT
pop TMP_SMOKE.SMOKE_RFT
pop TMP_SMOKE.SMOKE_ZFINE
pop TMP_SMOKE.SMOKE_ZFINE
pop WORD PTR TMP_SMOKE.SMOKE_ZFT_HI
pop WORD PTR TMP_SMOKE.SMOKE_ZFT_HI
pop WORD PTR TMP_SMOKE.SMOKE_ZFT_LO
pop WORD PTR TMP_SMOKE.SMOKE_ZFT_LO
pop WORD PTR TMP_SMOKE.SMOKE_COL ;(col + flags)
pop WORD PTR TMP_SMOKE.SMOKE_COL ;(col + flags)
or TMP_SMOKE.SMOKE_FLAGS,SFLG_REPRO
or TMP_SMOKE.SMOKE_FLAGS,SFLG_REPRO
pop dx
pop dx
pop ax
pop ax
SkipRepro: shr dx,1
SkipRepro: shr dx,1
shr ax,1
shr ax,1
sub dx,ax
sub dx,ax
Copia
Copiato
Copia
Copiato
REPT
3;
2 ;radius = (expand time - time) / 4
REPT
2 ;radius = (expand time - time) / 4
shr dx,1
shr dx,1
ENDM
ENDM
mov TMP_SMOKE.SMOKE_RFT,dx
mov TMP_SMOKE.SMOKE_RFT,dx
;* drift upwards
;* drift upwards
mov ax,DeltaTime
mov ax,DeltaTime
xor dx,dx
xor dx,dx
REPT 6 ;climb rate = 32ft / sec (64 * bin frac)
REPT 6 ;climb rate = 32ft / sec (64 * bin frac)
shl ax,1
shl ax,1
rcl dx,1
rcl dx,1
ENDM
ENDM
add TMP_SMOKE.SMOKE_ZFINE,ax
add TMP_SMOKE.SMOKE_ZFINE,ax
add WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,dx
add WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,dx
adc WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0
adc WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0
clc ;cf = 0 = smoke ok
clc ;cf = 0 = smoke ok
ret
ret
CtrlGnd1 ENDP
CtrlGnd1 ENDP
;----------------------------------------------------------------------------
;----------------------------------------------------------------------------
;* CtrlAir1 - control routine for air smoke type 1
;* CtrlAir1 - control routine for air smoke type 1
;*
;*
;* pass: TMP_SMOKE
;* pass: TMP_SMOKE
;* ret : TMP_SMOKE
;* ret : TMP_SMOKE
;* cf = 0 = smoke ok
;* cf = 0 = smoke ok
;* cf = 1 = smoke cleared
;* cf = 1 = smoke cleared
;* kill: assume all (except cf)
;* kill: assume all (except cf)
;*
;*
;* note: Phase 1: Expand radius.
;* note: Phase 1: Expand radius.
;* Phase 2: Contract radius.
;* Phase 2: Contract radius.
CtrlAir1 PROC NEAR
CtrlAir1 PROC NEAR
;--------------
;--------------
;* update timer
;* update timer
;--------------
;--------------
mov ax,TMP_SMOKE.SMOKE_TIME
mov ax,TMP_SMOKE.SMOKE_TIME
add ax,LastFrame
add ax,LastFrame
mov TMP_SMOKE.SMOKE_TIME,ax
mov TMP_SMOKE.SMOKE_TIME,ax
;------------
;------------
;* sort phase
;* sort phase
;------------
;------------
mov dx,TMP_SMOKE.SMOKE_EXP_TIME
mov dx,TMP_SMOKE.SMOKE_EXP_TIME
cmp ax,dx ;expand phase?
cmp ax,dx ;expand phase?
jbe Air1Phase1 ;yes ->
jbe Air1Phase1 ;yes ->
sub ax,dx
sub ax,dx
shl dx,1 ;contract phase is double expand phase
shl dx,1 ;contract phase is double expand phase
cmp ax,dx ;contract phase?
cmp ax,dx ;contract phase?
jbe Air1Phase2 ;yes ->
jbe Air1Phase2 ;yes ->
;-------------------
;-------------------
;* end of smoke life
;* end of smoke life
;-------------------
;-------------------
mov TMP_SMOKE.SMOKE_TYPE,STYPE_NULL
mov TMP_SMOKE.SMOKE_TYPE,STYPE_NULL
stc ;cf = 1 = smoke cleared
stc ;cf = 1 = smoke cleared
ret
ret
;---------------------------
;---------------------------
Air1Phase1 LABEL NEAR ;expand radius
Air1Phase1 LABEL NEAR ;expand radius
;---------------------------
;---------------------------
Copia
Copiato
Copia
Copiato
REPT
3;
2 ;radius = time / 4
REPT
2 ;radius = time / 4
shr ax,1
shr ax,1
ENDM
ENDM
mov TMP_SMOKE.SMOKE_RFT,ax
mov TMP_SMOKE.SMOKE_RFT,ax
clc ;cf = 0 = smoke ok
clc ;cf = 0 = smoke ok
ret
ret
;---------------------------
;---------------------------
Air1Phase2 LABEL NEAR ;contract radius
Air1Phase2 LABEL NEAR ;contract radius
;---------------------------
;---------------------------
shr dx,1
shr dx,1
shr ax,1
shr ax,1
sub dx,ax
sub dx,ax
Copia
Copiato
Copia
Copiato
REPT
3;
2 ;radius = (expand time - time) / 4
REPT
2 ;radius = (expand time - time) / 4
shr dx,1
shr dx,1
ENDM
ENDM
mov TMP_SMOKE.SMOKE_RFT,dx
mov TMP_SMOKE.SMOKE_RFT,dx
clc ;cf = 0 = smoke ok
clc ;cf = 0 = smoke ok
ret
ret
CtrlAir1 ENDP
CtrlAir1 ENDP
VISCODE ENDS
VISCODE ENDS
;============================================================================
;============================================================================
END
END
Copia
Copiato
Copia
Copiato
Diff salvati
Testo originale
Apri file
;Modded /VISUAL/SMOKE.ASM ;**************************************************************************** ;* ;* SMOKE.ASM ;* ;* Smoke effects generator. ;* ;* 29.11.1992 - KJB ;* 08.02.1993 - KJB - "air" smoke effects added. ;* ;**************************************************************************** OPTION M510 ;<<<<< MASM v5.10 <<<<< PUBLIC MakeSmokeEffect PUBLIC ScanSmoke EXTRN RandX:FAR EXTRN CalcGndHeight:FAR EXTRN DrawSmoke:NEAR EXTRN LastFrame:WORD EXTRN DeltaTime:WORD ;============================================================================ INCLUDE VISDATA.INC INCLUDE PALETTES.INC INCLUDE \LIB8086\USEFUL.INC ;============================================================================ DATA SEGMENT PARA PUBLIC 'DATA' NextSmokePtr DW OFFSET SmokeBuffer TMP_SMOKE SMOKE <> ;* init smoke effect switch InitSmoke DW InitCrater1 ;SMOKE_CRATER1 DW InitCrater2 ;SMOKE_CRATER2 DW InitCrater3 ;SMOKE_CRATER3 DW InitBurning ;SMOKE_BURNING DW InitKickUp ;SMOKE_KICK_UP DW InitAirExplo ;SMOKE_AIR_EXPLO DW InitAirTrail ;SMOKE_AIR_TRAIL ;* control smoke switch CtrlSmoke DW CtrlNull ;STYPE_NULL DW CtrlGnd1 ;STYPE_GND1 DW CtrlAir1 ;STYPE_AIR1 DATA ENDS ;============================================================================ SMOKEDATA SEGMENT PARA PUBLIC 'DATA' ;* cyclic buffer for smoke SmokeBuffer LABEL SMOKE SMOKE NUM_SMOKE DUP(<>) SmokeBufEnd LABEL SMOKE SMOKEDATA ENDS ;============================================================================ VISCODE SEGMENT BYTE PUBLIC 'CODE' ASSUME CS:VISCODE ASSUME DS:DATA ;* MakeSmokeEffect ;* ;* pass: bx = smoke effect type (see VISDATA.INC) ;* si -> VIEWPOINT data block ;* ret : nothing ;* kill: assume all MakeSmokeEffect PROC FAR ;----------------------- ;* copy viewpoint origin ;----------------------- mov ax,[si].VP_XSEC mov TMP_SMOKE.SMOKE_XSEC,ax mov ax,[si].VP_YSEC mov TMP_SMOKE.SMOKE_YSEC,ax mov ax,[si].VP_XFT mov TMP_SMOKE.SMOKE_XFT,ax mov ax,[si].VP_YFT mov TMP_SMOKE.SMOKE_YFT,ax mov ax,WORD PTR [si].VP_ZFT_LO mov WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax mov ax,WORD PTR [si].VP_ZFT_HI mov WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,ax ;------------------- ;* init smoke effect ;------------------- call InitSmoke[bx] ret MakeSmokeEffect ENDP ;---------------------------------------------------------------------------- ;* MakeSingleSmoke ;* ;* pass: NextSmokePtr ;* TMP_SMOKE data block ;* ret : NextSmokePtr ;* kill: assume all MakeSingleSmoke PROC NEAR mov ax,SMOKEDATA mov es,ax mov si,OFFSET TMP_SMOKE mov di,NextSmokePtr mov cx,SMOKE_REC_SIZE FAST_MOVE mov ax,DATA mov es,ax cmp di,OFFSET SmokeBufEnd ;end of buffer? jb @F ;no -> mov di,OFFSET SmokeBuffer ;wrap around @@: mov NextSmokePtr,di ret MakeSingleSmoke ENDP ;---------------------------------------------------------------------------- ;* RND_SMOKE_COL - set random smoke colour ;* ;* pass: nothing ;* ret : TMP_SMOKE.SMOKE_COL ;* kill: ax, flags RND_SMOKE_COL MACRO call RandX and al,1 add al,COL_SMOKE_GREY1 mov TMP_SMOKE.SMOKE_COL,al ENDM ;---------------------------------------------------------------------------- ;* InitGnd1 - init ground smoke type 1 effects ;* ;* InitCrater1 - init smoke for SMOKE_CRATER1 effect ;* InitCrater2 - init smoke for SMOKE_CRATER2 effect ;* InitCrater3 - init smoke for SMOKE_CRATER3 effect ;* InitBurning - init smoke for SMOKE_BURNING effect ;* InitKickUp - init smoke for SMOKE_KICK_UP effect ;* ;* pass: si -> VIEWPOINT data block ;* TMP_SMOKE ;* ret : TMP_SMOKE ;* kill: assume all ;--------------------------- InitCrater1 LABEL NEAR ;--------------------------- mov TMP_SMOKE.SMOKE_SIB_CNTR,0 mov cx,1 ;number of additional smokes jmp InitGnd1 ;--------------------------- InitCrater2 LABEL NEAR ;--------------------------- mov TMP_SMOKE.SMOKE_SIB_CNTR,0 mov cx,3 ;number of additional smokes jmp InitGnd1 ;--------------------------- InitCrater3 LABEL NEAR ;--------------------------- mov TMP_SMOKE.SMOKE_SIB_CNTR,0 mov cx,7 ;number of additional smokes jmp InitGnd1 ;--------------------------- InitBurning LABEL NEAR ;--------------------------- mov TMP_SMOKE.SMOKE_SIB_CNTR,10 mov cx,9 ;number of additional smokes jmp InitGnd1 ;--------------------------- InitKickUp LABEL NEAR ;--------------------------- mov TMP_SMOKE.SMOKE_SIB_CNTR,0 mov cx,3 ;number of additional smokes ;--------------------------- InitGnd1 PROC NEAR ;--------------------------- ;------------------ ;* init first smoke (always at viewpoint datum) ;------------------ mov TMP_SMOKE.SMOKE_TYPE,STYPE_GND1 RND_SMOKE_COL mov TMP_SMOKE.SMOKE_FLAGS,0 mov TMP_SMOKE.SMOKE_ZFINE,0 mov TMP_SMOKE.SMOKE_RFT,0 mov TMP_SMOKE.SMOKE_TIME,0 call RandX add ax,8 ;128 mov TMP_SMOKE.SMOKE_EXP_TIME,ax push cx push si call MakeSingleSmoke pop si pop cx ;------------------------ ;* init additional smokes ;------------------------ jcxz InitGnd1Exit ;no additional smokes -> AddSmokeLoop: push cx RND_SMOKE_COL call RandX add ax,8;128 mov TMP_SMOKE.SMOKE_EXP_TIME,ax ;* offset xft from origin (keep within sector) call RandX cbw sar ax,1 ;-64ft .. +63ft offset add ax,[si].VP_XFT cmp ax,8191 jle @F mov ax,8191 @@: cmp ax,-8192 jge @F mov ax,-8192 @@: mov TMP_SMOKE.SMOKE_XFT,ax ;* offset yft from origin (keep within sector) call RandX cbw sar ax,1 ;-64ft .. +63ft offset add ax,[si].VP_YFT cmp ax,8191 jle @F mov ax,8191 @@: cmp ax,-8192 jge @F mov ax,-8192 @@: mov TMP_SMOKE.SMOKE_YFT,ax push si call MakeSingleSmoke pop si pop cx loop AddSmokeLoop InitGnd1Exit: ret InitGnd1 ENDP ;---------------------------------------------------------------------------- ;* InitAir1 - init air smoke type 1 effects ;* ;* InitAirExplo - init smoke for SMOKE_AIR_EXPLO effect ;* InitAirTrail - init smoke for SMOKE_AIR_TRAIL effect ;* ;* pass: si -> VIEWPOINT data block ;* TMP_SMOKE ;* ret : TMP_SMOKE ;* kill: assume all ;--------------------------- InitAirExplo LABEL NEAR ;--------------------------- mov cx,15 ;number of additional smokes jmp InitAir1 ;--------------------------- InitAirTrail LABEL NEAR ;--------------------------- mov cx,3 ;number of additional smokes ;--------------------------- InitAir1 PROC NEAR ;--------------------------- push cx push si call CalcGndHeight pop si pop cx mov bp,ax ;bp = ground height ;------------------ ;* init first smoke (always at viewpoint datum) ;------------------ mov TMP_SMOKE.SMOKE_TYPE,STYPE_AIR1 RND_SMOKE_COL mov TMP_SMOKE.SMOKE_FLAGS,0 mov TMP_SMOKE.SMOKE_ZFINE,0 mov TMP_SMOKE.SMOKE_RFT,0 mov TMP_SMOKE.SMOKE_TIME,0 mov TMP_SMOKE.SMOKE_SIB_CNTR,0 call RandX add ax,8;128 mov TMP_SMOKE.SMOKE_EXP_TIME,ax call CheckAirPos push cx push si push bp call MakeSingleSmoke pop bp pop si pop cx ;------------------------ ;* init additional smokes ;------------------------ jcxz InitAir1Exit ;no additional smokes -> AirSmokeLoop: push cx RND_SMOKE_COL call RandX add ax,8;128 mov TMP_SMOKE.SMOKE_EXP_TIME,ax ;* offset xft from origin (keep within sector) call RandX cbw sar ax,1 ;-64ft .. +63ft offset add ax,[si].VP_XFT cmp ax,8191 jle @F mov ax,8191 @@: cmp ax,-8192 jge @F mov ax,-8192 @@: mov TMP_SMOKE.SMOKE_XFT,ax ;* offset yft from origin (keep within sector) call RandX cbw sar ax,1 ;-64ft .. +63ft offset add ax,[si].VP_YFT cmp ax,8191 jle @F mov ax,8191 @@: cmp ax,-8192 jge @F mov ax,-8192 @@: mov TMP_SMOKE.SMOKE_YFT,ax ;* offset zft from origin call RandX cbw sar ax,1 ;-64ft .. +63ft offset cwd add ax,WORD PTR [si].VP_ZFT_LO adc dx,WORD PTR [si].VP_ZFT_HI jns @F xor ax,ax xor dx,dx @@: mov WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax mov WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,dx call CheckAirPos push si push bp call MakeSingleSmoke pop bp pop si pop cx loop AirSmokeLoop InitAir1Exit: ret InitAir1 ENDP ;---------------------------------------------------------------------------- ;* CheckAirPos - check air smoke does not penetrate ground ;* ;* pass: TMP_SMOKE ;* bp = ground height ;* ret : TMP_SMOKE ;* kill: ax, dx, flags CheckAirPos PROC NEAR ;* if zft < 65536 then ;* ;* zdiff = zft - ground height ;* ;* if zdiff < 0 then ;* zft = ground height + 32 ;* expand time = 128 ;* else ;* if zdiff < expand time / 4 then ;* expand time = zdiff * 4 ;* if expand time < 128 then ;* zft = ground height + 32 ;* expand time = 128 ;* endif ;* endif ;* endif ;* endif cmp WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0 ja ExitAirPos mov ax,WORD PTR TMP_SMOKE.SMOKE_ZFT_LO sub ax,bp jb SetMinSize mov dx,TMP_SMOKE.SMOKE_EXP_TIME REPT 2 shr dx,1 ENDM cmp ax,dx jae ExitAirPos REPT 2 shl ax,1 ENDM cmp ax,8;128 jae @F SetMinSize: mov ax,bp add ax,8;32 mov WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax mov ax,8;128 @@: mov TMP_SMOKE.SMOKE_EXP_TIME,ax ExitAirPos: ret CheckAirPos ENDP ;---------------------------------------------------------------------------- ;* ScanSmoke - scan smoke buffer and draw smoke ;* ;* pass: nothing ;* ret : nothing ;* kill: assume all ;* ;* note: Smoke circles are low priority objects and could possibly clog the ;* object buffer. Therefore call this routine "later on" in the visual ;* drawing order. ScanSmoke PROC NEAR ;----------- ;* scan loop ;----------- mov cx,NUM_SMOKE mov si,OFFSET SmokeBuffer mov ax,SMOKEDATA mov ds,ax SmokeLoop: cmp [si].SMOKE_TYPE,STYPE_NULL ;smoke active? jne SortSmoke ;yes -> NextSmoke: add si,SMOKE_REC_SIZE loop SmokeLoop mov ax,DATA mov ds,ax ret ;----------------------------------- ;* copy smoke data into working copy ;----------------------------------- SortSmoke: push cx ;store loop count push si ;store smoke ptr mov di,OFFSET TMP_SMOKE mov cx,SMOKE_REC_SIZE FAST_MOVE mov ax,DATA mov ds,ax ;-------------- ;* update smoke ;-------------- mov bx,TMP_SMOKE.SMOKE_TYPE call CtrlSmoke[bx] jc @F ;smoke cleared -> ;------------ ;* draw smoke ;------------ mov si,OFFSET TMP_SMOKE call DrawSmoke ;----------------------------------- ;* copy smoke data from working copy ;----------------------------------- @@: pop di ;smoke ptr push di mov cx,SMOKE_REC_SIZE mov si,OFFSET TMP_SMOKE mov ax,SMOKEDATA mov es,ax FAST_MOVE mov ax,DATA mov es,ax ;------------------------------- ;* prepare to re-enter scan loop ;------------------------------- mov ax,SMOKEDATA mov ds,ax pop si ;restore smoke ptr pop cx ;restore loop count jmp NextSmoke ScanSmoke ENDP ;---------------------------------------------------------------------------- ;* CtrlNull ;* ;* pass: nothing ;* ret : cf = 1 = smoke cleared ;* kill: nothing CtrlNull PROC NEAR stc ret CtrlNull ENDP ;---------------------------------------------------------------------------- ;* CtrlGnd1 - control routine for ground smoke type 1 ;* ;* pass: TMP_SMOKE ;* ret : TMP_SMOKE ;* cf = 0 = smoke ok ;* cf = 1 = smoke cleared ;* kill: assume all (except cf) ;* ;* note: Phase 1: Expand radius keeping base of smoke on crater base. ;* Phase 2: Contract radius and drift upwards until radius is zero. CtrlGnd1 PROC NEAR ;-------------- ;* update timer ;-------------- mov ax,TMP_SMOKE.SMOKE_TIME add ax,LastFrame mov TMP_SMOKE.SMOKE_TIME,ax ;------------ ;* sort phase ;------------ mov dx,TMP_SMOKE.SMOKE_EXP_TIME cmp ax,dx ;expand phase? jbe Gnd1Phase1 ;yes -> sub ax,dx shl dx,1 ;contract phase is double expand phase cmp ax,dx ;contract phase? jbe Gnd1Phase2 ;yes -> ;------------------- ;* end of smoke life ;------------------- mov TMP_SMOKE.SMOKE_TYPE,STYPE_NULL stc ;cf = 1 = smoke cleared ret ;--------------------------- Gnd1Phase1 LABEL NEAR ;expand radius ;--------------------------- REPT 3;2 ;radius = time / 4 shr ax,1 ENDM mov dx,TMP_SMOKE.SMOKE_RFT mov TMP_SMOKE.SMOKE_RFT,ax ;* reset base zft sub WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,dx sbb WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0 ;* set centre zft wrt radius add WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax adc WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0 clc ;cf = 0 = smoke ok ret ;--------------------------- Gnd1Phase2 LABEL NEAR ;contract radius and drift upwards ;--------------------------- ;* reproduce sibling? test TMP_SMOKE.SMOKE_FLAGS,SFLG_REPRO ;already reproduced? _JNZ SkipRepro ;yes -> cmp TMP_SMOKE.SMOKE_SIB_CNTR,0 ;reproduce any more? _JE SkipRepro ;no -> ;* reproduce push ax push dx dec TMP_SMOKE.SMOKE_SIB_CNTR push WORD PTR TMP_SMOKE.SMOKE_COL ;(col + flags) push WORD PTR TMP_SMOKE.SMOKE_ZFT_LO push WORD PTR TMP_SMOKE.SMOKE_ZFT_HI push TMP_SMOKE.SMOKE_ZFINE push TMP_SMOKE.SMOKE_RFT push TMP_SMOKE.SMOKE_TIME push TMP_SMOKE.SMOKE_EXP_TIME mov ax,TMP_SMOKE.SMOKE_RFT sub WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax ;reset base zft sbb WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0 RND_SMOKE_COL mov TMP_SMOKE.SMOKE_FLAGS,0 mov TMP_SMOKE.SMOKE_ZFINE,0 mov TMP_SMOKE.SMOKE_RFT,0 mov TMP_SMOKE.SMOKE_TIME,0 call RandX add ax,8;128 mov TMP_SMOKE.SMOKE_EXP_TIME,ax call MakeSingleSmoke pop TMP_SMOKE.SMOKE_EXP_TIME pop TMP_SMOKE.SMOKE_TIME pop TMP_SMOKE.SMOKE_RFT pop TMP_SMOKE.SMOKE_ZFINE pop WORD PTR TMP_SMOKE.SMOKE_ZFT_HI pop WORD PTR TMP_SMOKE.SMOKE_ZFT_LO pop WORD PTR TMP_SMOKE.SMOKE_COL ;(col + flags) or TMP_SMOKE.SMOKE_FLAGS,SFLG_REPRO pop dx pop ax SkipRepro: shr dx,1 shr ax,1 sub dx,ax REPT 3;2 ;radius = (expand time - time) / 4 shr dx,1 ENDM mov TMP_SMOKE.SMOKE_RFT,dx ;* drift upwards mov ax,DeltaTime xor dx,dx REPT 6 ;climb rate = 32ft / sec (64 * bin frac) shl ax,1 rcl dx,1 ENDM add TMP_SMOKE.SMOKE_ZFINE,ax add WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,dx adc WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0 clc ;cf = 0 = smoke ok ret CtrlGnd1 ENDP ;---------------------------------------------------------------------------- ;* CtrlAir1 - control routine for air smoke type 1 ;* ;* pass: TMP_SMOKE ;* ret : TMP_SMOKE ;* cf = 0 = smoke ok ;* cf = 1 = smoke cleared ;* kill: assume all (except cf) ;* ;* note: Phase 1: Expand radius. ;* Phase 2: Contract radius. CtrlAir1 PROC NEAR ;-------------- ;* update timer ;-------------- mov ax,TMP_SMOKE.SMOKE_TIME add ax,LastFrame mov TMP_SMOKE.SMOKE_TIME,ax ;------------ ;* sort phase ;------------ mov dx,TMP_SMOKE.SMOKE_EXP_TIME cmp ax,dx ;expand phase? jbe Air1Phase1 ;yes -> sub ax,dx shl dx,1 ;contract phase is double expand phase cmp ax,dx ;contract phase? jbe Air1Phase2 ;yes -> ;------------------- ;* end of smoke life ;------------------- mov TMP_SMOKE.SMOKE_TYPE,STYPE_NULL stc ;cf = 1 = smoke cleared ret ;--------------------------- Air1Phase1 LABEL NEAR ;expand radius ;--------------------------- REPT 3;2 ;radius = time / 4 shr ax,1 ENDM mov TMP_SMOKE.SMOKE_RFT,ax clc ;cf = 0 = smoke ok ret ;--------------------------- Air1Phase2 LABEL NEAR ;contract radius ;--------------------------- shr dx,1 shr ax,1 sub dx,ax REPT 3;2 ;radius = (expand time - time) / 4 shr dx,1 ENDM mov TMP_SMOKE.SMOKE_RFT,dx clc ;cf = 0 = smoke ok ret CtrlAir1 ENDP VISCODE ENDS ;============================================================================ END
Testo modificato
Apri file
;Original ;**************************************************************************** ;* ;* SMOKE.ASM ;* ;* Smoke effects generator. ;* ;* 29.11.1992 - KJB ;* 08.02.1993 - KJB - "air" smoke effects added. ;* ;**************************************************************************** OPTION M510 ;<<<<< MASM v5.10 <<<<< PUBLIC MakeSmokeEffect PUBLIC ScanSmoke EXTRN RandX:FAR EXTRN CalcGndHeight:FAR EXTRN DrawSmoke:NEAR EXTRN LastFrame:WORD EXTRN DeltaTime:WORD ;============================================================================ INCLUDE VISDATA.INC INCLUDE PALETTES.INC INCLUDE \LIB8086\USEFUL.INC ;============================================================================ DATA SEGMENT PARA PUBLIC 'DATA' NextSmokePtr DW OFFSET SmokeBuffer TMP_SMOKE SMOKE <> ;* init smoke effect switch InitSmoke DW InitCrater1 ;SMOKE_CRATER1 DW InitCrater2 ;SMOKE_CRATER2 DW InitCrater3 ;SMOKE_CRATER3 DW InitBurning ;SMOKE_BURNING DW InitKickUp ;SMOKE_KICK_UP DW InitAirExplo ;SMOKE_AIR_EXPLO DW InitAirTrail ;SMOKE_AIR_TRAIL ;* control smoke switch CtrlSmoke DW CtrlNull ;STYPE_NULL DW CtrlGnd1 ;STYPE_GND1 DW CtrlAir1 ;STYPE_AIR1 DATA ENDS ;============================================================================ SMOKEDATA SEGMENT PARA PUBLIC 'DATA' ;* cyclic buffer for smoke SmokeBuffer LABEL SMOKE SMOKE NUM_SMOKE DUP(<>) SmokeBufEnd LABEL SMOKE SMOKEDATA ENDS ;============================================================================ VISCODE SEGMENT BYTE PUBLIC 'CODE' ASSUME CS:VISCODE ASSUME DS:DATA ;* MakeSmokeEffect ;* ;* pass: bx = smoke effect type (see VISDATA.INC) ;* si -> VIEWPOINT data block ;* ret : nothing ;* kill: assume all MakeSmokeEffect PROC FAR ;----------------------- ;* copy viewpoint origin ;----------------------- mov ax,[si].VP_XSEC mov TMP_SMOKE.SMOKE_XSEC,ax mov ax,[si].VP_YSEC mov TMP_SMOKE.SMOKE_YSEC,ax mov ax,[si].VP_XFT mov TMP_SMOKE.SMOKE_XFT,ax mov ax,[si].VP_YFT mov TMP_SMOKE.SMOKE_YFT,ax mov ax,WORD PTR [si].VP_ZFT_LO mov WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax mov ax,WORD PTR [si].VP_ZFT_HI mov WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,ax ;------------------- ;* init smoke effect ;------------------- call InitSmoke[bx] ret MakeSmokeEffect ENDP ;---------------------------------------------------------------------------- ;* MakeSingleSmoke ;* ;* pass: NextSmokePtr ;* TMP_SMOKE data block ;* ret : NextSmokePtr ;* kill: assume all MakeSingleSmoke PROC NEAR mov ax,SMOKEDATA mov es,ax mov si,OFFSET TMP_SMOKE mov di,NextSmokePtr mov cx,SMOKE_REC_SIZE FAST_MOVE mov ax,DATA mov es,ax cmp di,OFFSET SmokeBufEnd ;end of buffer? jb @F ;no -> mov di,OFFSET SmokeBuffer ;wrap around @@: mov NextSmokePtr,di ret MakeSingleSmoke ENDP ;---------------------------------------------------------------------------- ;* RND_SMOKE_COL - set random smoke colour ;* ;* pass: nothing ;* ret : TMP_SMOKE.SMOKE_COL ;* kill: ax, flags RND_SMOKE_COL MACRO call RandX and al,1 add al,COL_SMOKE_GREY1 mov TMP_SMOKE.SMOKE_COL,al ENDM ;---------------------------------------------------------------------------- ;* InitGnd1 - init ground smoke type 1 effects ;* ;* InitCrater1 - init smoke for SMOKE_CRATER1 effect ;* InitCrater2 - init smoke for SMOKE_CRATER2 effect ;* InitCrater3 - init smoke for SMOKE_CRATER3 effect ;* InitBurning - init smoke for SMOKE_BURNING effect ;* InitKickUp - init smoke for SMOKE_KICK_UP effect ;* ;* pass: si -> VIEWPOINT data block ;* TMP_SMOKE ;* ret : TMP_SMOKE ;* kill: assume all ;--------------------------- InitCrater1 LABEL NEAR ;--------------------------- mov TMP_SMOKE.SMOKE_SIB_CNTR,0 mov cx,1 ;number of additional smokes jmp InitGnd1 ;--------------------------- InitCrater2 LABEL NEAR ;--------------------------- mov TMP_SMOKE.SMOKE_SIB_CNTR,0 mov cx,3 ;number of additional smokes jmp InitGnd1 ;--------------------------- InitCrater3 LABEL NEAR ;--------------------------- mov TMP_SMOKE.SMOKE_SIB_CNTR,0 mov cx,7 ;number of additional smokes jmp InitGnd1 ;--------------------------- InitBurning LABEL NEAR ;--------------------------- mov TMP_SMOKE.SMOKE_SIB_CNTR,10 mov cx,9 ;number of additional smokes jmp InitGnd1 ;--------------------------- InitKickUp LABEL NEAR ;--------------------------- mov TMP_SMOKE.SMOKE_SIB_CNTR,0 mov cx,3 ;number of additional smokes ;--------------------------- InitGnd1 PROC NEAR ;--------------------------- ;------------------ ;* init first smoke (always at viewpoint datum) ;------------------ mov TMP_SMOKE.SMOKE_TYPE,STYPE_GND1 RND_SMOKE_COL mov TMP_SMOKE.SMOKE_FLAGS,0 mov TMP_SMOKE.SMOKE_ZFINE,0 mov TMP_SMOKE.SMOKE_RFT,0 mov TMP_SMOKE.SMOKE_TIME,0 call RandX add ax,128 mov TMP_SMOKE.SMOKE_EXP_TIME,ax push cx push si call MakeSingleSmoke pop si pop cx ;------------------------ ;* init additional smokes ;------------------------ jcxz InitGnd1Exit ;no additional smokes -> AddSmokeLoop: push cx RND_SMOKE_COL call RandX add ax,128 mov TMP_SMOKE.SMOKE_EXP_TIME,ax ;* offset xft from origin (keep within sector) call RandX cbw sar ax,1 ;-64ft .. +63ft offset add ax,[si].VP_XFT cmp ax,8191 jle @F mov ax,8191 @@: cmp ax,-8192 jge @F mov ax,-8192 @@: mov TMP_SMOKE.SMOKE_XFT,ax ;* offset yft from origin (keep within sector) call RandX cbw sar ax,1 ;-64ft .. +63ft offset add ax,[si].VP_YFT cmp ax,8191 jle @F mov ax,8191 @@: cmp ax,-8192 jge @F mov ax,-8192 @@: mov TMP_SMOKE.SMOKE_YFT,ax push si call MakeSingleSmoke pop si pop cx loop AddSmokeLoop InitGnd1Exit: ret InitGnd1 ENDP ;---------------------------------------------------------------------------- ;* InitAir1 - init air smoke type 1 effects ;* ;* InitAirExplo - init smoke for SMOKE_AIR_EXPLO effect ;* InitAirTrail - init smoke for SMOKE_AIR_TRAIL effect ;* ;* pass: si -> VIEWPOINT data block ;* TMP_SMOKE ;* ret : TMP_SMOKE ;* kill: assume all ;--------------------------- InitAirExplo LABEL NEAR ;--------------------------- mov cx,15 ;number of additional smokes jmp InitAir1 ;--------------------------- InitAirTrail LABEL NEAR ;--------------------------- mov cx,3 ;number of additional smokes ;--------------------------- InitAir1 PROC NEAR ;--------------------------- push cx push si call CalcGndHeight pop si pop cx mov bp,ax ;bp = ground height ;------------------ ;* init first smoke (always at viewpoint datum) ;------------------ mov TMP_SMOKE.SMOKE_TYPE,STYPE_AIR1 RND_SMOKE_COL mov TMP_SMOKE.SMOKE_FLAGS,0 mov TMP_SMOKE.SMOKE_ZFINE,0 mov TMP_SMOKE.SMOKE_RFT,0 mov TMP_SMOKE.SMOKE_TIME,0 mov TMP_SMOKE.SMOKE_SIB_CNTR,0 call RandX add ax,128 mov TMP_SMOKE.SMOKE_EXP_TIME,ax call CheckAirPos push cx push si push bp call MakeSingleSmoke pop bp pop si pop cx ;------------------------ ;* init additional smokes ;------------------------ jcxz InitAir1Exit ;no additional smokes -> AirSmokeLoop: push cx RND_SMOKE_COL call RandX add ax,128 mov TMP_SMOKE.SMOKE_EXP_TIME,ax ;* offset xft from origin (keep within sector) call RandX cbw sar ax,1 ;-64ft .. +63ft offset add ax,[si].VP_XFT cmp ax,8191 jle @F mov ax,8191 @@: cmp ax,-8192 jge @F mov ax,-8192 @@: mov TMP_SMOKE.SMOKE_XFT,ax ;* offset yft from origin (keep within sector) call RandX cbw sar ax,1 ;-64ft .. +63ft offset add ax,[si].VP_YFT cmp ax,8191 jle @F mov ax,8191 @@: cmp ax,-8192 jge @F mov ax,-8192 @@: mov TMP_SMOKE.SMOKE_YFT,ax ;* offset zft from origin call RandX cbw sar ax,1 ;-64ft .. +63ft offset cwd add ax,WORD PTR [si].VP_ZFT_LO adc dx,WORD PTR [si].VP_ZFT_HI jns @F xor ax,ax xor dx,dx @@: mov WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax mov WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,dx call CheckAirPos push si push bp call MakeSingleSmoke pop bp pop si pop cx loop AirSmokeLoop InitAir1Exit: ret InitAir1 ENDP ;---------------------------------------------------------------------------- ;* CheckAirPos - check air smoke does not penetrate ground ;* ;* pass: TMP_SMOKE ;* bp = ground height ;* ret : TMP_SMOKE ;* kill: ax, dx, flags CheckAirPos PROC NEAR ;* if zft < 65536 then ;* ;* zdiff = zft - ground height ;* ;* if zdiff < 0 then ;* zft = ground height + 32 ;* expand time = 128 ;* else ;* if zdiff < expand time / 4 then ;* expand time = zdiff * 4 ;* if expand time < 128 then ;* zft = ground height + 32 ;* expand time = 128 ;* endif ;* endif ;* endif ;* endif cmp WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0 ja ExitAirPos mov ax,WORD PTR TMP_SMOKE.SMOKE_ZFT_LO sub ax,bp jb SetMinSize mov dx,TMP_SMOKE.SMOKE_EXP_TIME REPT 2 shr dx,1 ENDM cmp ax,dx jae ExitAirPos REPT 2 shl ax,1 ENDM cmp ax,128 jae @F SetMinSize: mov ax,bp add ax,32 mov WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax mov ax,128 @@: mov TMP_SMOKE.SMOKE_EXP_TIME,ax ExitAirPos: ret CheckAirPos ENDP ;---------------------------------------------------------------------------- ;* ScanSmoke - scan smoke buffer and draw smoke ;* ;* pass: nothing ;* ret : nothing ;* kill: assume all ;* ;* note: Smoke circles are low priority objects and could possibly clog the ;* object buffer. Therefore call this routine "later on" in the visual ;* drawing order. ScanSmoke PROC NEAR ;----------- ;* scan loop ;----------- mov cx,NUM_SMOKE mov si,OFFSET SmokeBuffer mov ax,SMOKEDATA mov ds,ax SmokeLoop: cmp [si].SMOKE_TYPE,STYPE_NULL ;smoke active? jne SortSmoke ;yes -> NextSmoke: add si,SMOKE_REC_SIZE loop SmokeLoop mov ax,DATA mov ds,ax ret ;----------------------------------- ;* copy smoke data into working copy ;----------------------------------- SortSmoke: push cx ;store loop count push si ;store smoke ptr mov di,OFFSET TMP_SMOKE mov cx,SMOKE_REC_SIZE FAST_MOVE mov ax,DATA mov ds,ax ;-------------- ;* update smoke ;-------------- mov bx,TMP_SMOKE.SMOKE_TYPE call CtrlSmoke[bx] jc @F ;smoke cleared -> ;------------ ;* draw smoke ;------------ mov si,OFFSET TMP_SMOKE call DrawSmoke ;----------------------------------- ;* copy smoke data from working copy ;----------------------------------- @@: pop di ;smoke ptr push di mov cx,SMOKE_REC_SIZE mov si,OFFSET TMP_SMOKE mov ax,SMOKEDATA mov es,ax FAST_MOVE mov ax,DATA mov es,ax ;------------------------------- ;* prepare to re-enter scan loop ;------------------------------- mov ax,SMOKEDATA mov ds,ax pop si ;restore smoke ptr pop cx ;restore loop count jmp NextSmoke ScanSmoke ENDP ;---------------------------------------------------------------------------- ;* CtrlNull ;* ;* pass: nothing ;* ret : cf = 1 = smoke cleared ;* kill: nothing CtrlNull PROC NEAR stc ret CtrlNull ENDP ;---------------------------------------------------------------------------- ;* CtrlGnd1 - control routine for ground smoke type 1 ;* ;* pass: TMP_SMOKE ;* ret : TMP_SMOKE ;* cf = 0 = smoke ok ;* cf = 1 = smoke cleared ;* kill: assume all (except cf) ;* ;* note: Phase 1: Expand radius keeping base of smoke on crater base. ;* Phase 2: Contract radius and drift upwards until radius is zero. CtrlGnd1 PROC NEAR ;-------------- ;* update timer ;-------------- mov ax,TMP_SMOKE.SMOKE_TIME add ax,LastFrame mov TMP_SMOKE.SMOKE_TIME,ax ;------------ ;* sort phase ;------------ mov dx,TMP_SMOKE.SMOKE_EXP_TIME cmp ax,dx ;expand phase? jbe Gnd1Phase1 ;yes -> sub ax,dx shl dx,1 ;contract phase is double expand phase cmp ax,dx ;contract phase? jbe Gnd1Phase2 ;yes -> ;------------------- ;* end of smoke life ;------------------- mov TMP_SMOKE.SMOKE_TYPE,STYPE_NULL stc ;cf = 1 = smoke cleared ret ;--------------------------- Gnd1Phase1 LABEL NEAR ;expand radius ;--------------------------- REPT 2 ;radius = time / 4 shr ax,1 ENDM mov dx,TMP_SMOKE.SMOKE_RFT mov TMP_SMOKE.SMOKE_RFT,ax ;* reset base zft sub WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,dx sbb WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0 ;* set centre zft wrt radius add WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax adc WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0 clc ;cf = 0 = smoke ok ret ;--------------------------- Gnd1Phase2 LABEL NEAR ;contract radius and drift upwards ;--------------------------- ;* reproduce sibling? test TMP_SMOKE.SMOKE_FLAGS,SFLG_REPRO ;already reproduced? _JNZ SkipRepro ;yes -> cmp TMP_SMOKE.SMOKE_SIB_CNTR,0 ;reproduce any more? _JE SkipRepro ;no -> ;* reproduce push ax push dx dec TMP_SMOKE.SMOKE_SIB_CNTR push WORD PTR TMP_SMOKE.SMOKE_COL ;(col + flags) push WORD PTR TMP_SMOKE.SMOKE_ZFT_LO push WORD PTR TMP_SMOKE.SMOKE_ZFT_HI push TMP_SMOKE.SMOKE_ZFINE push TMP_SMOKE.SMOKE_RFT push TMP_SMOKE.SMOKE_TIME push TMP_SMOKE.SMOKE_EXP_TIME mov ax,TMP_SMOKE.SMOKE_RFT sub WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,ax ;reset base zft sbb WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0 RND_SMOKE_COL mov TMP_SMOKE.SMOKE_FLAGS,0 mov TMP_SMOKE.SMOKE_ZFINE,0 mov TMP_SMOKE.SMOKE_RFT,0 mov TMP_SMOKE.SMOKE_TIME,0 call RandX add ax,128 mov TMP_SMOKE.SMOKE_EXP_TIME,ax call MakeSingleSmoke pop TMP_SMOKE.SMOKE_EXP_TIME pop TMP_SMOKE.SMOKE_TIME pop TMP_SMOKE.SMOKE_RFT pop TMP_SMOKE.SMOKE_ZFINE pop WORD PTR TMP_SMOKE.SMOKE_ZFT_HI pop WORD PTR TMP_SMOKE.SMOKE_ZFT_LO pop WORD PTR TMP_SMOKE.SMOKE_COL ;(col + flags) or TMP_SMOKE.SMOKE_FLAGS,SFLG_REPRO pop dx pop ax SkipRepro: shr dx,1 shr ax,1 sub dx,ax REPT 2 ;radius = (expand time - time) / 4 shr dx,1 ENDM mov TMP_SMOKE.SMOKE_RFT,dx ;* drift upwards mov ax,DeltaTime xor dx,dx REPT 6 ;climb rate = 32ft / sec (64 * bin frac) shl ax,1 rcl dx,1 ENDM add TMP_SMOKE.SMOKE_ZFINE,ax add WORD PTR TMP_SMOKE.SMOKE_ZFT_LO,dx adc WORD PTR TMP_SMOKE.SMOKE_ZFT_HI,0 clc ;cf = 0 = smoke ok ret CtrlGnd1 ENDP ;---------------------------------------------------------------------------- ;* CtrlAir1 - control routine for air smoke type 1 ;* ;* pass: TMP_SMOKE ;* ret : TMP_SMOKE ;* cf = 0 = smoke ok ;* cf = 1 = smoke cleared ;* kill: assume all (except cf) ;* ;* note: Phase 1: Expand radius. ;* Phase 2: Contract radius. CtrlAir1 PROC NEAR ;-------------- ;* update timer ;-------------- mov ax,TMP_SMOKE.SMOKE_TIME add ax,LastFrame mov TMP_SMOKE.SMOKE_TIME,ax ;------------ ;* sort phase ;------------ mov dx,TMP_SMOKE.SMOKE_EXP_TIME cmp ax,dx ;expand phase? jbe Air1Phase1 ;yes -> sub ax,dx shl dx,1 ;contract phase is double expand phase cmp ax,dx ;contract phase? jbe Air1Phase2 ;yes -> ;------------------- ;* end of smoke life ;------------------- mov TMP_SMOKE.SMOKE_TYPE,STYPE_NULL stc ;cf = 1 = smoke cleared ret ;--------------------------- Air1Phase1 LABEL NEAR ;expand radius ;--------------------------- REPT 2 ;radius = time / 4 shr ax,1 ENDM mov TMP_SMOKE.SMOKE_RFT,ax clc ;cf = 0 = smoke ok ret ;--------------------------- Air1Phase2 LABEL NEAR ;contract radius ;--------------------------- shr dx,1 shr ax,1 sub dx,ax REPT 2 ;radius = (expand time - time) / 4 shr dx,1 ENDM mov TMP_SMOKE.SMOKE_RFT,dx clc ;cf = 0 = smoke ok ret CtrlAir1 ENDP VISCODE ENDS ;============================================================================ END
Trovare la differenza