;----------------------------------------------------------------------------
; Texture Mapping assembler modul
; Copyright (c) 1994,95 by J.E. Hoffmann
; All rights reserved
;----------------------------------------------------------------------------
  TITLE TPOLY.ASM


  MODEL SMALL


  IDEAL
  NOJUMPS
  LOCALS @@



  INCLUDE "_VGAXASM.INC"



  STRUC TLine
    x     dw ?
    Tx    dd ?
    Ty    dd ?
    Ticx  dd ?
    Ticy  dd ?
    ddy   dw ?
    ddx   dw ?
    icx   dw ?
    error dw ?
    yTo   dw ?
    xTo   dw ?
  ENDS


  STRUC TEntry
    x     dw ?
    Tx    dd ?
    Ty    dd ?
  ENDS




  DATASEG
    EXTRN _VirtualVSeg :Word
    EXTRN xSize       :Word

    EXTRN TexXSize    :Word
    EXTRN TexYSize    :Word

    LL          TLine ?
    RL          TLine ?
    yMin        dw ?
    yMax        dw ?
    min         dw ?
    L           dw ?
    R           dw ?
    yi          dw ?
    K           dw ?

    k1          TEntry ?
    k2          TEntry ?

    DeltaX      dw ?
    uicx        dd ?
    uicy        dd ?
    TextureSeg  dw ?


  CODESEG


  PUBLIC CxyTexturedPoly
  P386N



;ננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננ
; procedure CxyTexturedPoly(P,T :Pointer; Count :Word; Texture :Pointer);
;ננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננננ
  PROC CxyTexturedPoly FAR
       ARG Texture:DWord, Count:Word, T:DWord, P:DWord = @@return
       enter  0,0
       cld
       mov    ax,[WORD PTR 2+Texture]
       mov    [TextureSeg],ax
       mov    [min],-1
       mov    [yMin],200
       mov    [yMax],-1

       xor    cx,cx
       les    si,[P]
       mov    bx,si
       inc    si
       inc    si
  @@11:
       mov    ax,[es:si]
       cmp    ax,[yMin]
       jnl    @@12
       mov    [yMin],ax
       mov    [min],cx
  @@12:
       mov    ax,[es:si]
       cmp    ax,[yMax]
       jnge   @@13
       mov    [yMax],ax
  @@13:
       add    si,4
       inc    cx
       cmp    cx,[Count]
       jb     @@11
       cmp    [yMin],199
       jg     @@71
       cmp    [yMax],0
       jl     @@71

       mov    ax,199
       cmp    [yMax],ax
       jle    @@14
       mov    [yMax],ax
  @@14:
       mov    ax,[yMin]
       mov    [yi],ax

       mov    ax,[min]
       mov    [L],ax
       mov    [R],ax
       shl    ax,2
       add    bx,ax
       mov    ax,[es:bx]
       mov    [LL.x],ax
       mov    [RL.x],ax

       call   _InitLeft
       call   _InitRight

       mov    ax,[yMin]
       inc    ax
       cmp    ax,[yMax]
       jg     @@71
       mov    [yi],ax
  @@21:
       mov    ax,[LL.x]
       mov    dx,[LL.ddy]
       mov    bx,[LL.error]
       cmp    bx,[LL.ddx]
       jge    @@33
       cmp    ax,[LL.xTo]
       je     @@33
  @@31:
       add    bx,dx
       add    ax,[LL.icx]
       mov    [LL.error],bx
       mov    [LL.x],ax
       cmp    bx,[LL.ddx]
       jge    @@32
       cmp    ax,[LL.xTo]
       jne    @@31
  @@32:
       mov    [LL.x],ax
  @@33:
       sub    bx,[LL.ddx]
       mov    [LL.error],bx
       mov    eax,[LL.Ticx]
       add    [LL.Tx],eax
       mov    eax,[LL.Ticy]
       add    [LL.Ty],eax

       mov    ax,[RL.x]
       mov    dx,[RL.ddy]
       mov    bx,[RL.error]
       cmp    bx,[RL.ddx]
       jge    @@43
       cmp    ax,[RL.xTo]
       je     @@43
  @@41:
       add    bx,dx
       add    ax,[RL.icx]
       mov    [RL.error],bx
       mov    [RL.x],ax
       cmp    bx,[RL.ddx]
       jge    @@42
       cmp    ax,[RL.xTo]
       jne    @@41
  @@42:
       mov    [RL.x],ax
  @@43:
       sub    bx,[RL.ddx]
       mov    [RL.error],bx
       mov    eax,[RL.Ticx]
       add    [RL.Tx],eax
       mov    eax,[RL.Ticy]
       add    [RL.Ty],eax

       cmp    [yi],0
       jl     @@60
       push   ds
       pop    es
       mov    si,OFFSET LL
       mov    di,OFFSET k1
       movsd
       movsd
       movsw
       mov    si,OFFSET RL
       mov    di,OFFSET k2
       movsd
       movsd
       movsw
       call   TextureVLine

  @@60:
       mov    ax,[yi]
       cmp    [LL.yTo],ax
       jne    @@61
       call   _InitLeft
       mov    ax,[yi]
  @@61:
       cmp    [RL.yTo],ax
       jne    @@62
       call   _InitRight
  @@62:
       inc    [yi]
       mov    ax,[yMax]
       cmp    [yi],ax
       jle    @@21
  @@71:
       leave
       ret    @@return
  ENDP



