Newer
Older
Import / research / 4k-asm / render_backup_3.asm
org      100h 
section .text 

%macro init_gfx 0
  mov    ax,0x13
  int    0x10
%endmacro

%macro usleep 2  ; usecs hi, lo
  mov    ax,0x8600
  mov    cx, %1
  mov    dx, %2
  int    0x15
%endmacro

%macro create_texture 0
  mov    di,texture
  mov    dx,4
  mov    bx,80
  mov    cx,20
  mov    ax,1
%%again:
  rep    stosb
  mov    cx,ax
  mov    ax,1
  sub    ax,cx
  mov    cx,20
  dec    bx
  jnz    %%again
  mov    cx,ax
  mov    ax,1
  sub    ax,cx
  mov    bx,80
  mov    cx,20
  dec    dx
  jnz    %%again
%endmacro

%macro blit 5    ;  src, x,y, w,h
  mov    ax,0xA000
  mov    es,ax
  mov    si,%1
  mov    di,%2+320*%3
  mov    bx,%4
  mov    cx,%5
%%again:
  rep    movsb
  add    di,320-%4
  mov    cx,%4
  dec    bx
  jnz    %%again
%endmacro

%macro cls 0
  xor    di,di
  mov    al,50 ; 200
 cl1:
  mov    dx,0x3c8
  out    dx,al ; 0x3c8 ;al
  inc    dx
  ; mov    ah,al
  ; shr    al,2
  out    dx,al ; 0x3c8 ;al
  out    dx,al ; 0x3c8 ;al
  out    dx,al ; 0x3c8 ;al
  mov    cx,320*4  ; *200
  ; mov    al,ah
  rep    stosb
  dec    al
  jnz    cl1
%endmacro
  
%macro puts 1  ; str
  mov    dx,%1
  mov    ah,0x09
  int    0x21
%endmacro

%macro exit 0
  int    0x20
%endmacro

%macro angle_setup 0
  fild   word [angle]
	fild   word [Rads]
  fdivp               ; deg2rad
  fsincos             ; sin(a) and cos(a)
  fstp   dword [sine]
  fstp   dword [cosine]
%endmacro

%macro transform_point 0
  ; d - dist of screen from COP
  ; x / z   =   sx / d
  ; d * (x/z) =  screen-x


  fild   word [pntX] ; [si+Points-4] ; x
  fisub  word [Size]
  ;fimul  word [Scale]
  fst    st1
  fild   word [pntY]
  fisub  word [Size]
  ;fimul  word [Scale]
  ;fild   word [si+Points-6] ; y
  
  call   rotate

  ; x,y
  
  ;fst    st2
  ;fst    st3
  ;fstp   st4
  ; y,_,_,x
  ; fimul  word [Dist]
  fistp  dword [tmp1d]
  
  ;fistp  dword [tmp2d]
  ; tmp1d = -y * sin(a) + x * cos(a))
  ; tmp2d = x * sin(a) + y * cos(a)

  ;fild   word [tmp2d] ; y (tmp2d)
  ;add    si,4
  fst    st1
  fild   word [pntZ] 
  fisub  word [Size]
  ;fimul  word [Scale]
  ;fild   word [si+Points-2] ; y

  call   rotate
  ; t3,t4,x

  ; fiadd  150

  fistp  dword [tmp3d]
  
  ;fimul  word [Dist]
  ;fidiv  dword [tmp3d]
  fistp  dword [tmp4d]
  ; tmp3d = -z * sin(a) + y * cos(a)
  ; tmp4d = y * sin(a) + z * cos(a)


  ;fld    st4
  ;fistp  dword [tmp1d]


  mov    cx,[tmp3d] ; [si+Points-2] ; z
  add    cx,180
  
  ;mov   cx,[si+Points-2] ; z

  ; X
  mov    ax,0
  mov    ax,[tmp1d] ; x
  
  call   project_worker
  ;mov    dx,45
  ;imul   dx
  ;idiv   cx
  add    ax,160
  
  mov    di,ax

  ; Y
  mov    ax,[tmp4d] ; [tmp2d] ; y
  ;mov    ax,[tmp2d] ; y
  
  call   project_worker
  ;mov    dx,45
  ;imul   dx
  ;idiv   cx
  add    ax,100
 
