Files
Work/ddraw/TRIMAP32.SAF
2024-08-07 09:16:27 -04:00

333 lines
20 KiB
Plaintext

;********************************************************************************************************
; MODULE: TRIMAP32.ASM DATE: FEBRUARY 11, 1999
; AUTHOR: SEAN M. KESSLER
; TARGET: 32 BIT TARGET
; FUNCTION : TEXTURE MAPPING TRIANGLES
;********************************************************************************************************
SMART
.386
.MODEL FLAT
.DATA
bmData@@mSrcWidth DD ?
bmData@@mSrcHeight DD ?
bmData@@mSrcExtent DD ?
bmData@@mlpSrcPtr DD ?
bmData@@mDstWidth DD ?
bmData@@mDstPitch DD ?
bmData@@mDstHeight DD ?
bmData@@mDstExtent DD ?
bmData@@mlpDstPtr DD ?
bmData@@mlpDstIndexPtr DD ?
.LALL
INCLUDE ..\COMMON\COMMON.INC
INCLUDE ..\DDRAW\TRIMAP32.INC
INCLUDE ..\DDRAW\UTIL32.INC
.CODE
roundEAX MACRO
LOCAL @@return
mov edx,eax ; copy eax to edx
and edx,7FFh ; get remainder to edx register
shr eax,0Bh ; get whole number to eax register
cmp edx,400h ; if remainder>1024 then increment eax
jle @@return ; ... otherwise return
inc eax ; increment value in eax
@@return:
ENDM
scanline MACRO
mov ecx,[esi].DirectTriEdge@@mxRight ; move mxRight into ecx
sub ecx,[esi].DirectTriEdge@@mxLeft ; subtract out mxLeft, this is dx
cmp ecx,0000h ; compare dx to zero
je @@scanlineLoopEnd ; if dx is zero then don't scan the line
mov eax,[esi].DirectTriEdge@@muRight ; move muRight into eax
sub eax,[esi].DirectTriEdge@@muLeft ; subtract out muLeft
shl eax,0Bh ; multiply this by 2048
divide eax,ecx ; divide by dx, this is du
mov du,eax ; store du into local variable
mov eax,[esi].DirectTriEdge@@mvRight ; move mvRight into eax
sub eax,[esi].DirectTriEdge@@mvLeft ; subtract out mvLeft
shl eax,0Bh ; multiply this by 2048
divide eax,ecx ; divide by dx, this is dv
mov dv,eax ; store dv into local variable
mov eax,[esi].DirectTriEdge@@muLeft ; move muLeft into eax
mov ui,eax ; muLeft is initial value for ui
mov eax,[esi].DirectTriEdge@@mvLeft ; move mvLeft into eax
mov vi,eax ; mvLeft is initial value for vi
mov eax,[esi].DirectTriEdge@@mxLeft ; move mxLeft into eax
mov x,eax ; mxLeft is initial value for x
@@scanlineLoop: ; scanline loop sync address
mov eax,[esi].DirectTriEdge@@mxRight ; move mxRight into eax
cmp x,eax ; compare x to mxRight
jg @@scanlineLoopEnd ; if x>mxRight then we're done with the scanline
getSrcDataByte ; get source byte at [ui][vi] to cl register
setDstDataByte ; set destination byte at [x][y],cl
incrementScan ; advance along the scanline
jmp @@scanlineLoop ; continue execution
@@scanlineLoopEnd: ; end scanline sync address
ENDM
incrementScan MACRO ; advance along the scanline
mov eax,ui ; move ui to eax
shl eax,0Bh ; multiply by 2048
add eax,du ; add in du
shr eax,0Bh ; divide by 2048
mov ui,eax ; update ui
mov eax,vi ; move vi to eax
shl eax,0Bh ; multiply by 2048
add eax,dv ; add in dv
shr eax,0Bh ; divide by 2048
mov vi,eax ; update vi
inc x ; increment x
ENDM
increment MACRO
mov eax,[esi].DirectTriEdge@@mxLeft ; move mxLeft into eax
shl eax,0Bh ; multiply by 2048
add eax,[esi].DirectTriEdge@@mDXLeft ; add in the delta
roundEAX ; adjust and round the value
mov [esi].DirectTriEdge@@mxLeft,eax ; this is new mxLeft
mov eax,[esi].DirectTriEdge@@mxRight ; move mxRight into eax
shl eax,0Bh ; multiply by 2048
add eax,[esi].DirectTriEdge@@mDXRight ; add in the delta
roundEAX ; adjust and round the value
mov [esi].DirectTriEdge@@mxRight,eax ; this is new mxRight
mov eax,[esi].DirectTriEdge@@muLeft ; move muLeft into eax
shl eax,0Bh ; multiply by 2048
add eax,[esi].DirectTriEdge@@mDULeft ; add in the delta
roundEAX ; adjust and round the value
mov [esi].DirectTriEdge@@muLeft,eax ; this is new muLeft
mov eax,[esi].DirectTriEdge@@muRight ; move muRight into eax
shl eax,0Bh ; multiply by 2048
add eax,[esi].DirectTriEdge@@mDURight ; add in the delta
roundEAX ; adjust and round the value
mov [esi].DirectTriEdge@@muRight,eax ; this is new muRight
mov eax,[esi].DirectTriEdge@@mvLeft ; move mvLeft into eax
shl eax,0Bh ; multiply by 2048
add eax,[esi].DirectTriEdge@@mDVLeft ; add in the delta
roundEAX ; adjust and round the value
mov [esi].DirectTriEdge@@mvLeft,eax ; this is new mvLeft
mov eax,[esi].DirectTriEdge@@mvRight ; move mvRight into eax
shl eax,0Bh ; multiply by 2048
add eax,[esi].DirectTriEdge@@mDVRight ; add in the delta
roundEAX ; adjust and round the value
mov [esi].DirectTriEdge@@mvRight,eax ; this is new mvRight
inc y ; increment y
ENDM
initialize MACRO
mov eax,[esi].DirectTriEdge@@my2 ; move my2 into eax
sub eax,[esi].DirectTriEdge@@my0 ; eax has (y2-y0)
mov [esi].DirectTriEdge@@mDY,eax ; move (y2-y0) into mDY variable
mov eax,[esi].DirectTriEdge@@mx2 ; move x2 into eax
sub eax,[esi].DirectTriEdge@@mx0 ; eax has (x2-x0)
shl eax,0Bh ; multiply result by 2048 for precision
divide eax,[esi].DirectTriEdge@@mDY ; eax has (x2-x0)/(y2-y0)
mov [esi].DirectTriEdge@@mDXLeft,eax ; this is mDXLeft
mov eax,[esi].DirectTriEdge@@mx1 ; move x1 into eax
sub eax,[esi].DirectTriEdge@@mx0 ; eax has (x1-x0)
shl eax,0Bh ; multiply result by 2048 for precision
divide eax,[esi].DirectTriEdge@@mDY ; eax has (x1-x0)/(y2-y0)
mov [esi].DirectTriEdge@@mDXRight,eax ; this is mDXRight
mov eax,[esi].DirectTriEdge@@mu2 ; move u2 into eax
sub eax,[esi].DirectTriEdge@@mu0 ; eax has (u2-u0)
shl eax,0Bh ; multiply result by 2048 for precision
divide eax,[esi].DirectTriEdge@@mDY ; eax has (u2-u0)/(y2-y0)
mov [esi].DirectTriEdge@@mDULeft,eax ; this is mDULeft
mov eax,[esi].DirectTriEdge@@mu1 ; move u1 into eax
sub eax,[esi].DirectTriEdge@@mu0 ; eax has (u1-u0)
shl eax,0Bh ; multiply result by 2048 for precision
divide eax,[esi].DirectTriEdge@@mDY ; eax has (u1-u0)/(y2-y0)
mov [esi].DirectTriEdge@@mDURight,eax ; this is mDURight
mov eax,[esi].DirectTriEdge@@mv2 ; move v2 into eax
sub eax,[esi].DirectTriEdge@@mv0 ; eax has (v2-v0)
shl eax,0Bh ; multiply result by 2048 for precision
divide eax,[esi].DirectTriEdge@@mDY ; eax has (v2-v0)/(y2-y0)
mov [esi].DirectTriEdge@@mDVLeft,eax ; this is mDVLeft
mov eax,[esi].DirectTriEdge@@mv1 ; move v1 into eax
sub eax,[esi].DirectTriEdge@@mv0 ; eax has (v1-v0)
shl eax,0Bh ; multiply result by 2048 for precision
divide eax,[esi].DirectTriEdge@@mDY ; eax has (v1-v0)/(y2-y0)
mov [esi].DirectTriEdge@@mDVRight,eax ; this is mDVRight
mov eax,[esi].DirectTriEdge@@mx0 ; move x0 into eax
mov [esi].DirectTriEdge@@mxLeft,eax ; mxLeft=x0
mov [esi].DirectTriEdge@@mxRight,eax ; mxRight=x0
mov eax,[esi].DirectTriEdge@@mu0 ; move u0 into eax
mov [esi].DirectTriEdge@@muLeft,eax ; muLeft=u0
mov [esi].DirectTriEdge@@muRight,eax ; muRight=u0
mov eax,[esi].DirectTriEdge@@mv0 ; move v0 into eax
mov [esi].DirectTriEdge@@mvLeft,eax ; mvLeft=v0
mov [esi].DirectTriEdge@@mvRight,eax ; mvRight=v0
ENDM
if 0
initialize MACRO
mov eax,[esi].DirectTriEdge@@my2 ; move my2 into eax
sub eax,[esi].DirectTriEdge@@my0 ; eax has (y2-y0)
mov [esi].DirectTriEdge@@mDY,eax ; move (y2-y0) into mDY variable
mov eax,[esi].DirectTriEdge@@mx2 ; move x2 into eax
sub eax,[esi].DirectTriEdge@@mx0 ; eax has (x2-x0)
shl eax,0Bh ; multiply result by 2048 for precision
divide eax,[esi].DirectTriEdge@@mDY ; eax has (x2-x0)/(y2-y0)
mov [esi].DirectTriEdge@@mDXLeft,eax ; this is mDXLeft
mov eax,[esi].DirectTriEdge@@mx1 ; move x1 into eax
sub eax,[esi].DirectTriEdge@@mx0 ; eax has (x1-x0)
shl eax,0Bh ; multiply result by 2048 for precision
divide eax,[esi].DirectTriEdge@@mDY ; eax has (x1-x0)/(y2-y0)
mov [esi].DirectTriEdge@@mDXRight,eax ; this is mDXRight
mov eax,[esi].DirectTriEdge@@mu2 ; move u2 into eax
sub eax,[esi].DirectTriEdge@@mu0 ; eax has (u2-u0)
shl eax,0Bh ; multiply result by 2048 for precision
divide eax,[esi].DirectTriEdge@@mDY ; eax has (u2-u0)/(y2-y0)
mov [esi].DirectTriEdge@@mDULeft,eax ; this is mDULeft
mov eax,[esi].DirectTriEdge@@mu1 ; move u1 into eax
sub eax,[esi].DirectTriEdge@@mu0 ; eax has (u1-u0)
shl eax,0Bh ; multiply result by 2048 for precision
divide eax,[esi].DirectTriEdge@@mDY ; eax has (u1-u0)/(y2-y0)
mov [esi].DirectTriEdge@@mDURight,eax ; this is mDURight
mov eax,[esi].DirectTriEdge@@mv2 ; move v2 into eax
sub eax,[esi].DirectTriEdge@@mv0 ; eax has (v2-v0)
shl eax,0Bh ; multiply result by 2048 for precision
divide eax,[esi].DirectTriEdge@@mDY ; eax has (v2-v0)/(y2-y0)
mov [esi].DirectTriEdge@@mDVLeft,eax ; this is mDVLeft
mov eax,[esi].DirectTriEdge@@mv1 ; move v1 into eax
sub eax,[esi].DirectTriEdge@@mv0 ; eax has (v1-v0)
shl eax,0Bh ; multiply result by 2048 for precision
divide eax,[esi].DirectTriEdge@@mDY ; eax has (v1-v0)/(y2-y0)
mov [esi].DirectTriEdge@@mDVRight,eax ; this is mDVRight
mov eax,[esi].DirectTriEdge@@mx0 ; move x0 into eax
mov [esi].DirectTriEdge@@mxLeft,eax ; mxLeft=x0
mov [esi].DirectTriEdge@@mxRight,eax ; mxRight=x0
mov eax,[esi].DirectTriEdge@@mu0 ; move u0 into eax
mov [esi].DirectTriEdge@@muLeft,eax ; muLeft=u0
mov [esi].DirectTriEdge@@muRight,eax ; muRight=u0
mov eax,[esi].DirectTriEdge@@mv0 ; move v0 into eax
mov [esi].DirectTriEdge@@mvLeft,eax ; mvLeft=v0
mov [esi].DirectTriEdge@@mvRight,eax ; mvRight=v0
ENDM
endif
getSrcDataByte MACRO ; BYTE getSrcDataByte (ui,vi)
LOCAL @@continue
mov ebx,vi ; move column into ebx
cmp ebx,bmData@@mSrcWidth ; compare column to width
jge @@continue ; if column greater than width, return
mov eax,ui ; move row into eax
cmp eax,bmData@@mSrcHeight ; compare row to height
jge @@continue ; if row greater than height, return
imul eax,bmData@@mSrcWidth ; multiply (row*width)->eax
add eax,bmData@@mSrcWidth ; add in the width
mov edx,bmData@@mSrcExtent ; move bitmap extent to edx
sub edx,eax ; subtract (row*width)+width from extent
add edx,vi ; now add in the column
mov ebx,bmData@@mlpSrcPtr ; move bitmap pointer into ebx
mov cl,byte ptr[ebx+edx] ; set the byte
@@continue:
ENDM
if 0
setDstDataByte MACRO ; setDstDataByte x,y,cl
mov ebx,y ; move column into ebx
cmp ebx,bmData@@mDstWidth ; compare column to width
jge @@continue ; if column greater than width, return
mov eax,x ; move row into eax
cmp eax,bmData@@mDstHeight ; compare row to height
jge @@continue ; if row greater than height, return
imul eax,bmData@@mDstWidth ; multiply (row*width)->eax
add eax,bmData@@mDstWidth ; add in the width
mov edx,bmData@@mDstExtent ; move bitmap extent to edx
sub edx,eax ; subtract (row*width)+width from extent
add edx,y ; now add in the column
mov ebx,bmData@@mlpDstPtr ; move bitmap pointer into ebx
mov byte ptr[ebx+edx],cl ; set the byte
@@continue:
ENDM
endif
setDstDataByte MACRO ; setDstDataByte x,y,cl
mov ebx,x ; move column into ebx
cmp ebx,bmData@@mDstWidth ; compare column to width
jge @@continue ; if column greater than width, return
mov eax,y ; move row into eax
cmp eax,bmData@@mDstHeight ; compare row to height
jge @@continue ; if row greater than height, return
imul eax,bmData@@mDstWidth ; multiply (row*width)->eax
add eax,bmData@@mDstWidth ; add in the width
mov edx,bmData@@mDstExtent ; move bitmap extent to edx
sub edx,eax ; subtract (row*width)+width from extent
add edx,x ; now add in the column
mov ebx,bmData@@mlpDstPtr ; move bitmap pointer into ebx
mov byte ptr[ebx+edx],cl ; set the byte
@@continue:
ENDM
_directTriSetSrcBitmapInfo proc near ; void setSrcBitmapInfo(WORD width,WORD height,UHUGE *lpBitmapImage)
push ebp ; save old stack frame
mov ebp,esp ; create new stack frame
push eax ; save eax register
push ebx ; save ebx register
mov eax,dword ptr[ebp+08h] ; move width into eax register
mov bmData@@mSrcWidth,eax ; move width into bmData@@mSrcWidth
mov ebx,dword ptr[ebp+0Ch] ; move height into ebx register
mov bmData@@mSrcHeight,ebx ; move height into ebx register
imul eax,ebx ; multiply width*height, result to eax
mov bmData@@mSrcExtent,eax ; (width*height) to mSrcExtent
push dword ptr[ebp+10h] ; save lpBitmapImage on stack
pop bmData@@mlpSrcPtr ; restore in mlpSrcPtr
pop ebx ; restore ebx register
pop eax ; restore eax register
pop ebp ; restore old stack frame
retn ; return near to caller
_directTriSetSrcBitmapInfo endp
_directTriSetDstBitmapInfo proc near ; void setDstBitmapInfo(WORD width,WORD height,WORD pitch,UHUGE *lpBitmapImage)
push ebp ; save old stack frame
mov ebp,esp ; create new stack frame
push eax ; save eax register
push ebx ; save ebx register
mov eax,dword ptr[ebp+10h] ; move pitch into eax register
mov bmData@@mDstPitch,eax ; move pitch into mDstPitch
mov eax,dword ptr[ebp+08h] ; move width into eeax register
mov bmData@@mDstWidth,eax ; move width into mDstWidth
mov ebx,dword ptr[ebp+0Ch] ; move height into ebx register
mov bmData@@mDstHeight,ebx ; move height into mDstHeight
imul eax,ebx ; multiply width*height, result to eax
mov bmData@@mDstExtent,eax ; move (width*height) into mDstExtent
push dword ptr[ebp+14h] ; save lpBitmapImage on stack
pop bmData@@mlpDstPtr ; restore in mlpDstPtr
pop ebx ; restore ebx register
pop eax ; restore eax register
pop ebp ; restore old stack frame
retn ; return near to caller
_directTriSetDstBitmapInfo endp
_directTriMapTexture proc near ; void directTriMapTexture(DirectTriEdge *pEdge)
LOCAL y:DWORD,x:DWORD,du:DWORD,dv:DWORD,ui:DWORD,vi:DWORD=LocalLength ; local variables for proc
push ebp ; save prior stack frame
mov ebp,esp ; create new frame
sub esp,LocalLength ; make room for local variables
pushad ; save all general purpose registers
mov esi,[ebp+08h] ; move pEdge to esi register
initialize ; initialize the edge
mov eax,[esi].DirectTriEdge@@my0 ; move y0 into eax
mov y,eax ; initialize y with y0
@@verticalLoop: ; beginning of vertical loop
mov ecx,[esi].DirectTriEdge@@my1 ; move y1 into ecx
cmp y,ecx ; compare y to y1
jg @@verticalLoopEnd ; if y>y1 then we're done
scanline ; perform scanline on the horizontal
increment ; increment along the vertical
jmp @@verticalLoop ; continue execution
@@verticalLoopEnd: ; end loop sync address
popad ; restore all general purpose registers
add esp,LocalLength ; remove local variables from frame
pop ebp ; restore prior stack frame
retn ; return near to caller
_directTriMapTexture endp
public _directTriSetSrcBitmapInfo
public _directTriSetDstBitmapInfo
public _directTriMapTexture
END