; Rotozoomer in 204 bytes (final version is 128 bytes) ; 20 Feb 2000, Mikael Kalms ; ; Clean implementation, no particular tricks are used. ; A sine table is generated, then a texture is rendered ; by drawing a few circles with pseudorandom positions. ; After that, the program performs 2d rotation and parallax ; scrolling over the texture. ; ; Assembles with TASM. b EQU byte ptr w EQU word ptr d EQU dword ptr LOCALS @@ .MODEL TINY .CODE .386 ORG 100h start: ; Set screenmode (320x200x256) and palette (greyscale) mov ax,13h int 10h mov dx,03c8h xor ax,ax out dx,al inc dx @@pal: out dx,al inc al jnz @@pal ; Setup auxiliary segments mov ax,cs add ah,10h mov fs,ax ; Texture add ah,10h mov gs,ax ; Sine table push 0a000h pop es ; Graphics memory ; Generate sine table and clear texture xor bx,bx fldz @@gensine: fld st fsin fimul w sinescale fistp w gs:[bx] mov w fs:[bx],0 fadd sinestep inc bx inc bx jnz @@gensine fstp st ; Generate texture mov di,5*2 @@circle: mov si,[di+100h] xor bx,bx @@pix: mov al,bl imul al xchg cx,ax mov al,bh imul al add ax,cx cmp ax,50*50-1 ja @@outside mov b fs:[bx+si],dl @@outside: inc bx jnz @@pix dec di dec di jnz @@circle ; Mainloop @@frame: call drawrot2d ; Draw the magic mov ah,1 ; Check for keypress int 16h jz @@frame ; Set 80x25 textmode mov ax,3 int 10h ; Return to DOS ret drawrot2d: mov bx,angle ; Get texture gradients for mov ax,gs:[bx] ; current rotation angle mov dudx,ax mov si,gs:[bx+4000h] xor dx,dx xor bp,bp xor di,di mov cx,200 @@y: pusha mov cx,320 @@x: add bp,si ; Step horizontally in texture add dx,dudx mov bx,bp mov bl,dh mov al,5*4 ; Iterate through layers, @@miss: ; looking for a hit push bx add bx,scroll cmp b fs:[bx],0 pop bx jnz @@hit add bx,bx ; Next layer is twice as sub al,1*4 ; far away jnz @@miss @@hit: stosb loop @@x popa add di,320 sub bp,dudx ; Step vertically in texture add dx,si loop @@y add b angle+1,1 add b scroll+1,4 ret angle LABEL WORD sinescale dw 0100h sinestep dd 0.0001917476 scroll dw ? dudx dw ? END start