Search code examples
assemblynasminterruptdos

Assembler plump/water animation


I am new in assembler and I am looking for easy solution how to insert a loop in my code. Can you guys give me a tip or answer? I found some articles on google and I cannot understand them cuz I am dumb, though. I've to do a projeckt: animation of water, http://kino-ap.eng.hokudai.ac.jp/all-LiF.gif http://thumbs.dreamstime.com/z/circular-splash-drop-water-blue-forming-circle-waves-liquid-surface-37560386.jpg

I want to use a Circle so i found this code

; nasm -O999 -o kolo.com -f bin kolo.asm

org 100h

    mov ax, 13h
    int 10h

    mov ax, 0a000h
    mov es, ax

    mov cx, 360

    finit
    fldpi
    fild word [sto80]

    fdivp st1, st0        ; pi/180

    fld1
    fild word [r]        ; r, 1, pi/180
    fldz            ; angle=0, r, 1, pi/180

    mov al, 15

draw:                 
    fld st0            ; angle, angle, r, 1, pi/180

    fmul st4        ; angle in radius
    mov di, 100*320 + 160    ; middle of screen

    fsin            ; sin(angle), angle, r, 1, pi/180
    fmul st2        ; sin(angle)*r, angle, r, 1, pi/180

    fistp word [height]    ; angle, r, 1, pi/180

    fld st0            ; angle, angle, r, 1, pi/180
    fmul st4        ; angle in radius
    fcos            ; cos(angle),angle, r, 1, pi/180
    fmul st2        ; r*cos(angle), angle, r, 1, pi/180

    fistp word [width]    ; angle, r, 1, pi/180

    add di, [width]        ; add the horizontal length

    mov dx, [height]
    mov bx, dx
    shl dx, 8
    shl bx, 6
    add dx, bx        ; dx = height*320

    sub di, dx        ; We subtract the vertical distance

    mov [es:di], al        ; show pixel

    fadd st0, st2        ; angle += 1

    dec cx
    jnz draw

    finit

    xor ah, ah
    int 16h

    mov ax, 3
    int 10h

    mov ax, 4c00h
    int 21h

r    dw    50
width    dw    0 
height    dw    0
sto80    dw    180 

For now i want to add one circle which will be increased . I need to add a loop that will increment r (for r=0;r<300;r++. After r==300 change r=0) and redraw it and maybe hide last circle pixels?


Solution

  • You should not let your radius get bigger than 99 because the dimensions of the screen are 320x200 and you are drawing from the center of the screen with no checks on the outcome of the address calculation in DI register.

    To get the desired loop make the following changes:

     org 100h
     mov ax, 0013h
     int 10h
     mov ax, 0a000h
     mov es, ax
    NextCircle:           ; Add this
     mov cx, 360
    
     ...
    
     fadd st0, st2        ; angle += 1
     dec cx
     jnz draw
     xor ah, ah           ; Maybe add this (To wait between circles)
     int 16h              ; Maybe add this (To wait between circles)
     inc word [r]         ; Add this
     cmp word [r], 100    ; Add this
     jb NextCircle        ; Add this
     finit
     xor ah, ah
     int 16h
     mov ax, 0003h
     int 10h
     mov ax, 4c00h
     int 21h
    

    To hide the previous circle you can redraw it using the black color (AL=0).