Tajemnice ATARI

PISZEMY DEMO

   Tak, jak obiecaliśmy ostatnio, w tym odcinku naszego cyklu zaprezentujemy cztery przykłady programów wykorzystujących przerwanie Display List.

Program 1

    Co pewien czas w czasopismach poświęconych komputerowi Atari pojawiają się programy tworzące najpopularniejszą, ruchomą "tęczę". Programy te są zazwyczaj długie i wykorzystują dodatkowe komórki pamięci, a czasami nawet całe tablice wartości kolorów. Dlatego też zdecydowaliśmy się zaprezentować jedno z najkrótszych rozwiązań tego problemu.
Program   Equ $8800

List_mem  Equ %00000110
List_err  Equ %00000101 
Code_mem  Equ %00010000
Code_dsk  Equ %00100000

Colpf2    Equ $D018
Dliv      Equ $0200 
Dlptrs    Equ $0230 
Rtclok    Equ $12
Nmien     Equ $D40E 
Wsync     Equ $D40A

Pom       Equ $F0

       Opt List_err+Code_mem
          Org Program

          Jmp Init

Przerw    Pha
          Txa
          Pha
          Tya
          Pha
          Ldx #$D0
          Ldy Rtclok+$02
L1        Sty Colpf2
          Sty Wsync
          Iny
          Dex
          Bne L1

          Pla
          Tay
          Pla
          Tax
          Pla
          Rti

Init      Lda Dlptrs
          Sta Pom 
          Lda Dlptrs+1
          Sta Pom+1
          Lda Dliv
          Pha
          Lda Dliv+1
          Pha
          Ldy #$00
          Lda (Pom),y
          Ora #$80
          Sta (Pom),y
          Ldx Przerw
          Lda #$C0
          Stx Dliv
          Sty Dliv+1
          Sta Nmien
          Jsr Klawisz
          Lda #$00
          Sta Nmien
          Sei
          Pla
          Sta Dliv+1
          Pla
          Sta Dliv
          Lda #$FF
          Sta Nmien
          Cli
          Rts

Kolory    Dta B($00)

          End of file
   Zarówno w tym jak i w kolejnych programach korzystamy ze znanej procedury Klawisz oczekującej na wciśnięcie dowolnego klawisza, oraz z dotąd nie znanej procedury Init.

    Pierwsza część procedury Init ustawia wektor przerwania Display List oraz inicjuje go. Po powrocie z procedury Klawisz przywracana jest wartość wektora Dliv i na tym procedura się kończy.

    A co się dzieje w procedurze przerwania (etykieta Przerw)? Po odłożeniu wszystkich rejestrów na stos wykonywana jest jedna pętla, która realizuje efekt tęczy. Rejestr X służy jako licznik pętli, natomiast rejestr Y zachowuje wartość koloru linii. Dzięki temu, że jest on zwiększany w każdym przebiegu pętli, kolory układają się w tęczę. Pozostaje jeszcze do wyjaśnienia rola rejestru Rtclok.

    Rejestr Rtclok ($12) jest to 3-bajtowy zegar czasu rzeczywistego. W momencie włączenia komputera (lub "zimnego startu") jest on zerowany. Następnie w każdym obiegu przerwania systemowego VBLK jest on zwiększany o jeden. Jak już wiemy przerwanie VBLK wykonywane jest 50 razy na sekundę, czyli z taką samą prędkością, jak przerwanie Display List. Dzięki temu najmłodszy bajt zegara ($14) zwiększa się po wykonaniu procedury przerwania. Wracając do naszego przykładu: kolor pierwszej linii pobierany jest z Rtclok'a.

Program 2

   Poniższy program realizuje również tęczę, lecz przy pomocy tablicy kolorów, którą sam tworzy i modyfikuje. Procedura przerwania Display List jest podobna jak w poprzednim przykładzie, lecz efekt jest znacznie ładniejszy. W programie korzystamy z procedur: Init i Klawisz.
Program   Equ $8800

List_mem  Equ %00000110  
List_err  Equ %00000101
Code_mem  Equ %00010000
Code_dsk  Equ %00100000

Colpfl    Equ $D017 
Colpf2    Equ $D018 
Dliv      Equ $0200
Dlptrs    Equ $0230
Nmien     Equ $D40E 
Wsync     Equ $D40A

Pom       Equ $F0
 
       Opt List_err+Code_mem
          Org Program

          Ldy #$00
          Ldx #$07
