Tajemnice ATARI

Piszemy GRĘ


    Chyba każdy, kto zajmuje się pisaniem programów napisał, próbował napisać lub chciałby napisać grę. Prezentowany przeze mnie cykl artykułów ma na celu wyjaśnienie pewnych problemów napotykanych podczas ich tworzenia.

   Na pewno niejeden z czytelników zastanawiał się, w jaki sposób uzyskać dużą ilość grafiki na ekranie. Do tworzenia jej najlepiej użyć trybu $04 ANTIC'a, ze względu na dostępną ilość kolorów, rozdzielczość i ilość potrzebnej pamięci. Normalnie w tym trybie mamy do dyspozycji 128 znaków o wymiarach 4*8 punktów, lecz na pewno każdy zauważył, że w większości gier wydanych przez L.K.Avalon elementy graficzne są dwukrotnie szersze i wyższe (najlepiej widać to chyba na przykładzie ROBBO). Efekt taki możemy uzyskać używając dwóch zestawów znaków naprzemiennie włączanych w każdej linii ekranu oraz wyświetlając w dwóch sąsiednich liniach takie same dane. Pierwszy zestaw powinien zawierać definicje górnych, a drugi dolnych połówek znaków. Dla lepszego zrozumienia proszę się przyjrzeć, jak zrobione to jest w naszym przykładzie. Wyjaśniłem już podwójną wysokość, natomiast podwójną szerokość uzyskuje się po prostu przez wyświetlenie obok siebie dwóch sąsiednich znaków (np. 0 i 1). Używając tej metody mamy do dyspozycji 64 znaki o wymiarach 8*16 punktów. W tym odcinku, ze względu na objętość nie przedstawię więcej problemów natury technicznej, poprzestanę jedynie na opisaniu pewnych fragmentów programu.

   Pierwszym ciekawym fragmentem jest procedura INI_VAR.

 opt 21
 org $a000
* --- constans --- *

fonts    equ $b400
sprites  equ $a800
shapel   equ fonts+$110
shape2   equ fonts+$510
color1 equ $02
color2 equ $04
color3 equ $0a
color4 equ $06
color5 equ $00
color6 equ $04
color7 equ $02


dma_mod  equ %00111101
gti_mod  equ %00110001
plus4hsc equ $d4
plus4    equ $c4

esc      equ $1c

space    equ $00
inf_spac equ $2 a
inf_pict equ $40
gaov_txt equ $4a

* --- zero page -- *

adrl     equ $b0

help_l   equ $b8
count    equ $b9

* --- system ----- * 	

clock 	 equ $14 	
atract 	 equ $4d 	

dliv     equ $0200 	
dmactls  equ $022f 	
dlptrs 	 equ $0230 	
gtictls  equ $026f 	
strig0 	 equ $0284 	
colpm0 	 equ $02c0 	
colpf0 	 equ $02c4 	
kbcodes  equ $02fc 	

hposp0 	 equ $d000 	
sizep0 	 equ $d008 	
pmcntl 	 equ $d01d 	
consol 	 equ $d01f 	
audctl 	 equ $d208 	
skctl 	 equ $d20f 	
pmbase 	 equ $d407 	
chbase 	 equ $d409 	
wsync 	 equ $d40a 	
vcount 	 equ $d40b 	
nmien 	 equ $d40e 	

* --- program ---- *


begin    equ *

 jsr init
 jmp gme_strt

game_lop equ *

* wyzerowanie zmiennych

 ldy #0
 sta var_bgn,y
 iny
 cpy <var_len
 bcc *-6

* ustalenie poczatkowych
* wartosci zmiennych

 lda #color6
 sta colpm0
 lda #color7
 sta colpm0+1
 lda #$99
 sta ammo_cou
 sta fuel_cou
 lda #$19
 sta fuel_cou+l
 lda #$ff
 sta kbcodes

* glowna petla
* programu