;  lea    eax,[eax*4+eax]
;  shl    ax,6
  mov    dx,320
  imul   dx
  add    di,ax
  
  ; draw
  sub    cl,140
  mov    al,cl
  ; mov    ax,1
  stosb
  ;stosb
  ;add    di,318
  ;stosb
  ;stosb
%endmacro

start:
  ; program code
  init_gfx

  ; create_texture
  ; blit  texture, 100, 100, 80, 80
  ; usleep 0x1,0xFFFF
  ; cls
  ; exit

  ; I think ss might already be same as ds
  push   ds
  pop    ss

  mov    ax,0xA000
  mov    es,ax
  
; loop for different angles
loop1:
  
  ; usleep 0,0x0080

  mov    dx,0x3da
  in     al,dx
  and    al,8
  jnz    loop1 ; wait_retrace1


  cls

  angle_setup

;; loop over the points
;  mov    si,24+24
;  ;mov    si,8  ; idea is use bit0, bit1, bit2   for sign of the point's x,y,z coords respectively
;  ; 40x40x40 = 64000
;more_pnts:
;  transform_point
;  ; call   xform_display
;  sub    si,10
;  jne    more_pnts

  mov    word [pntZ],80
moreZ:
  mov    word [pntY],80
moreY:
  mov    word [pntX],80
moreX:
  transform_point
  dec    word [pntX]
  jnz    moreX
  dec    word [pntY]
  jnz    moreY
  dec    word [pntZ]
  jnz    moreZ

  dec    word [angle]
  jnz    loop1
  exit

;xform_display:
;  transform_point
;  ret

project_worker:
  mov    dx,150 ; 45
  imul   dx
  idiv   cx
  ;add    ax,100
  ret

rot_worker:
  fld    dword [sine]
  ; cos,y, x, x, y
  fmulp
  ; y*cos, x, x, y
  fld    dword [cosine]
  ; sin, y*cos, x, x, y
  fmulp  st2
  ret


rotate:
  ; mov    bp,sp
  ;fldz


  fst    st3
  call   rot_worker
  ; ; y, x, x, y
  ; fld    dword [sine]
  ; ; cos,y, x, x, y
  ; fmulp
  ; ; y*cos, x, x, y
  ; fld    dword [cosine]
  ; ; sin, y*cos, x, x, y
  ; fmulp  st2
  ; ; y*cos, x*sin, x, y
  fsubp
  ; y*cos - x*sin, x, y

  fstp   st3
  call   rot_worker
  ; ; x, y, y*cos - x*sin
  ; fld    dword [sine]
  ; ; cos, x, y, y*cos - x*sin
  ; fmulp 
  ; ; x*cos, y, y*cos - x*sin
  ; fld    dword [cosine]
  ; ; sin, x*cos, y, y*cos - x*sin
  ; fmulp  st2
  ; ; x*cos, y*sin, y*cos - x*sin
	faddp
  ; x*cos + y*sin, y*cos - x*sin
  ; 1) sine * [bp+4] - cosine * [bp+2]
  ; 0) sine * [bp+2] + cosine * [bp+4]

  retn   ; 4


section .data
  ;Hello      db   'Hello world', 0xD, 0xA, '$'
  angle      dw    360
  Rads       dw    58
;  Dist       dw    45
  Size       dw    40
;  Points     dw    -50,-50,-50,  -50,50,-50,   -50,50,50,   -50,-50,50
;  Points2    dw     50,-50,-50,   50,50,-50,    50,50,50,    50,-50,50


section .bss
  ; uninitialized data
  pntX:      resw 1
  pntY:      resw 1
  pntZ:      resw 1
  tmp1w:     resw 1
  tmp2w:     resw 1
  tmp0d:     resd 1
  tmp1d:     resd 1
  tmp2d:     resd 1
  tmp3d:     resd 1
  tmp4d:     resd 1
  sine:      resd 1
  cosine:    resd 1
  texture:   resb 6400    ; 80x80
  offscreen: resb 64000