Myši a ZX Spectrum
Úvod
S prvními zmínkami o myši u ZX Spectra jsem se setkal snad už v 90. roce, ale tenkrát nebylo ještě snadné sehnat pěknou myš za rozumné peníze. Velmi často bylo možné koupit myši jen velmi nepraktické do ruky, často velmi hranaté a neergonomické (např. třítlačítkové modely od firmy Genius, případně všelijaké stavebnice - mám jednu s pingpongovým míčkem a tlačítky realizovanými ze svěracích špendlíků s papírovými clonkami). Myši se začaly nejprve vyskytovat u vícebitových počítačů orientovaných na grafiku, což byly všelijaké Apple Macintosh, Atari, Amiga a později i IBM PC. Koncem 80. a začátkem 90. let, tj. v době největšího rozmachu ZX Spectra byly např. u Amigy myši standardní součástí výbavy, u IBM PC je uživatelé teprve objevovali.
Není divu, že uživatelé ZX Spectra uživatelům počítačů s grafickým prostředím trochu záviděli a přemýšleli, jak si taky myšku připojit a naučit se s ní pracovat. Bohužel to nebylo tak jednoduché. U ZX Spectra se vyskytovalo mnoho různých rozhraní, jak paralelních, tak sériových, ale žádné nebylo rozšířeno globálně, žádné rozhraní nikdy nemělo status standardu (byť nepsaného v rámci platformy). Jako např. sériové porty, PS/2 a později USB na platformě PC.
Bylo tedy nutné použít rozhraní, když ne globálně rozšířené, tak alespoň trochu rozšířené a pokud možno snadno sehnatelné a levné, aby připojení už tak drahé myši (tenkrát stály často kolem 500Kčs i víc a platy se pohybovaly někde od 2,5 - 5000Kčs) nebylo zbytečně zatěžováno i drahým rozhraním. Jednou z možností byl sériový port. Sériové myši byly snadněji sehnatelné, levnější a byl v nich výrazně větší výběr. Ale ZX Spectrum nemělo standardně sériový port, kromě modelů ZX Spectrum 128kB, a šedivých ZX Spectrum +2, +2A, +3, které však měly naprosto nestandardní konektory, navíc nevhodně umístěné, protože je zakrývalo kdejaké zařízení připojené k systémové sběrnici (např. Betadisk). Tato, v té době rozšířenější, implementace sériového portu používá obvod AY-3-8912 jako IO port. Řízení signálů musel provádět software a v různých přídavných rozhraních s kompatibilním zvukovým čipem se používaly i jiné varianty čipu AY, případně jeho klony a občas i verze bez IO portů. Takže sériová myš existuje, ale je velmi obtížně připojitelná (má-li být zachována kompatibilita) s 48kB verzemi ZX Spectra včetně těch rozšířených na 128kB a doplněných o AY, protože těm i po rozšíření chyběly převodníky z TTL <-> RS232 a napájecí zdroj dodávající napětí +12V a -12V. Dnes dostupný např. MAX232 neexistoval.
Další volbou byl port paralelní, nejčastěji 8255 v UR-4 a Didakticích. Zapojení myši do UR-4 je extrémně jednoduché, vlastně není potřeba provádět vůbec žádnou úpravu, pokud se spokojíte jen s jedním tlačítkem. Bohužel velmi zásadní nevýhodou je obrovské zatížení CPU, protože myš je potřeba obsluhovat zcela kompletně programově a tímto programem, pokud možno, číst stav signálů neustále. Pro další činnosti, krom obsluhy myši zbývá nejvýše 50% času CPU, spíš méně, pokud má být pohyb kurzoru opravdu plynulý. U klikacích menu to většinou nevadí, ale je to zcela nepoužitelné v náročnějších hrách. Přesto se tato myš v mém okolí po určitou dobu rozšířila nejvíc. Částečně kvůli ART Studiu v češtině pro tento typ myši a Betadisk, trochu i kvůli mému Bootu a dalším drobnostem. Této myši se říkalo "Amiga Mouse" (zkráceně jen A-Mouse) podle typu použité myši, vyráběné původně pro Amigu a Atari.
V souvislosti s UR-4 musím zmínit pokus Proximy o rozšíření kompatibilnější a méně náročné varianty, tzv. "Kempston Mouse". Bohužel ji znám jen z doslechu, ale vím, že byla použitelná místo Kempston joysticku. Bylo potřeba, kromě samotného rozhraní joysticku, ještě rozhraní s jednočipovým mikroprocesorem PIC, takže její připojení zcela jednoduché nebylo. Ale velmi jednoduché bylo využití v programech. Interface myši emuloval Kempston joystick a řídil čas sepnutí směrů pomocí PWM takže bylo možné v několika málo krocích měnit i rychlost kurzoru v závislosti na rychlosti pohybu myší. Díky tomu fungovala s naprostou většinou programů používajících Kempston joystick a to buď stejně jako joystick, nebo v lepším případě podobně jako skutečná myš. Tato verze se v mém okolí nevyskytovala vůbec. Článek o této myši zde.
Poslední variantou je vytvoření vlastního interface s alespoň minimální hardwareovou akcelerací, aby se o myš nemusel starat procesor. Každý ušetřený takt je užitečný. Nejzajímavější varianta pochází od firmy Kempston, stejně jako známé zapojení joysticku na port 31 a připojuje s k ní taky Amiga myš s TTL rozhraním. Výsledkem činnosti nepříliš složitého a vcelku levného rozhraní jsou tři čísla na třech portech. Dvě čísla udávají polohu myši v rozsahu od 0 do 255 včetně a bity ve třetím bytu určují stisknutá tlačítka. Je sice nutné provést jednoduchou softwarovou korekci pro výšku obrazovky 192px, ale to je zanedbatelné vzhledem k ostatním variantám myší. A jedná se o skutečnou myš, takže pohyb kurzoru zcela kopíruje pohyb myši včetně změn rychlosti pohybu. S touto variantou jsem se setkal až o mnoho let později, kdy jsem už měl k dispozici připojení k internetu a ZX Spectrum už tolik uživatelů nezajímalo (1995 - 1996).
Souhrn
Typ myši | rozhraní | výhody | nevýhody | ostatní |
---|---|---|---|---|
Kempston Mouse | speciální interface, schéma zde, nebo zde. | Skoro vůbec nezatěžuje procesor. Stačí číst 3 čísla na 3 portech a to je vše. | Obsazuje 3 porty, vrací nevhodně stav tlačítek (podle mého názoru). | Původní interface firmy Kepston, vyskytuje se často u ruských počítačů Pentagon, Scorpion a zcela určitě v počítači Sprinter, emulována v X128. |
Kempston Mouse Proxima | speciální rozhraní od Proximy, prý s jednočipem PIC | Není třeba speciální software, pracuje v programech, které umí pracovat s Kempston joystickem. | Je nutné speciální, relativně složité rozhraní. | Není to skutečná myš. Pohyb kurzoru není zcela dokonalý. Spíše se jedná o joystick s možností zpomalení pohybu kurzoru. |
Amiga Mouse (Heptau?) | UR-4, nebo jiný interface Kempston joysticku se správně zapojeným napájením. | MHB8255 je velmi rozšířený interface na území české a slovenské republiky. Máte-li UR-4, nic jiného nepotřebujete. | Velmi hodně zatěžuje procesor, vše musí obsloužit program (zabere nejméně 1/2 přerušení). Dobře použitelné v užitkových programech se spoustou ikon a tlačítek, horší ve hrách. | V ČR a SR velmi rozšířený typ myši, kvůli jednoduchosti připojení. Tuto myš jsem podporoval ve svých programech až do náhrady za KMouse od Velesofta, nyní jen volitelně. |
Sériová Myš (ing. Petr Simandl) | RS232, které je součástí Spectra 128 kB | Relativně málo zatěžuje procesor, nutné pouze čtení několika bytů jednou za přerušení, ovšem ze sériového rozhraní. | Rozumně použitelná jen u ZX Specter 128kB, u ostatních bývají kompatibilní sériové porty jen vyjímečně. | Nutno upravit konektor RS232 na cannon 9pinů, úprava myši na konektor Spectra není vhodné. Originální konektor obtížně sehnatelný a nevhodně umístěný. |
Amiga Mouse
Amiga myš není zaměnitelná se sériovou. Komunikuje na úrovních TTL a v podstatě počítači předává přímo stav clonek přes tvarovač se Schmittovými klopnými obvody 74HC14. Používá 4 vodiče pro přenos pulzů ze čtyř čidel, dva signály/clonky pro každou osu, další až tři vodiče pro přenos stavu tlačítek a dva pro napájení GND a +5V. tj. 7 až 9 vodičů. Víc nemá smysl, protože se u ní, stejně jako u joysticku (Kempston, Amiga ...) používá devítipinový konektor DSUB (Canon). Narozdíl od sériové myši, kde se napětí pulzů může pohybovat od -15V do -3V pro log. 1 a od +3V do +15V pro log. 0 a data se přenáší protokolem RS232, jsou u Amiga myši signály TTL, tj. log. 0 je 0V až cca 1V a log. 1 přibližně 2.5V až 5V.
Velikost myši je docela běžná, nijak nevybočuje ani ve srovnání se "současnými", resp. vyráběnými o cca 10 až 20 let později. Na pravém obrázku je vidět obvod 74HC14N tvořící veškerou logiku myši. Konstrukce je tedy narozdíl od RS232 a pozdějších myší extrémně jednoduchá. Přesto bývaly i tyto myši velmi drahé a tehdy možná ještě o pár korun dražší kvůli barvě. Opravdu, i mnoho let potom bylo u PC běžné, že skoro všechny komponenty byly v barvě "slonovinová kost", tj. trochu zažloutle béžové plasty a výjimečně jiné (nejčastěji bílé, hnědé, černé).
Konstrukce Amiga myši
Na prvním obrázku je kromě jednoduché elektroniky jasně vidět i konektor s pouze osmi vodiči. Zapojené je totiž pouze levé a pravé tlačítko. Na připojení prostředního tlačítka už vodič nezbyl i kdyby to interface umožňoval.
Všimněte si přepínače na spodní straně myši, ale nenechte se zmást písmeny MS/PC, to se této myši netýká (plast je společný i pro RS232 variantu). Smysl mají písmena AM a AT, které značí počítače Amiga a Atari. K oběma se používala TTL myš, ale u Atari byly oproti Amize jinak zpřeházené signály z clonek. Pro ZX Spectrum je správná poloha přepínače AM
Konstrukce mechaniky je opět velmi jednoduchá, dva válečky s clonkami a přítlačné kolečko s pružinkou. Válečky i kolečko bylo občas nutné očistit, protože se na ně přes kuličku lepí prach z podložky. Ten vytvoří nejprve tenkou vrstvu, později tlustší a hrbolatější až se nakonec začnou válečky, nebo kulička zadrhávat.
Na snímku je vidět i trochu odřené místo, kde se kulička válečků dotýká, běžný důsledek používání.
Stavový diagram pulzů na výstupu myši