loop     equ *
 
 lda clock
 cmp clock
 beq *-2
 
 lda #0
 sta atract
 
 inc count
 
 lda kbcodes
 cmp #esc
 bne *+5
 jmp exit

* jsr scroll   odc 2
* jsr player   odc 2
* jsr fire     odc 3
* jsr animator odc 3
* jsr take     odc 4
* jsr result   odc 4
* jsr sounds   odc 4

 lda death
 beq loop
* jmp game_ovr  odc 4
 rts - skasowac po odc 4

gme_strt equ *

 jsr clr_scr
 jsr shw titl
* jsr clr_spr   odc 2

* oczekiwanie na
* zwolnienie FIRE

 lda strig0
 beg *-3
 
lda #$ff
 sta kbcodes

* oczekiwanie na
* uruchomienie gry
* lub jej opuszczenie

star_lop equ *

 lda kbcodes
 cmp #esc
 bne *+5
 jmp exit

 lda strig0
 beq start

 lda consol
 cmp #6
 bne star_lop

start    equ *

 jmp game_lop

* inicjacja gry

init     equ *

 jsr ini_var

* wlaczenie przerwan

 lda #l92
 sta nmien

* ustalenie wartosci
* rejestrow grafiki
* SPRITE'ow

 lda #3
 sta pmcntl
 ldy #4
 lda #0
 sta sizep0,y
 dey
 bpl *-4
 lda >sprites
 sta pmbase
 lda #$40
 sta hposp0
 sta hposp0+l

* reset POKEY'a

 lda #0
 sta audctl
 lda #3
 sta skctl

* jsr silence   odc 4

* wyswietlenie pola
* informacji

 ldy #0

init_2     equ *

 lda #inf_spac
 jsr shw_info
 iny
 iny
 cpy #$60
 bcc init_2

 lda #inf_pict
 sta help_1
 ldy #$00

init 3    equ *
 
 lda help_l
 jsr shw_info
 iny
 iny
 lda #inf_pict+8
 jsr shw_info
 lda help_l
 clc
 adc #$02
 sta help_l
 tya
 clc
 adc #$0e
 tay
 cpy #$32
 bcc init_3
 rts

* opuszczenie gry

exit    equ *

 lda clock
 cmp clock
 beq *-2
 jsr ini_var
 lda #64
 sta nmien
 ldy #7
 lda #0
 sta hposp0,y
 dey
 bpl *-4

* jsr silence    odc 4

 lda #$ff
 sta kbcodes
 rts

* procedura zapamietująca
* i odtwarzajaca zawartosc
* rejestrow systemowych

ini_var  equ *

 ldy #0
 ldx #0
ini_1    equ *

 lda loa_var,x
 sta adrl
 lda loa_var+l,x
 sta adrl+1
 lda (adrl),y
 pha
 lda loa_var+2,x
 sta (adrl),y
 pla
 sta loa_var+2,x
 inx
 inx
 inx
 cpx <loa_len
 bcc ini_1
 rts   

* przerwanie Display List

dlint    equ *

 pha
 cld
 lda vcount
 and #4
 eor #4
 clc
 adc >fonts
 sta wsync
 sta chbase
 pla
 rti

* wypelnienie ekranu
* spacjami

clr_scr   equ *

 ldy #0

clsc_l    equ *
 
 tya
 pha
 lda #space
 jsr shw_blck
 pla
 tay
 iny
 iny
 bne clsc_l
 rts

shw_titl equ *

* wyswietlenie
* planszy tytulowej

 ldy #l7

shti_1   equ *

 tya
 clc
 adc #gaov_txt
 sta screen+$50,y
 dey
 bpl shti_1

 ldy #20

shti_2   equ *
 
 tya
 clc
 adc #gaov_txt+18
 sta screen+$73,y
 dey
 bpl shti_2
 ldy #l4

shti_3   equ *

 tya
 clc
 adc #gaov_txt+39
 sta screen+$99,y
 dey
 bpl shti_3
 rts

