Napisalem sobie chyba najbardziej prosta animacje jaka da sie zrobic czyli cykliczne przesuwanie pixela po osi x na ekrania i chce to zgrac z dwubuforwaniem. Oczywiscie cos poszlo nie tak... sama animacja zdaje sie dzialac, zmiana fizycznego i logiczengo ekranu tez, ale animacja i tak nie jest plynna i czasem przeskakuje. Tak jak by buforowanie zupelnie nie dzialalo. Jako, iz szukam juz pol weekendu bezskutecznie bledu to moze Wam sie cos nasunie co robie nie tak.
Moj prosty kod z komentarzami:
; wlaczenie trybu super user
clr.l -(a7)
move.w #32,-(a7)
trap #1
addq.l #6,a7
move.l d0,_old_stack
_old_stack dc.l 0
; wyliczenie adresu fizycznego ekranu
move.l #screenbuffer+255,d0
; wyrownanie do rownych 256b
sub.b d0,d0
; ustawienie adres ekranu fizycznego do phyScr
move.l d0,phyScr
; znajdujemy obszar za fizycznym ekranem na ekran logiczny
addi.l #160*200,d0
; ustawiamy adres ekranu logicznego do logScr
move.l d0,logScr
; mowimy ST ze wyswetlany ekran zaczyna sie od phyScr
move.l phyScr,d0
lsr.w #8,d0
move.l d0,$ffff8200.w
; ustawienia koloru tla i animowanego pixela
move.w #$000,$ff8240
move.w #$777,$ff8244
; pozycja animowanego pixela
pos_x dc.w 1
pos_y dc.w 100
drawStart
; czekamy na vsync
move.w #37,-(a7)
trap #14
addq.l #2,a7
; zamieniamy ekrany logiczny z fizycznym (stary logiczny staje sie fizycznym i odwrotnie)
move.l logScr,d0
move.l phyScr,logScr
move.l d0,phyScr
; mowimy ST ze wyswetlany ekran zaczyna sie od phyScr
lsr.w #8,d0
move.l d0,$ffff8200.w
; adres logicznego ekranu wrzucamy do A0 - tam bedzie rysowac aplikacja
move.l logScr,a0
; ZAMIEN POWYZSZY BLOK NA PONIZSZY DLA WERSJI BEZ BUFFERINGU
;move.l phyScr,d0
;lsr.w #8,d0
;move.l d0,$ffff8200.w
;move.l phyScr,a0
; prosta animacja pixela na osi X
; wyczyszczenie starej pozycji pixela na logicznym ekranie
; poniewaz rysujemy na 2 ekranam przemiennie
; to stara pozycja na ekranie logicznym to pos_x-1
; bo pos_x to aktualna pozycja pixela na ekranie fizycznym
move.w pos_x,d4
; ZAKOMENTUJ PONIZEJ DLA WERSJI BEZ BUFFERINGU
subi.w #1,d4
cmp #-1,d4
; jesli poprzenia pozycja to -1 to znaczy ze mamy wyczyscic ostatni pixel linii
bne notTooLess
move.w #319,d4
notTooLess
move.w d4,d0
move.w pos_y,d1
; wywolanie procedury czyszczacej pixel d0,d1
; ZAKOMENTUJ BY NIE CZYSCIC OBRAZU
jsr clrPixelD0D1
; postawienie pixela w nowej przesunietej w prawo pozycji
addi #1,pos_x
cmp #320,pos_x
; jesli nowa pozycja to 320 to stawiamy pixel na poczatku linii
bne notTooBig
clr.w pos_x
notTooBig
move.w pos_x,d0
move.w pos_y,d1
; wywolanie procedury stawiajacej pixel d0,d1
jsr drawPixelD0D1
; petla nieskonczona
jmp drawStart
; procedura rysujaca pixel w do,d1 zakadajac ze pamiec ekranu zaczyna sie w A0
; rysowanie uzywa tylko pierwszego bit plane dla uproszczenia
drawPixelD0D1
; oblicznie adresu paczatku linii d1 w adresie a1
move.l a0,a1
mulu #160,d1
adda.l d1,a1
clr.l d3
; obliczamy offset poczatku Plane 1 zawierajacego pixel i przesuwamy o niego a1
move.w d0,d3
lsr.w #4,d3
lsl.w #3,d3
adda.l d3,a1
; obliczamy index pixela w bitplane
and.w #$f,d0
; zamieniamy index pixela na numer odpowiadajacego bitu (sa odwrocone) i umieszczamy do w d0
neg.w d0
add #$f,d0
; ustawiamy bit odpowiadajacy pixelowi w Plane 1
move.l (a1),d1
bset d0,d1
move.l d1,(a1)
rts
; procedura czyszczaca pixel w do,d1 zakadajac ze pamiec ekranu zaczyna sie w A0
clrPixelD0D1
; analogicznie jak rysowanie powyzej
move.l a0,a1
mulu #160,d1
adda.l d1,a1
clr.l d3
move.w d0,d3
lsr.w #4,d3
lsl.w #3,d3
adda.l d3,a1
and.w #$f,d0
neg.w d0
add #$f,d0
move.l (a1),d1
bclr d0,d1
move.l d1,(a1)
rts
; adres fizycznego ekranu
phyScr ds.l 1
; adres logicznego ekranu
logScr ds.l 1
; pamiec ekranu
screenbuffer equ *
Aplikacja jak widac jest trywialna. Przeuwam pixel o 1 w prawo, i czyszcze ostatnia pozycje na danym ekranie (jako iz mam 2 ekrany to na kazdym ekranie efektywnie animuje co 2 pixele). Manipulujac zakomentowanym kodem mozna wylaczyc buforowanie i w sumie efekt jest podobny. Mozna tez wylaczyc czyszczenie poprzedniej pozycji pixela i wtedy widac, ze samo rysowanie odbywa sie raczej prawidlowo i widac podmieniajace sie bardzo szybko ekrany z naprzemienna pozycja pixeli.
Macie jakis pomysl co robie nie tak? HELP!
--------
Atari 65XE + Ultimate 1MB + Stereo + SIO2SD | Atari 520STE + 4MB + UltraSatan | Atari Falcon 030 + CT60e + 14MB ST + 256MB TT + 68882 + CF + Netusbee | Amiga 500 + 1MB + Gotek | Amiga 600 + 2MB Chip + 8MB Fast + CF