Délka pulzů záleží na rychlosti pohybu myši. Aby se kurzor myši mohl pohnout musí být dokončena celá sekvence pulzů od stavu 0, 0 do stavu 0, 0. Pořadí pulzů udává směr pohybu, resp. směr pohybu je možné zjistit z toho, který pulz přijde první. Pokud sekvence začíná jedním z pulzů a končí tímtéž, pohyb není detekován (odpovídá pohybu myši o stejnou vzdálenost tam a zpět) a kurzorem myši nebude pohnuto.
Zapojení konektoru A-Mouse
Pro srovnání jsem přidal i zapojení Kempston joysticku. Tlačítko 2 se u joystiku využívá výjimečně, pokud ano, tak by vždy měla existovat i alternativní klávesa, která dělá totéž. Dvě tlačítka bývají na joystiku často, ale málokterý joystik je má zapojená samostatně.
bit | vývod | Kempston joystick | Amiga Myš |
---|---|---|---|
0 | 4 | vpravo | osa X2 (XB) |
1 | 3 | vlevo | osa Y1 (YA) |
2 | 2 | dolů | osa X1 (XA) |
3 | 1 | nahoru | osa Y2 (YB) |
4 | 6 | tlačítko 1 | tlačítko 1 (levé) |
5 | 9 | tlačítko 2 (výjimečně) | tlačítko 2 (pravé) |
6 | 5 | tlačítko 3 (prostřední) | |
7 | nezapojeno | nezapojeno | |
7 | +5V | +5V | |
8 | GND | GND |
V případě UR-4 je pro 2. a 3. tlačítko nutné doplnit invertory po vzoru ostatních signálů joysticku (jako směry a fire). V případě jiných interface možná ne, např Jiiirův UPI má zapojená všechna 3 tlačítka.
Nepřipojený bit 7 znamená, že interface na tomto bitu vždy vrací 0. Podle toho lze při čtení hodnoty z portu 31 softwarově odhadnout přítomnost Kempston joystiku, resp. kompatibilního rozhraní.
Na snímku konektoru je černou čárkou označený vývod číslo 1. Následující nákres ukazuje číslování všech vývodů kabelového konektoru.