L1        Tya
          Asl @
          Sta Kolory,y
          Txa
          Asl @
          Sta Kolory+$08,y
          Iny
          Dex
          Bpl L1
          Ldy #$01 
L2        Tya 
          Pha
          Ldx #$00
          Asl @
          Asl @
          Asl @
          Asl @
          Tay
L3        Lda Kolory,x
          Sta Kolory,y 
          Inx
          Iny
          Cpx #$10
          Bne L3
          Pla
          Tay
          Iny
          Cpy #$0C
          Bne L2

          Jmp Init

Przerw    Pha
          Txa
          Pha
          Tya
          Pha
          Ldx #$00

L4        Lda Kolory,x
          Sta Colpf2
          Eor #$FF
          Sta Colpfl
          Sta Wsync
          Inc Kolory,x
          Inx
          Cpx #$C0
          Bne L4
          
          Pla 
          Tay
          Pla
          Tax
          Pla
          Rti

Kolory    Dta B ($00)

          End of file
   Przed wywołaniem procedury Init tworzona jest tablica kolorów. Realizują to dwie pętle. Pierwsza z nich tworzy szesnastobajtową tablicę o następujących wartościach: $00, $02, $04, $06, $08, $0A, $0C, $0E, $0E, $0C, $0A, $08, $06, $04, $02, $00. Pętla druga powiela tę tablicę $0C razy.

    Procedura przerwania Display List to znów jedna pętla, w której pobierane są kolejne wartości z tablicy kolorów i wpisywane do dwóch rejestrów kolorów: do znanego nam już z poprzednich programów Colpf2 i (po wykonaniu operacji logicznej) do Colpf1 określającego w trybie Antic'a 2 kolor tekstu. Również w tej samej pętli poszczególne elementy tablicy zwiększane są o jeden.

Program 3

prezentuje jeden z ciekawszych i częściej umieszczanych w demonstracjach efektów: skaczącą "rurę".
Program   Equ $8800

List_mem  Equ %00000110
List_err  Equ %00000101
Code_mem  Equ %00010000
Code_dsk  Equ %00100000

Colbak    Equ $D01A
Colbks    Equ $2C8
Dliv      Equ $200
Dlptrs    Equ $230
Nmien     Equ $D40E
Wsync     Equ $D40A

Pom       Equ $F0

       Opt List_err+Code_mem
          Org Program

          Ldx #$00
          Stx Poz_y
          Stx Licznik

          Jmp Init

Przerw    Pha
          Tya
          Pha
          Txa 
          Pha

          Ldy Poz_y
          Lda Pozycje,y
          Tax
          Inc Poz_y
          Cpy #$1E
          Bne L2
          Ldy Licznik
          Clc
          Lda Kolory,y
          Adc #$10 
          Sta Kolory,y
          Ldy #$00 
          Inc Licznik
          Lda Licznik 
          Cmp #$0E 
          Bne L1
          Sty Licznik
L1        Sty Poz_y 
L2        Sta Wsync
          Sta Wsync
          Dex
          Bpl L2
          Ldy #$00
L3        Lda Kolory,y
          Sta Colbak
          Sta Wsync
          Sta Wsync
          Sta Wsync
          Iny
          Cpy #$0E
          Bne L3
          Lda Colbks
          Sta Colbak
         
          Pla
          Tax
          Pla
          Tay
          Pla
          Rti

Poz_y     Dta B($00)
Licznik   Dta B($00)

Kolory    Equ *
     Dta B($D2),B($D4),B($D6)
     Dta B($D8),B($DA),B($DC)
     Dta B($DE),B($DE),B($DC)
     Dta B($DA),B($D8),B($D6) 
     Dta B($D4),B($D2)