;---------------------------------------------------------------------------
; procedure TextureVLine
;---------------------------------------------------------------------------
  PROC TextureVLine NEAR
       push   ds
       push   bp

       movzx  ebx,[k2.x]
       sub    bx,[k1.x]
       jns    @@01
       neg    bx
  @@01:
       inc    bx
       mov    [DeltaX],bx

       mov    eax,[k2.Tx]
       sub    eax,[k1.Tx]
       cdq
       idiv   ebx
       mov    [uicx],eax

       mov    eax,[k2.Ty]
       sub    eax,[k1.Ty]
       cdq
       idiv   ebx
       mov    [uicy],eax

;------------------------------
       movsx  eax,[k1.x]
       cmp    ax,[k2.x]
       jnl    @@c3

       movsx  eax,[k1.x]
       or     ax,ax
       jnl    @@c1
       push   eax
       imul   [uicx]
       sub    [k1.Tx],eax
       pop    eax
       imul   [uicy]
       sub    [k1.Ty],eax
       mov    [k1.x],0
  @@c1:
       movsx  eax,[k2.x]
       cmp    ax,319
       jng    @@c2
       sub    eax,319
       push   eax
       imul   [uicx]
       sub    [k2.Tx],eax
       pop    eax
       imul   [uicy]
       sub    [k2.Ty],eax
       mov    ax,319
       mov    [k2.x],ax
  @@c2:
       cmp    [k1.x],ax
       jnle   @@40
       jmp    @@c6
  @@c3:

       movsx  eax,[k1.x]
       cmp    ax,319
       jng    @@c4
       sub    eax,319
       push   eax
       imul   [uicx]
       add    [k1.Tx],eax
       pop    eax
       imul   [uicy]
       add    [k1.Ty],eax
       mov    [k1.x],319
  @@c4:
       movsx  eax,[k2.x]
       or     ax,ax
       jnl    @@c5
       push   eax
       imul   [uicx]
       add    [k2.Tx],eax
       pop    eax
       imul   [uicy]
       add    [k2.Ty],eax
       xor    ax,ax
       mov    [k2.x],ax
  @@c5:
       cmp    ax,[k1.x]
       jnle   @@40
  @@c6:

       mov    bx,[k1.x]
       sub    bx,[k2.x]
       jns    @@11
       neg    bx
  @@11:
       inc    bx
       mov    [DeltaX],bx
;--------------------------------------------------------------------------

       mov    eax,[k2.Tx]
       cmp    eax,[k1.Tx]
       jng    @@21

       movzx  edi,[k1.x]
       mov    ax,[xSize]
       mul    [yi]
       add    di,ax

       mov    ax,[WORD PTR 2+k1.Ty]
       mul    [TexXSize]
       add    ax,[WORD PTR 2+k1.Tx]
       add    ax,[WORD PTR Texture]
       movzx  esi,ax

       mov    eax,[k2.Ty]
       cmp    eax,[k1.Ty]
       jng    @@12

       mov    ax,[TexXSize]
       mul    [WORD PTR 2+uicy]
       mov    bp,[WORD PTR 2+uicx]
       add    bp,ax

       mov    dx,[TexXSize]
       jmp    @@13
  @@12:
       neg    [uicy]
       mov    ax,[TexXSize]
       mul    [WORD PTR 2+uicy]
       mov    bp,[WORD PTR 2+uicx]
       sub    bp,ax

       mov    dx,[TexXSize]
       neg    dx
  @@13:
       push   1
       jmp    @@24
  @@21:
       neg    [uicx]
       movzx  edi,[k2.x]
       mov    ax,[xSize]
       mul    [yi]
       add    di,ax

       mov    ax,[WORD PTR 2+k2.Ty]
       mul    [TexXSize]
       add    ax,[WORD PTR 2+k2.Tx]
       add    ax,[WORD PTR Texture]
       movzx  esi,ax

       mov    eax,[k2.Ty]
       cmp    eax,[k1.Ty]
       jng    @@22
       mov    ax,[TexXSize]
       mul    [WORD PTR 2+uicy]
       mov    bp,[WORD PTR 2+uicx]
       sub    bp,ax
       mov    dx,[TexXSize]
       neg    dx
       jmp    @@23
  @@22:
       neg    [uicy]
       mov    ax,[TexXSize]
       mul    [WORD PTR 2+uicy]
       mov    bp,[WORD PTR 2+uicx]
       add    bp,ax
       mov    dx,[TexXSize]
  @@23:
       push   -1
  @@24:

       movzx  ebx,[WORD PTR uicx]
       rol    ebx,16
       rol    ebp,16
       mov    bp,[WORD PTR uicy]
       rol    ebp,16

       add    edi,ebx
       adc    esi,ebp
       jnc    @@30
       add    si,dx
  @@30:
       pop    bx

       mov    ax,[k1.x]
       cmp    ax,[k2.x]
       jng    @@31
       neg    bx
  @@31:
       mov    cx,[DeltaX]
       mov    es,[_VirtualVSeg]
       mov    ds,[TextureSeg]
  @@32:
       mov    al,[si]
       mov    [es:di],al
       add    edi,ebx
       adc    esi,ebp
       jnc    @@33
       add    si,dx
  @@33:
       loop   @@32
  @@40:
       pop    bp
       pop    ds
       ret
  ENDP