- HwB - popis konektoru pro připojení myši a joysticku k Amize
- HwB - popis konektoru podobné myši používané u Atari
Kempston Mouse
Kempston Mouse interface vytvořila v roce 1986 stejná firma, jako interface pro připojení joysticků na port 31 jehož vylepšenou variantou je i UR-4. Jako polohovací zařízení se k interface připojuje zas TTL myš podobná té k Amize (zpřeházené vývody, viz schéma překreslené Velesoftem), ale navíc je v interface logika, která signály z clonek převádí na byte, jehož hodnota se mění v rozsahu <0, 255> podle směru a rychlosti pohybu myši. Logika interface prakticky dělá totéž, co by jinak musel provádět procesor. Uživateli pak stačí přečíst ze dvou portů hodnoty pro osy X a Y jednou za čas, třeba jednou za 1/50s. Nároky na čas procesoru jsou tak minimální.
S touto myší jsem se poprvé setkal v emulátoru X128, později jsem ji objevil na ruských webových stránkách. V Rusku byla zjevně oblíbená pro svou použitelnost i ve hrách, např. v předělávce WarCraft 1 pro ZX Spectrum "Black Raven" (rusky Чёрный Ворон) a mnoha dalších, dokonce není problém ji používat v Basicu, což ani s A-Mouse, ani s RS232 myší přímo možné není.
Kempston Mouse používá šestnáctibitové adresy portů (detailněji v tomto článku) a to na portech uvedených v tabulce. Původní interface pracoval se dvěma tlačítky, ruské verze i se třemi, v některých případech bylo levé a pravé tlačítko přehozené. Velesoftův interface podporuje tři tlačítka s možností levé a pravé přehodit, navíc na horních 4 bitech vrací hodnotu v rozsahu <0, 15> měnící se podle pohybu kolečkem myši. Princip čtení kolečka je stejný jako princip čtení polohy myši.
porty Kempston mouse
Hex | Dec | označení | poznámka |
---|---|---|---|
#FADF | 64223 | tlačítka | B0=pravé, B1=levé, B2=střední (0=stisknuto, 1=nestisknuto) |
#FBDF | 64479 | souřadnice X | souřadnice v intervalu <0, 255> |
#FFDF | 65503 | souřadnice Y | souřadnice v intervalu <0, 255> |
#FEDF | 65247 | souřadnice Z | kolečko myši implementované Velesoftem (později, přesunuto na port tlačítek kvůli kompatibilitě, verze 2008 zde vrací obsah portu #7FFD, na orig. ZXS 128k nečitelný) |
Kempston Mouse vrací hodnotu od 0 do 255 i pro Y-ovou souřadnici, je tedy potřeba provést jednoduchou korekci na výšku obrazovky 192px. Hodnoty je možné chápat jako absolutní souřadnici, což je triviální, ale v některých ohledech problematické, nebo porovnáním s minulou hodnotou získat posun určitým směrem a ten pak použít.
- článek o Kempston Mouse na Wikipedii
- článek o originální Kempston mouse od Velesofta
- podrobnosti o KMouse Turbo 2008 na webu Velesofta
- můj článek o KMouse
Program zobrazující šipku ovládanou myší
Šipku zobrazovanou následujícím programem lze ovládat buď klávesami (Sinclair joystick, OPQAM), Kempston joystickem, nebo Amiga myší. Program je napsán univerzálně, podle bitu 7 v log. 1 (což s připojenou UR-4/UPI nenastane) detekuje přítomnost interface pro Kempston joystick, nebo Amiga myš na portu 31 a podle současně nastavených bitů pro směry vlevo a vpravo, nebo nahoru a dolů dokáže rozlišit Amiga myš od joysticku. Případně lze obojí vypnout, kdyby to náhodou na nějaké hardwarové konfiguraci nefungovalo.
Program umožňující volat myš z Basicu (kvůli HL')
Nezapomeňte si upravit cesty ke vkládaným zdrojovým textům sipka.za a downhl.za.
;============================================================================== ; TESTOVACÍ PROGRAM PRO ŠIPKU ;============================================================================== cpu z80undoc org 60000 START di push ix exx push hl ; HL' nutno zachovat kvůli Basicu exx ld a,6 out (254),a call MOUSE ld a,2 out (254),a END exx pop hl exx pop ix ei ret EXIT ld a,1 out (254),a jr END XYIKON db 0,255,0,192 ; x1,x2,y1,y2 (celá obrazovka) dw EXIT db 255 include ../libs/sipka.za include ../libs/downhl.za
Vlastní ovladač myši
Program byl zkoušen v emulátoru FUSE a kompilován kompilerem AS, nicméně s drobnými úpravami konstant by měl být zkompilovatelný kdekoliv. Zdrojový text je mimochodem odsazován po 10 znacích, některé řádky jsou proto trochu rozházené.
;============================================================================== ; KOMPLEXNÍ PROGRAM PRO ČTENÍ KLÁVESNICE, AMIGA MYŠI A K-MOUSE ;============================================================================== ; Stručný princip: ; ; Vezmi původní souřadnice, spočítej adresu na obrazovce (MOUSE_XY). ; Vykresli šipku na obrazovku, zároveň ulož co bylo pod ní. ; Zpracuj vstup ze zvoleného HID a spočítej nové souřadnice. ; Zapiš nové souřadnice. ; Zapiš stav tlačítek HID (proměnná MOUSE_B) ; Čekej na přerušení. ; Smaž šipku a místo ní vykresli původní obsah obrazovky. ; Opakuj celý proces dokud není stisknuto tlačítko fire. ; Zjisti jestli a na jakou ikonu bylo kliknuto, jinak opakuj. ; Skoč na obslužnou rutinu ikony (JP). ; Význam bitů proměnné MOUSE_B: ; ; bit 0 = klávesa 1, nebo levé tlačítko myši ; bit 1 = klávesa 2, nebo pravé tlačítko myši ; bit 2 = klávesa 3, nebo prostřední tlačítko myši ; ; další tlačítka nejsou definována %00000xxx - horní bity jsou vždy 0 ; ; update (spíše jen úvaha do budoucna): ; bit 3 = kolečko myši nahoru?, resp. tlačítko 4 ; bit 4 = kolečko myši dolu, resp. tlačítko 5 ; bit 5 = tlačítko 6, resp. tlačítko pod kolečkem myši MOUSE_X equ MOUSE+2 ; poslední známé souřadnice šipky MOUSE_Y equ MOUSE+1 MOUSE_XY equ MOUSE_Y ; 16ti bitové souřadnice MOUSE_T equ MOUSE_S+1 ; typ zařízení 0=KEYS, 1=AMOUSE, 2=KMOUSE MOUSE_B equ MOUSEBUTT+1 ; stav tlačítek MOUSE_KS equ MOUSEKS ; KEYSTEP, velikost kroku při ovládání pomocí kláves MOUSE ld hl,96+128*256 ; souřadnice šipky X do L, Y do H push hl ; náhrada za neexistující instrukci ld bc,hl pop bc ; takže X je v C, Y v B ld ix,MSIPKA ; do IX adresu spritu exx ld hl,MSIPKA_B ; do HL' adresu bufferu na pozadi sipky exx ld a,b ; vezmi Y-ovou souradnici (jaký význam má v A?) call 8881 ; ze souřadnic v BC spočítej adresu ve VRAM do HL ld (MOUSEC+1),hl ; ulož tuto adresu, bude užitečná při mazání šipky ld (MOUSE2+1),a ; toto cislo budu odecitat, co znamena ???? ; vykreslení šipky - pochází z knihy Assembler a ZX Spectrum II, komentáře jsem přepsal ld b,15 ; sprite šipky je vysoký 15 pixelů (mimochodem široký je 1 byte) MOUSE1 push bc ; ulož kolik opakování - mikrořádků zbývá push hl ; dvakrát ulož adresu šipky ve VRAM, na kterou se bude kreslit push hl ld h,0 ; do H ulož 0, sem se bude rotovat sprite/maska, pokud to bude třeba ld l,(ix+0) ; do L přečti byte spritu ld d,h ; vynuluj D (to samé jako H) ld e,(ix+15) ; do E přečti byte masky inc ix ; posuň ukazatel na grafiku spritu ld a,8 ; rotovat můžu nejvýše 8x MOUSE2 sub 0 ; od počtu rotací odečtu počet rotací vlevo a získám počet rotací vpravo ld b,a ; počet rotací vpravo si uložím do B MOUSE3 add hl,hl ; HL *= 2 (náhrada rr hl) ex de,hl ; prohoď HL a DE (add de,de taky bohužel neexistuje) add hl,hl ; HL *= 2 (náhrada rr de) ex de,hl ; HL a DE prohoď zase zpátky djnz MOUSE3 ; jednobytový sprite a maska jsou uloženy v HL a DE posunuté jak je třeba ex (sp),hl ; prohoď poslední hodnotu v zásobníku (adresa šipky ve VRAM) a obsahem HL pop bc ; do BC tak ze zásobníku vyzvednu odrotovanou předlohu ld a,(hl) ; do A načtu původní obsah obrazovky exx ld (hl),a ; uložím na (HL') - adresa bufferu na původní pozadí (1. levý byte, budou dva) inc hl ; posunu ukazatel do bufferu exx ld a,d ; vezmu do a pravou část masky cpl ; invertuju ji (kdybych ji uložil už invertovanou, měl bych problém s rotací) and (hl) ; a z pozadí vymažu ty pixely, kde měla maska 0 or b ; a do vykousnutého pozadí zaoruju předlohu ld (hl),a ; a nakonec uložím do VRAM ; call RIGHTL ; spočítej adresu o byte vpravo inc hl ld a,(hl) ; celé kreslení provedu ještě jednou pro 2. byte více vpravo exx ld (hl),a inc hl exx ld a,e cpl and (hl) or c ld (hl),a pop hl ; obnov adresu levého bytu ve VRAM call DOWNHL ; spočítej adresu o pixel níž pop bc ; obnov počítadlo djnz MOUSE1 ; a opakuj, dokud nejsou vykresleny všechny mikrořádky šipky ; volba polohovacího zařízení 0=KEYS, 1=AMOUSE, 2=KMOUSE MOUSE_S ld a,0 or a jp z,MOUSEB ; A=0 ; Buttons - klávesy dec a jp z,MOUSEA ; A=1 ; Amiga mouse (myška z Amigy zapojená do UR-4) dec a jp z,MOUSEK ; A=2 ; ruská Kempston mouse vracející přímé souřadnice ; v ostatních případech čtu klávesy ;------------------------------------------------------------------------------ ; ZMĚNA SOUŘADNIC [X,Y] pomocí klávesnice ;------------------------------------------------------------------------------ MOUSEB call MOUSRKEY ; prečti porty definovaných kláves, v D bude stav testovaných kláves ld hl,(MOUSE_XY) ; do HL přečti souřadnice šipky MOUSEKS ld c,2 ; velikost kroku šipky, o kolik se šipka pohne při stisku klávesy bit 5,d ; testování 1. klávesy (UP) jr z,MOUSEB1 ; Z = klávesa nebyla stisknuta => přeskoč zpracování ld a,h ; vezmi z H Y-ovou souřadnici sub c ; odečti krok posunu ld h,a ; ulož novou Y-ovou souřadnici do H jr nc,MOUSEB1 ; nedošlo-li k podtečení, přeskoč korekci ld h,0 ; C = šipka narazila do horního okraje => proveď korekci, aby neprošla MOUSEB1 bit 6,d ; testování 2. klávesy (DOWN) jr z,MOUSEB2 ; Z = klávesa nebyla stisknuta => přeskoč zpracování ld a,h ; vezmi z H Y-ovou souřadnici add a,c ; pričti krok posunu ld h,a ; ulož novou Y-ovou souřadnici do H cp 189 ; a otestuj jestli šipka neprošla dolním okrajem jr c,MOUSEB2 ; není-li souřadnice větší než 189, přeskoč korekci ld h,190 ; C = šipka narazila do dolního okraje => proveď korekci, aby neprošla MOUSEB2 bit 3,d ; testování 3. klávesy (LEFT) jr z,MOUSEB3 ; Z = klávesa nebyla stisknuta => přeskoč zpracování ld a,l ; vezmi z L X-ovou souřadnici sub c ; odečti krok posunu ld l,a ; ulož novou X-ovou souřadnici do L jr nc,MOUSEB3 ; nedošlo-li k podtečení, přeskoč korekci ld l,0 ; C = šipka narazila do levého okraje => proveď korekci, aby neprošla MOUSEB3 bit 4,d ; testování 4. klávesy (RIGHT) jr z,MOUSEB4 ; Z = klávesa nebyla stisknuta => přeskoč zpracování ld a,l ; vezmi z L X-ovou souřadnici add a,c ; přičti krok posunu ld l,a ; ulož novou X-ovou souřadnici do L cp 252 ; a otestuj jestli šipka neprošla pravým okrajem jr c,MOUSEB4 ; není-li souřadnice větší než 252, přeskoč korekci ld l,252 ; C = šipka narazila do pravého okraje => proveď korekci, aby neprošla MOUSEB4 ld a,d ; vezmi do A stav prečtených kláves and 00000111b ; ponech jen bity, které označují tlačítka jako fire (jako tlač. myši) ld (MOUSE_B),a ; a stav tlačítek zapiš do proměnné MOUSE_B ld (MOUSE_XY),hl ; ulož nové souřadnice šipky pro příští použití jp MOUSE50 ; Rutina na čtení kláves z knihy "Assembler a ZX Spectrum 2" ; Může být společná pro klávesu a Kempston joystick (nemá s ruskou Kempston Myší nic společného, jen jméno) MOUSRKEY ld hl,MOUSEKTAB ; vezmi adresu tabulky kláves ld de,7 ; v E je počet kláves a v D bude výsledek (1 = stisknuto) MOUSRK1 ld c,(hl) ; do BC prečti z tabulky adresu portu inc hl ld b,(hl) inc hl in a,(c) ; prečti port (BC - 16ti bitové adresování) bit 7,c ; otestuj bit 7, u kempston joysticku je tam vždy 0 (leda by byl vadný) jp z,MOUSRK2 ; přeskoč CPL jedná-li se o Kempston joystick cpl ; 1 = klávesa stisknuta (normálně to je u kláves obráceně) MOUSRK2 and (hl) ; ponech jen testovaný bit (filtrace tabulkou) inc hl ; a posuň HL na začátek dalšího řádku tabulky jr z,MOUSRK3 set 7,d ; nastav bit 7 na 1 MOUSRK3 srl d ; a posuň ho dolů (tím se do D postupně uloží stav všech kláves) dec e ; sniž počítadlo portů k prečtení jr nz,MOUSRK1 ; opakuj dokud není vše přečteno ret ; Tabulka kódů kláves, kterou je možné měnit - první 2 byty jsou adresou portu, 3. byte je bitový filtr. ; Tímto způsobem je možno definovat i Kempston joystick, ale není možné ho rozumně detekovat, pokud je ; zároveň připojena amiga mouse, uživatel musí sám rozhodnout co chce používat, nejlépe stiskem klávesy. ; Kempston joystick a klávesy je samozřejmě možné libovolně kombinovat, i když to asi není praktické. MOUSEKTAB db 254, 127, 00000100b ; FIRE 1 (M) db 254, 127, 00001000b ; FIRE 2 (N) db 254, 127, 00010000b ; FIRE 3 (B) db 254, 223, 00000010b ; LEFT (O) db 254, 223, 00000001b ; RIGHT (P) db 254, 251, 00000001b ; UP (Q) db 254, 253, 00000001b ; DOWN (A) ;------------------------------------------------------------------------------ ; ZMĚNA SOUŘADNIC [X,Y] pomocí AMIGA MOUSE ;------------------------------------------------------------------------------ ; Pozor! Interface s MHB8255 je nutné inicializovat mimo tento program. MOUSEA ld bc,130*256 ; B = počet průchodů čtecí smyčkou (rozumný kompromis) ld a,(MOUSE_X) ; souřadnice se budou uvnitř smyčky měnit a je lépe budou-li operandem ld (MOUSAX+1),a ld a,(MOUSE_Y) ld (MOUSAY+1),a MOUSEA1 push bc ; uloz BC do zasobniku - zde zacina smycka ld b,c ; a do B ????? in a,(31) ; čti port ld de,MOUSEAP ; pomocná proměnná call MOUS_SM ; zjisti jakym smerem se mys pohnula MOUSAX ld a,77h ; vezmi souradnice mysi add a,(hl) jr z,MOUSAKX ; Z = preskoc zapis X-ove souradnice ld (MOUSAX+1),a MOUSAKX inc de in a,(31) ; čti port rrca ; posun o 1 bit vpravo, kvuli detekci smeru call MOUS_SM ; a ted se da pouzit stejna rutina jako pro X MOUSAY ld a,60h ; vezmi starou Y-ovou souradnici add a,(hl) ; a pricti cislo prectene z tabulky jr z,MOUSAKY ; Z = preskoc zapis a korekci Y-ove souradnice cp 192 ; otestuj jestli sipka neprosla spodnim okr. jr nz,MOUSADO ; pokud prosla (Z) ld a,191 ; proced korekci MOUSADO ld (MOUSAY+1),a ; zapis novou Y-ovou souradnici MOUSAKY pop bc ; obnov pocitadlo pruchodu djnz MOUSEA1 ; a opakuj pokud tento nebyl posledni ld a,(MOUSAX+1) ; zapis nove souradnice do promennych ld (MOUSE_X),a ld a,(MOUSAY+1) ld (MOUSE_Y),a in a,(31) ; naposledy precti port mysi rra rra rra rra and 00000111b ; ponech jen bity tlacitek ld (MOUSE_B),a jp MOUSE50 MOUS_SM and 5 ; testuje jakym smerem se amiga mys pohnula ld c,a ; na zaklade Karnaughovych map ld a,(de) rlca and 10 or c ld (de),a ld c,a ld hl,MOUSTAB add hl,bc ret MOUSTAB db 0,255,1,0 ; tabulka kódů pro výpočet pohybu AMOUSE db 1,0,0,255 db 255,0,0,1 db 0,1,255,0 MOUSEAP dw 0 ; promenna tykajici se vyhradne detekce smeru ; pohybu AMIGA MOUSE ;------------------------------------------------------------------------------ ; ZMENA SOURADNIC [X,Y] pomocí KMOUSE (Ruská verze - později i od Velesofta) ;------------------------------------------------------------------------------ ; .... OTESTOVAT V PRAXI! MOUSEK ld a,251 ; cti X-ovou souradnici z portu 64479 in a,(223) ld (MOUSE_X),a ; uloz pro pristi zavolani programu MOUSE ld a,255 in a,(223) ; cti Y-ovou souradnici z portu 65503 cpl ; u souradnice Y nam nevyhovuje hodnota nad 192 cp 191 ; takze provedu jednoduchou korekci jp c,MOUSEKK ; IF A>191 THEN A=191 ld a,191 MOUSEKK ld (MOUSE_Y),a ; a uloz pro dalsi volani programu MOUSE ld a,250 ; cti port 64223 - BUTTONS in a,(223) ; ale ziskal jsem nevhodny zpusob ulozeni stavu cpl ; takze zase provedu korekci, nejdrive neguju and 00000111b ; byte a pak z nej necham jen dolni 3 bity ld b,a ; zalohuju do B a ted prehodim bit 0 a bit 1 rla ; bit 0 v A posunu na pozici bitu 1 and 00000010b ; ponecham jen bit 1 ld c,a ; a ulozim do C ld a,b ; znovu vezmu puvodni byte rra ; posunu bit 1 v A na pozici bitu 0 and 00000001b ; ponecham jen bit 0 or c ; pridam bit 1 ulozeny v C ld c,a ; ted budu mit v C ulozene prehozene bity 0 a 1 ld a,b ; naposledy vezmu puvodni byte and 00000100b ; ponecham z nej jen bit 2 or c ; pridam k nemu bity 0 a 1 ld (MOUSE_B),a ; ulozim do pameti a je hotovo jp MOUSE50 ; Před HALT (za MOUSE50) je možno přidat automatickou detekci polohovacího zařízení a ; následnou změnu proměnné MOUSE_T. V dalším volaní pak bude takto zvolené zařízení ; normálně používáno. ; autodetect KEYBOARD - Je-li stisknuta klávesa přepne se ovladač na čtení klávesnice, užitečné ; pokud uživatel potřebuje z jakéhokoliv důvodu ovládat program klávesnicí ; ale byla zvolena myš. ; xor a ; ctu port 0*256+254 ; in a,(254) ; cpl ; and %00011111 ; ponecham dolnich 5 bitu ; jr nz,MOUSE50 ; ld a,0 ; do A cislo odpovidajici klavesnici ; ld (MOUSE_T),a ; a zapisu ho do promenne MOUSE_T ; autodetect AMIGA MOUSE - Amiga mouse se oproti Kempston joystiku liší tím, že u ní mohou běžně ; nastat log. 1 na bitech, které u joysticku znamenají protilehlé směry, ; takže je není možno zvolit bez jeho mechanického zničení. ; Bohužel detekce nemůže být 100% spolehlivá, ačkoli většinou funguje. ; in a,(31) ; čti port na němž je připojena myš ; bit a,7 ; je-li bit 7 log. 1 pravděpodobně port 31 není funkční ; jp nz,MOUSE50 ; takže zbytek rutiny přeskoč ; and %101 ; tyto bity nemohou být nikdy v log. 1 pokud ; cp %101 ; je připojen jenom Kempston joystick ; jp nz,MOUSE50 ; Z = bity byly v log. 1 => myš je pravděpodobně připojena ; ld a,1 ; do A číslo odpovídající amiga myši ; ld (MOUSE_T),a ; a zapíšu ho do proměnné MOUSE_T ; Jak jednoduše detekovat KEMPSTON MOUSE nevím! ; Jak jednoduše detekovat KEMPSTON joystick nevím (resp. vím, ale ne v kombinaci s Amiga mouse)! MOUSE50 ei ; povolím přerušení, pokud náhodou povolené nebylo halt ; a počkám na něj (paprsek začíná kreslit obrazovku) ; případný zákaz přerušení si přidejte sami ; smazání šipky a vykreslení původního obsahu obrazovky MOUSEC ld hl,0 ; do operandu je místo 0 zapisována adresa šipky ve VRAM ld b,15 ; počet pixelů na výšku ld de,MSIPKA_B ; adresa uloženého původnho pozadí pod šipkou MOUSEC1 ld a,(de) ; vezmu byte z původního pozadí ld (hl),a ; a zapíšu ho do VRAM inc de ; posunu DE o 1 push hl ; zapamatuju HL call RIGHTL ; a spočítám adresu HL o byte vpravo (inc HL nestačí, kus šipky může zmizet) ld a,(de) ; vezmi další byte z původního pozadí ld (hl),a ; a zapíšu ho do VRAM inc de ; posunu DE o 1 pop hl ; obnovím v HL adresu levého bytu call DOWNHL ; a z ní spočítám adresu o pixel níž djnz MOUSEC1 ; opakuj tolikrát, kolik pixelů na výšku šipka má MOUSEBUTT ld a,0 ; vezmi stav stisknutí tlačítek or a ; 0 = žádné nebylo stisknuto jp z,MOUSE ; pokud nebylo tlačítko stisknuto, opakuj činnost celého programu ret ; nějaké tlačítko bylo stisknuto, vrať se, záleží na programu ; využívajícím šipku jak tlačítka zpracuje (tím může být NOIKON) ;============================================================================== ; GRAFIKA A NĚKTERÉ PROMĚNÉ ;============================================================================== MSIPKA db 00000000b ; sprite šipky db 01000000b db 01100000b db 01110000b db 01111000b db 01111100b db 01111110b db 01111000b db 01001000b db 00001000b db 00000100b db 00000100b db 00000010b db 00000010b db 00000000b MSIPKA_M db 11100000b ; maska šipky - musí následovat hned za spritem db 11110000b db 11111000b db 11111100b db 11111110b db 11111111b db 11111111b db 11111111b db 11111100b db 11111110b db 00011110b db 00001111b db 00001111b db 00000111b db 00000111b MSIPKA_B ds 30 ; sem se ukládá z VRAM to co šipka překryla ;============================================================================== ; PODPŮRNÉ RUTINY ;============================================================================== RIGHTL ld a,l ; RIGHTL zajištuje posun adresy spritu ve inc l ; VRAM o byte vpravo a jeho spravné vykreslení, xor l ; pokud je jeho levá půlka přímo u pravého bit 5,a ; okraje obrazovky. V takovém případě se ret z ; pravá půlka kreslí do ROM, takže vlastně ld h,0 ; nekreslí / BACHA NA WRITEABLE ROMky!! (nahradit 0 číslem 60, poškodí font) ret ; include downhl.za ; tato rutina by mela byt soucasti programu, který myš používá
;============================================================================== ; RUTINA, KTERÁ ZAVOLÁ ŠIPKU A VOLÁ JI TAK DLOUHO DOKUD UŽIVATEL NEKLIKNE ; NA NĚKTEROU PLATNOU IKONU (POLOHA DEFINOVANÁ V TABULCE). V TOM OKAMŽIKU ; RUTINA SKOČÍ NA ADRESU PŘÍSLUŠNÉ RUTINY, KTERÁ IKONĚ ODPOVÍDÁ. ;============================================================================== NOICON call MOUSE ; zavolej program pro obsluhu HID a kreslení šipky na obrazovku ; rutinu NOICON možno volat pomocí CALL a instrukci ; RET umístit do rutiny reagující na kliknuti na ikonu TSTXY ld de,(MOUSE_XY) ; souřadnice šipky do DE (D = X, E = Y) ld bc,6 ; do BC délku souřadnic v tabulce ikon a adresy příslušné rutiny ld ix,XYIKON-6 ; do IX adresu tabulky ikon a adres rutin mínus jednu položku TSTXY_1 add ix,bc ; pričti BC k registru IX ld a,(ix+0) ; čti X1 cp 255 ; porovnej s 255 - znamená konec tabulky jr z,NOICON ; je-li 255 (Z) nebylo kliknuto na ikonu a bude opakováno kreslení šipky ld a,(ix+0) ; jinak porovnávej dál, dokud není nalezena ikona, nebo konec tabulky cp d jr nc,TSTXY_1 ld a,(ix+1) cp d jr c,TSTXY_1 ld a,(ix+2) cp e jr nc,TSTXY_1 ld a,(ix+3) cp e jr c,TSTXY_1 ld h,(ix+5) ; bylo kliknuto na nějakou ikonu, takže ld l,(ix+4) ; přečti do HL adresu obslužné rutiny jp (hl) ; a skoč na tuto adresu ; TOTO JE JEN UKAZKA - takovato tabulka by mela byt soucasti programu ; ;XYIKON db 0,16,0,16 ; x1,x2,y1,y2 ; defw EXIT_I ; adresa vykonne rutiny ; db 255 ; konec tabulky ikon (NUTNE! Nikdy nesmí chybět!) ; ;EXIT_I ; priklad ; ret ;==============================================================================
Celý ovladač myši je nutné spouštět od adresy NOICON. Rutina TEST_M je skutečně jen k testování, to není vstupní bod programu. Je nutné mít správně vyplněnou tabulku XYIKON, která obsahuje souřadnice ikon a adresu rutiny, která bude zavolána po kliknutí na ikonu. A za poslední, před tuto rutinu doporučuju přidat možnost volby ovládání, rozhodně bych si ve svém programu nedovolil jako defaultní ovladač použít jednu z myší. Když už, tak klávesy. A pokud má uživatel možnost změnit šipkou (třeba v menu) ovládání, musí existovat možnost totéž provést klávesnicí i po změně na myš.
Download
Zdroje informací: Tak různě z webu (porty a schéma připojení Kempston mouse), knížka Assembler a ZX Spectrum (prapůvodní základy pro kreslení šipky ovládané klávesami), a dost vlastních zkušeností.
Související odkazy
- HwB - popis konektoru pro připojení myši a joysticku k Amize
- HwB - popis konektoru podobné myši používané u Atari
- článek o Kempston Mouse na Wikipedii
- článek o originální Kempston mouse od Velesofta
- podrobnosti o KMouse Turbo 2008 na webu Velesofta
- můj článek o KMouse
Opravené chyby
- 28.2.2004 - celý článek přepracován, výrazně rozšířen úvod, opraveny chyby, doplněn datasheet 74HC14 a obrázek myši zevnitř.
- 11.4.2005 - opraveny přehozené bity 0 a 1 (v tabulce i diagramu), doplněny odkazy na HWBook s popisem konektorů, vše znovu pečlivě zkontrolováno podle reálného fungujícího hardwaru, upozornil Velesoft
- 23.12.2015 - revidováno, promazán balast a nesmysly z textu, doplněny obrázky, opraven pinout (poštouchl nalezenou chybou z00m).