* wyswietlenie
* znaku w polu
* informacyjnym

shw_info equ *
 
 sta info,y
 ora #1
 sta into+l,y
 rts

* wyswietlenie znaku
* na ekranie

shw_blck equ *

 sta screen,y
 ora #l
 sta screen+l,y
 rts

* zmienne

var_bgn  equ *

fuel_cou dta a(0)
ammo_cou dta b(0)
death    dta b(0)

var_len  egu *-var_bgn

* tablica rejestrow
* systemowych

loa_var  equ *
 
 dta a(dmactls),b(dma_mod)
 dta a(dlptrs),l(newdl)
 dta a(dlptrs+l),h(newdl)
 dta a(dliv),l(dlint)
 dta a(dliv+l),h(dlint)
 dta a(colpf0),b(color1)
 dta a(colpf0+l),b(color2)
 dta a(colpf0+2),b(color3)
 dta a(colpf0+3),b(color4)
 dta a(colpf0+4),b(color5)
 dta a(colpm0),b(color6)
 dta a(colpm0+l),b(color7)
 dta a(gtictls),b(gti_mod)

loa_len  equ *-loa_var

* wlasna Display List

newdl    equ *

 dta b($70),b($70),b($f0)
 dta b(plus4hsc),a(screen+$00)
 dta b(plus4hsc),a(screen+$00)
 dta b(plus4hsc),a(screen+$24)
 dta b(plus4hsc),a(screen+$24)
 dta b(plus4hsc),a(screen+$48)
 dta b(plus4hsc),a(screen+$48)
 dta b(plus4hsc),a(screen+$6c)
 dta b(plus4hsc),a(screen+$6c)
 dta b(plus4hsc),a(screen+$90)
 dta b(plus4hsc),a(screen+$90)
 dta b(plus4hsc),a(screen+$b4)
 dta b(plus4hsc),a(screen+$b4)
 dta b(plus4hsc),a(screen+$d8)
 dta b(plus4hsc),a(screen+$d8)
 dta b(plus4),a(info+$00)
 dta b(plus4),a(info+$00)
 dta b(plus4),a(info+$20)
 dta b(plus4),a(info+$20)
 dta b($41),a(newdl)

info     equ sprites
screen   equ sprites+$40

 opt 7
 end of Heli Killer


Dariusz Żołna


Napisanie gry nie jest rzeczą prostą - potrzeba wiele czasu i cierpliwości. Często zdarza się, że mamy gotowy program, lecz brakuje nam grafiki. W takim wypadku trzeba włączyć komputer, uruchomić program graficzny i zabrać się do pracy...

Aby zaoszczędzić Wam czasu, poniżej zamieszczam dane elementów graficznych Heli Killera. Należy je przepisać, zgrać Zgrywusem+ w formacie plikowym i dołączyć do gry, którą wspólnie piszemy.

