Už jsme se naučili psát písmenka, už známe organizaci videoram, takže se můžeme pustit do něčeho zábavnějšího: psaní celých textů.
Pokud používáme jen obyčejné rst 16 vystačíme si s docela jednoduchou rutinkou, která bere znak po znaku a předává je ROM. Tudíž do textu můžeme zapracovat všechny řídící kódy, které jsme si ukázali v prvním dílu. Jako koncová značka se bere nastavený sedmý bit znaku. Toto si můžeme dovolit, protože žádný řídící kód a ani jeho parametr nemůže být větší než 127. Kdybychom chtěli tiskat třeba znaky z UDG (uživatelem definovaná grafika), museli bychom koncové značce vyhradit jeden kód a ten by se nesměl vyskytovat nikde jinde než na konci. Nula by to být nemohla, spíše nějaký kód už z oblasti klíčových slov Basicu. Nyní rutina:
ld a,2 ;nesmime zapomenout
call $1601 ;otevrit prislusny kanal
ld hl,text ;ukazatel na text
call textout ;vytiskni
ret ;vrat se
TEXTOUT ld a,(hl) ;vezmi znak
res 7,a ;odrizni sedmy bit
rst 16 ;posli do ROMky
bit 7,(hl) ;testuj 7.bit znaku
inc hl ;posun ukazatel
jr z,textout ;pokud je bit nulovy, tiskni dalsi pismenko
ret ;jinak navrat
text db 22,10,5 ;ridici kody
db "Testovaci tex",'t'+128 ;jsou soucasti textu
Jestli znáte assembler PROMETHEUS, tak vidíte, že zápis s posledním znakem je tady poněkud složitější, ale dá se na to zvyknout.
ld a,2 ;opet otevrit kanal
call $1601
call TEXTOUT ;volej program
db 22,4,5,18,1 ;ihned za programem je vlastni text
db "pokusny text" ;soucasti textu jsou
db 18,0+128 ;ridici kody
ret ;navrat
TEXTOUT pop hl ;vyzvedni navratovou adresu
TEXTOUT_2 ld a,(hl) ;ta ukazuje na prvni pismenko
res 7,a ;oklestit o sedmy bit
rst 16 ;posli do rst 16
bit 7,(hl) ;testuj onen sedmy bit
inc hl ;posun ukazatel
jr z,TEXTOUT_2 ;neni nastaven, opakuj
jp (hl) ;navrat zpet, hl ukazuje ZA posledni znak
Tato rutinka je opět jedna z jednoduších, ale její princip se dá využít všude tam, kde se vyskytují různé krátké texty. Nemusí se před zavoláním rutinky plnil registr adresou textu (ta se naplní instrukcí pop hl) a nemusí se vymýšlet název textu a při psaní programu se nemusí napsat přeskakovat od části s kódem k části s texty a zpět. Tento princip je využit třeba v programu TOOLS 128. Celá finta spočívá v tom, že při zavolání programu TEXTOUT se na zásobník uloží návratová hodnota následující intrukce (bajtu) hned za instukcí call. A právě tam je text. Takže když se provede pop hl, v hl bude právě adresa textu. Následující kód je stejný jako v prvním případě, ale návrat je už jiný. Návratovou adresu už jsme vyzvedli, retem se vracet nemůžeme. Registr hl po vytištění textu ukazuje právě za poslední písmenko na první instukci, která je bezprostředně za textem. V&#
xA0;našem případě je to poslení ret z programu ven.
Je patrno, že pomocí rst 16 to není úplně ono, musíte mít stále na paměti, že úplně nejspodnější řádky mají jiný kanál než zbylých 22. Použijeme tedy proto naši vlastní rutinu pro tisk znaku. Jenomže naše rutina neumí nastavovat řídící kódy pro nastavení pozice a barvy textu. Nedá se nic dělat, prostě ho to musíme naučit. Ukáži vám základní rutinku, kterou si pak můžete upravit podle vlastních potřeb. Zná 2 řídící kódy:
db 1,y,x – nastavuje pozici do y-řádku a x-sloupce
db 2,z – nastaví barvu z (přímo hodnota attributu)
cpu z80undoc
relaxed on
org 25000
ld hl,text ;adresa textu
call textout ;vytiskni
ret
TEXTOUT ld a,(hl) ;nacti pismenko/kod
or a ;testuj konec textu
ret z ;navrat
cp 32 ;testuj jedna-li se o kod
inc hl ;posun se na dalsi pismenko/kod
jr c,KODY ;skoc na zpracovani kodu
call ZNAK ;neni kod, tiskni normalni znak
jr TEXTOUT ;smycka
KODY dec a ;kod 1?
jr z,KOD1 ;ano, skoc
dec a ;kod 2?
jr z,KOD2 ;ano, skoc
jr TEXTOUT ;neznamy kod, preskoc a jdi na zacatek
KOD1 ld b,(hl) ;nacti cislo sloupce
inc hl ;posun
ld c,(hl) ;nacti cislo radku
inc hl ;posun se
push hl ;uloz si ukazatel
call ADRSET ;nastav pozici
pop hl ;obnov ukazatel
jr TEXTOUT ;smycka
KOD2 ld a,(hl) ;nacti hodnotu atributu
ld (COLOR),a ;proste ho nastav
inc hl ;posun ukazatel
jr TEXTOUT ;smycka
TEXT db 1,6,16,2,56 ;text, nastaveni pozice a barvy
db "Pokusny Text" ;vlatni text
db 0 ;ukonceni textu
ZNAK push hl ;uloz adresu textu
sub 32 ;zbytek rutinky uz zname
ld l,a
ld h,0
add hl,hl
add hl,hl
add hl,hl
ld de,FONT
add hl,de
ld de,(POZICE)
push de
ld b,8
znak1 ld a,(hl)
ld (de),a
call DOWNDE
inc hl
djnz znak1
call ATTR
pop de
inc e ;rutina z domaci ulohy 2 ze 3.dílu
jr nz,znak2
ld a,d
add a,8
ld d,a
cp 88
jr c,ZNAK2
ld d,64
ZNAK2 ld (POZICE),de
pop hl ;obnov adresu textu
ret
POZICE dw 16384
COLOR db 56
FONT equ 15616
ADRSET ld a,c ;sloupec
add a,a ;nasob 8x
add a,a
add a,a ;dostaneme pixelovou pozici
ld c,a
ld a,b ;radek
add a,a
add a,a
add a,a
call $22B0 ;prepocet pixelovych souradnic
ld (POZICE),hl ; na adresu v pameti
ret
ATTR ld hl,(pozice) ;precti adresu pozice
ld a,h
sub $40 ;posunuti pocatku adresy do nuly
rrca ;deleni 8
rrca
rrca
and 3 ;v A je nyni cisl o tretiny
add a,$58 ;posun do attributu
ld h,a ;do vyssiho bajtu, nizsi je stejny
ld a,(COLOR)
ld (hl),a
ret
DOWNDE inc d ;posun v ramci textoveho radku
ld a,d ;je jednoduchy
and 7 ;neni-li prekrocen
ret nz ;vrat se zpet
ld a,e ;prechod mezi textovymi radky
add a,32 ;pokud pri pricitani dojde k preteceni
ld e,a ;je to signal, že doslo k prechodu
ld a,d ;mezi tretinami
jr c,DOWNDE2 ;hotovo a tedy odskok
sub 8 ;jeste zbyva uprava horniho bytu
ld d,a ;pri prechodu mezi tretinami
DOWNDE2 cp 88 ;test opusteni obrazovky
ret c ;nedoslo, navrat
ld d,$40 ;doslo, uprav na zacatek
ret ;navrat
Bystřejší oko jistě zpozorovalo, že koncová značka je nula. Bystřejší hlavou určitě bleskla myšlenka, že by se daly zobrazovat nejen písmenka ASCII, ale i nějaká další, třeba znaky s češtinou, nebo speciální znaky, jen si nakreslit vlastní font.
Domácí úkol: Zkuste tuto poslední rutinku doplnit o další řídící kódy, které budou nastavovat barvy INK, PAPER, FLASH, OVER každé zvlášť. Například db 3,7,4,0 nastaví inkoust na 7 a papír na 0.
4 komentáre na “4.díl: psaní textů”
Je nám líto, ale formulář pro přidávání komentářů je momentálně uzavřen.
vynikajici.jen tak dal, tenhle dil se mi obzvlas libil. musim sice jeste udelat ukol z 3. dilu, protoze nestiham, ale tenhle jsem zmaknul a uz se tesim na dalsi
A to Logout dokonce dopsal funkci OVER. Dokaze to jeste nekdo?
dopsal jsem BRIGHT, OVER bylo soucasti zadani, pokud se nepletu 😉
Pravda, bylo. Nevim proc jsem to tam napsal, to jsem puvodne nechtel, ale uz je to tam. Vzhledem k tomu, ze uz jsme OVER "brali" by to nemelo byt zas tak tezke. Takze vyzva pro ostatni: kdo z lameru trumfne Logouta? Kdo je nejslabsi? Kdo dostane panaka?