Pozycje   Equ *
    Dta B($20),B($21),B($21)
    Dta B($22),B($22),B($23)   
    Dta B($24),B($26),B($28)   
    Dta B($2A),B($2C),B($2F)   
    Dta B($32),B($35),B($38)   
    Dta B($3C),B($38),B($35)   
    Dta B($32),B($2F),B($2C)  
    Dta B($2A),B($28),B($26)   
    Dta B($24),B($23),B($22)   
    Dta B($22),B($21),B($21) 
    Dta B($20)
  
    End of file
   W programie korzystamy z dwóch tablic. Pierwsza z nich to tablica kolorów modyfikowana w trakcie wykonywania programu, natomiast druga to tablica pozycji "rury". Do poprawnego działania konieczne są jeszcze dwa rejestry: Pos_y wskazujący na element w tablicy pozycji i Licznik wskazujący na element tablicy kolorów. Przed uruchomieniem przerwania obydwa te rejestry otrzymują wartość $00.

    W samej procedurze przerwania wybierana jest wartość z tablicy pozycji wskazywana przez Poz_y i zapisywana w rejestrze X procesora. Jeśli tablica pozycji już się skończyła, to konieczne jest wyzerowanie Poz_y oraz zmodyfikowanie tablicy kolorów: element tablicy kolorów wskazywany przez Licznik zwiększany jest o $10 a następnie Licznik zwiększany jest o $01. W przypadku, gdy osiągnie wartość $0E (co oznacza, że tablica kolorów się skończyła) należy go też wyzerować.

    Od etykiety L2 zaczyna się część programu tworząca "rurę". Przypomnijmy, że w rejestrze X znajduje się wartość pobrana z tablicy Pozycje. W pętli zmniejszana jest wartość rejestru X i zarazem "opuszczane" są po dwie linie ekranu podczas każdego obiegu pętli, co powoduje, że "rura" skacze. W kolejnej pętli wyświetlana jest sama "rura" na ramce ekranu. Wartości kolorów odkładane są w rejestrze Colbak. Przed zakończeniem procedury przerwania do rejestru Colbak wpisywana jest wartość jego ciena - Colbaks (niestety byliśmy zmuszeni zmienić nazwę etykiety Colbaks na Colbks ze względu na to, że dla QA Colbak i Colbaks to to samo).

Program 4

   Na zakończenie tego artykułu jeszcze jeden efekt, na pewno najładniejszy z całej czwórki.
Program  Equ $8800

List_mem Equ %00000110
List_err Equ %00000101
Code_mem Equ %00010000
Code_dsk Equ %00100000

Colpf2   Equ $D018 
Dliv     Equ $0200
Dlptrs   Equ $0230 
Nmien    Equ $D40E 
Wsync    Equ $D40A

Pom      Equ $F0
      Opt List_err+Code_mem
         Org Program
 
         Ldx #$00
         Stx Licznik
         Stx Licznik+$01
         Txa
L1       Sta Kolory,x
         Inx
         Bne L1

         Ldy #$00
         Ldx #$0F
L2       Tya
         Eor #$30
         Sta Kolory+$20,y
         Txa
         Eor #$30
         Sta Kolory+$30,y
         Iny
         Dex
         Bpl L2

         Jmp Init

Przerw   Pha 
         Txa
         Pha
         Tya
         Pha

         Ldx #$00
         Stx Licznik
L3       Clc
         Lda Licznik+$01
         Adc Licznik
         Tax
         Ldy #$07
L4       Lda Kolory,x
         Sta Wsync
         Sta Colpf2
         Inx
         Dey
         Bpl L4
         Inc Licznik
         Ldx Licznik
         Cpx #$1A
         Bne L3
         Inc Licznik+$01
         Ldx Licznik+$01
         Cpx #$48
         Bne L5
         Ldx #$00
         Stx Licznik+$01

L5       Pla
         Tay
         Pla
         Tax
         Pla
         Rti

Licznik  Dla B($00),B($00)
Kolory   Dla B($00)

         End of file
    Podobnie jak poprzednik, program korzysta z dwóch komórek pamięci (etykieta Licznik) i tablicy kolorów. Tablica kolorów kreowana jest przed uruchomieniem przerwania. Miejsce w pamięci przeznaczone na tablicę jest zerowane w pierwszej pętli, a wraz z nim zerowane są liczniki. W kolejnej pętli od $20 elementu tablicy wpisywane są wartości od $30 do $3F a od elementu $30 w odwrotnej kolejności. Dane nie są wpisywane na początek tablicy po to, aby efekt rozpoczął się na dole ekranu.

    Na początku procedury Display List zerowany jest licznik zliczający w całej procedurze ilość małych "rur". Licznik+$01 wskazuje na element tablicy kolorów. W pętli L4 tworzona jest jedna mała "rura", następnie zwiększany jest Licznik. Wartość $1A w Liczniku oznacza utworzenie wszystkich $1A "rur". Dzięki dodawaniu na początku pętli L3 ułożenie kolorów w każdej z małych "rur" jest inne. Po zmianie kolorów Licznik+$01 zwiększany jest o jeden. W przypadku, gdy osiągnie koniec tablicy ($48) jest zerowany.

    W następnym artykule zakończymy zmagania z Antic'em definiując własne zestawy znaków.

Rafał Bielecki
Tomasz Bielak



Powrót na start | Powrót do spisu treści | Powrót na stronę główną

Pixel 2002