;----------------------------------------------------------------------------
; procedure InitLeft;
;----------------------------------------------------------------------------
  PROC _InitLeft NEAR
       les    si,[P]
  @@11:
       mov    bx,[L]
       mov    [K],bx
       shl    bx,2
       mov    ax,[es:si+bx]
       mov    [LL.x],ax

       mov    bx,[L]
       cmp    bx,0
       jne    @@12
       mov    bx,[Count]
  @@12:
       dec    bx
       mov    cx,bx
       mov    [L],bx

       shl    bx,2
       mov    ax,[es:si+bx+2]
       mov    [LL.yTo],ax
       sub    ax,[yi]
       jns    @@13
       neg    ax
  @@13:
       mov    [LL.ddy],ax
       cmp    ax,0
       jne    @@14
       cmp    cx,[min]
       je     @@16
       jmp    @@11
  @@14:
       mov    ax,[es:si+bx]
       mov    [LL.xTo],ax

       les    si,[T]
       mov    bx,[k]
       shl    bx,2
       mov    ax,[es:si+bx]
       shl    eax,16
       mov    [LL.Tx],eax

       mov    ax,[es:si+bx+2]
       shl    eax,16
       mov    [LL.Ty],eax

       mov    [LL.icx],1
       mov    ax,[LL.xTo]
       sub    ax,[LL.x]
       jns    @@15
       neg    [LL.icx]
       neg    ax
  @@15:
       mov    [LL.ddx],ax
       mov    [LL.error],0

       mov    bx,[L]
       shl    bx,2
       mov    ax,[es:si+bx]
       shl    eax,16
       sub    eax,[LL.Tx]
       cdq
       movzx  ecx,[LL.ddy]
       idiv   ecx
       mov    [LL.Ticx],eax

       mov    ax,[es:si+bx+2]
       shl    eax,16
       sub    eax,[LL.Ty]
       cdq
       movzx  ecx,[LL.ddy]
       idiv   ecx
       mov    [LL.Ticy],eax
  @@16:
       ret
  ENDP



;----------------------------------------------------------------------------
; procedure InitRight;
;----------------------------------------------------------------------------
  PROC _InitRight NEAR
       les    si,[P]
  @@11:
       mov    dx,[K]
       mov    bx,[R]
       mov    [K],bx
       shl    bx,2
       mov    ax,[es:si+bx]
       mov    [RL.x],ax

       mov    bx,[R]
       mov    ax,[Count]
       dec    ax
       cmp    bx,ax
       jne    @@12
       mov    bx,-1
  @@12:
       inc    bx
       mov    cx,bx
       mov    [R],bx

       shl    bx,2
       mov    ax,[es:si+bx+2]
       mov    [RL.yTo],ax
       sub    ax,[yi]
       jns    @@13
       neg    ax
  @@13:
       mov    [RL.ddy],ax
       cmp    ax,0
       jne    @@14
       cmp    cx,[min]
       je     @@16
       jmp    @@11
  @@14:
       mov    ax,[es:si+bx]
       mov    [RL.xTo],ax

       les    si,[T]
       mov    bx,[k]
       shl    bx,2
       mov    ax,[es:si+bx]
       shl    eax,16
       mov    [RL.Tx],eax

       mov    ax,[es:si+bx+2]
       shl    eax,16
       mov    [RL.Ty],eax

       mov    [RL.icx],1
       mov    ax,[RL.xTo]
       sub    ax,[RL.x]
       jns    @@15
       neg    [RL.icx]
       neg    ax
  @@15:
       mov    [RL.ddx],ax
       mov    [RL.error],0

       mov    bx,[R]
       shl    bx,2
       mov    ax,[es:si+bx]
       shl    eax,16
       sub    eax,[RL.Tx]
       cdq
       movzx  ecx,[RL.ddy]
       idiv   ecx
       mov    [RL.Ticx],eax

       mov    ax,[es:si+bx+2]
       shl    eax,16
       sub    eax,[RL.Ty]
       cdq
       movzx  ecx,[RL.ddy]
       idiv   ecx
       mov    [RL.Ticy],eax
  @@16:
       ret
  ENDP
  END