1000 REM *--------------------------*
1002 REM : HELI.FNT                 :
1004 REM :  autor: Dariusz Zolna    :
1006 REM : (c) 1993 Tajemnice ATARI :
1008 REM *--------------------------*
1010 DATA ffff00b4ffbb00000000000000
1020 DATA 000000000000000000ffead5da
1030 DATA dfdcdddffea959addd1dad6dff
1040 DATA ead5dadfdcdddffea959addd1d
1050 DATA adddffead5dadfdcdddffea959
1060 DATA addddddddd0000006a010e3efe
1070 DATA 000000a40040805e0000001a01
1080 DATA 0e3efe00000090004080520000
1090 DATA 0006010e3efe00000040004080
1100 DATA 5300000001010e3efe00000000
1110 DATA 0040805e00000006010e3efe00
1120 DATA 000040004080520000001a010e
1130 DATA 3efe0000009000408053000000
1140 DATA 00000004090000000000004040
1150 DATA 00000000052dbeaa0000000010
1160 DATA a0f4e0000000181d3929e50000
1170 DATA 00001464b8f400001464a92d55
1180 DATA 25000000001464b8bc00000044
1190 DATA 545054150000000014641a1600
1200 DATA 00004050504000000000004404
1210 DATA 05010000000000000000000000
1220 DATA 0000000038183c3c180018686e
1230 DATA 7278184c44004404183c3c1800
1240 DATA 18686e7278184c04404404183c
1250 DATA 3c180018686e7278180c444004
1260 DATA 04183c3c180018686e7278184c
1270 DATA 0440440455aaffaa5500000055
1280 DATA aaffaa5500000055aaffaa5500
1290 DATA aaff55aaffaa5500a0f455aaff
1300 DATA aa55000a3f55aaffaa55004040
1310 DATA 55aaffaa5500aaff55aaffaa55
1320 DATA 00a4f455aaffaa5500aaff55aa
1330 DATA ffaa5500a4f455aaffaa5500a4
1340 DATA f455aaffaa5500000055aaffaa
1350 DATA 5500aaff55aaffaa5500a4f455
1360 DATA aaffaa5500aaff55aaffaa5500
1370 DATA a4f455aaffaa5500aaff55aaff
1380 DATA aa5500a4f455aaffaa5500aaff
1390 DATA 55aaffaa5500a4f455aaffaa55
1400 DATA 00aaff55aaffaa5500a4f455aa
1410 DATA ffaa5500020155aaffaa5500e0
1420 DATA 5055aaffaa5500010055aaffaa
1430 DATA 5500900055aaffaa55003f3655
1440 DATA aaffaa5500c07055aaffaa5500
1450 DATA 38e955aaffaa5500000055aaff
1460 DATA aa5500000f55aaffaa550000c0
1470 DATA f0f0a0f0a0a0ffaaf3f3a2f3a2
1480 DATA a2f3a2ffffaaff8080fca8cfcf
1490 DATA 8acf0a0a0f0a00000000000000
1500 DATA 003c3c283c28283c2800000000
1510 DATA 000000000000000000000000f0
1520 DATA f0a0f0a0a0ffaaf3f3a2f3a2a2
1530 DATA f382cfcf8acf8a8acf8a000000
1540 DATA 00000000003c3c283c28283c28
1550 DATA 0000000000000000ffffaaffa0
1560 DATA a0ffaaf3f3a2f302020302ffff
1570 DATA aaff8282ffaac0c080c08080c0
1580 DATA 00000003010301020200000000
1590 DATA fc54080800000000c341828200
1600 DATA 0000000000000000fc57bd9682
1610 DATA 8282000f351f2520202f000fc5
1620 DATA 4b89888b8900c371d26222e252
1630 DATA 003010202020202000c34d8789
1640 DATA 888b8900f351f3510000c000fc
1650 DATA 54f8582ce47000000000000000
1660 DATA 00000000f088888850000000fc
1670 DATA 80a0805400000000000000003c
1680 DATA d769fe560b391c000f351f2520
1690 DATA 2020000cc4488888888b000302
1700 DATA 020202c242000c04cc78d87818
1710 DATA 003cd77d968282be0000000015
1720 DATA 80cfcc00000000402030300000
1730 DATA 00002233333300000000a23333
1740 DATA f300000000a23030f300020300
1750 DATA a03030f000a2f3c3c3c3c34100
1760 DATA a2f33030f3f31100a2f3333333
1770 DATA f35100a2f303c303f3510022f3
1780 DATA f33333331100a2f33333333311
1790 DATA 002a3f3030303f15002a3f303c
1800 DATA 303f1500000000000000000000
1810 DATA 000000000000dcddddd1daffea
1820 DATA 956dadadadadfda955d0dadfd0
1830 DATA daffea95dddddd1dadfda955dc
1840 DATA ddddd1daffea95dddddd1dadfd
1850 DATA a955aa551504982a0000aa5740
1860 DATA 4080a00000aa551504982a0000
1870 DATA af54404080a00000aa55150498
1880 DATA 2a0000aa5c404080a00000aa55
1890 DATA 1504982a0000aa57404080a000
1900 DATA 00aa551504982a0000af544040
1910 DATA 80a00000aa551504982a0000aa
1920 DATA 5c404080a000000f1b1e0a1904
1930 DATA 000090e090d0404000003f2fbb
1940 DATA 7bbea66510d0e0a4f4b4508000
1950 DATA fada6aaeaa366510b8a424f4b8
1960 DATA d8944064a4a5d5d96515506810
1970 DATA 50a478b8a41060040410005550
1980 DATA 10085410006000241800004000
1990 DATA 04001014000104001014500400
2000 DATA 00000000000000e9a9a9a51400
2010 DATA 0000240c0c24186014322c0044
2020 DATA 5040044002240c0c2418601432
2030 DATA 2c00445000444002240c0c2418
2040 DATA 6014322c00441040440002240c
2050 DATA 0c24186014322c004450004440
2060 DATA 02000000000000000000000000
2070 DATA 00000000f5f5f4f4ffaa551574
2080 DATA 743434f4a454543f1f1f0fffaa
2090 DATA 551540404040f4a4545455ffff
2100 DATA f5ffaa551574f4f454f4a45454
2110 DATA 55ffff55ffaa551574f4f4f4f4
2120 DATA a45454f4ffff5515000000f4f4
2130 DATA f4f4f4a45414d5ffff55ffaa55
2140 DATA 1554f4f4f4f4a45454d5fffff5
2150 DATA ffaa551554f4f474f4a4545457
2160 DATA 1f0f0703020100d4f4f4d4d090
2170 DATA 5050d5fffff5ffaa551574f4f4
2180 DATA 74f4a45454d5ffff55ffaa5515
2190 DATA 74f4f4f4f4a45454000000000f
2200 DATA 0e0502808080b0fca454200000
2210 DATA 00000a09000140404060a85000
2220 DATA 1036163a3a363936155c4444f4
2230 DATA 94649454a9a9a5140000000000
2240 DATA 0038e9a9a9a5140e0e05000f0e
2250 DATA 0e0540404000c0404040aa55a0
2260 DATA a050a05050a251a2a251a25151
2270 DATA a840808055aa55550a050a0a45
2280 DATA 8a45450000000055aa55552814
2290 DATA 28281428141400000000000000
2300 DATA 000000000000000000aa55a0a0
2310 DATA 50a050508251a2a251a251518a
2320 DATA 458a8a458a45450000000055aa
2330 DATA 555528142828152a1515000000
2340 DATA 0054a85454aa55a0a055aa5555
2350 DATA 0201020251a25151aa55828241
2360 DATA 82414100408080408040400202
2370 DATA 0301000000000808fc54000000
2380 DATA 008282ff550202ff5500000000
2390 DATA 00000000828282be97fd540025
2400 DATA 2f2520203010008b89888888cc
2410 DATA 4400f262222222331100202020
2420 DATA 2f351f05008781808fc54f0500
2430 DATA 73d162e272d3410090c040fc54
2440 DATA fc5400000f00000005000000cf
2450 DATA 888a8805000000cf0202024100
2460 DATA 0000c0000000000000e47090bf
2470 DATA 95ff55002020202f351f050089
2480 DATA 8b898bc94f0500c24202f252f2
2490 DATA 510008080808080c040096be96
2500 DATA 8282c34100cccf801500000000
2510 DATA 30302040000000003010301100
2520 DATA 00000030103051000000003010
2530 DATA 30510000000030103050000000
2540 DATA 00000000000000000000aafff3
2550 DATA f3ffaa51002a3f0f0f0f0a0500
2560 DATA 8acf0f0f0f0a0500a2f33333f3
2570 DATA a21100a8fcccfcfca84400aaff
2580 DATA 3c3c3caa550000000000000000


Dariusz Żołna

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

Pixel 2001