Stránka sa načítava, prosím čakajte…
© 2005 – 2024 Roman Horváth, všetky práva vyhradené. Dnes je 27. 4. 2024.
Dátum: 26. 10. 2013, pred viacerými rokmi, aktualizované: 30. 7. 2020, pred štyrmi rokmi
Na tejto stránke je publikovaný ukážkový projekt, ktorý môže tvoriť základ pre hru v žánri textovej adventúry. Ide len o návrh malej časti rozhrania hry. Termín textová adventúra označuje žáner hry, ktorá komunikuje s hráčom výhradne textovou formou. Aj napriek negrafickej orientácii projektu sú v ňom používané viaceré súčasti programovacieho rámca grafického robota.
- Zdrojové súbory projektu na prevzatie:
textova-adventura.7z
5,42 kB (5,29 KiB), 30. 7. 2020
Ukážka okna po spustení aplikácie a zadaní niekoľkých príkazov.
~
import knižnica.*; /** * Na programovaní textovej adventúry sa dá pekne predviesť podstata * objektového modelovania. Budeme pracovať s bežnými pojmami z reálneho * sveta, ale namiesto ich reálneho zobrazovania budeme pracovať s ich * textovými opismi, čo je pre tento žáner hry charakteristické. * * Na ukážku je v tomto projekte vytvorených niekoľko jednoduchých tried * reprezentujúcich miestnosti, predmety a hráča (avatara). * * Pri objektovom modelovaní ide o to, aby: * – vlastnosti boli vyjadrené premennými, ktoré sú súkromné, * – ku každej vlastnosti bolo poskytnuté programátorské rozhranie, to jest * definícia jednej alebo viacerých verejných metód, ktoré slúžia na * prácu s touto vlastnosťou. * * Toto rozhranie môže byť tvorené v podstate tromi základnými „druhmi“ metód: * – metódami, ktoré slúžia na zápis vlastností, * – metódami, ktoré slúžia na čítanie vlastností, * – metódami, ktoré slúžia na „inú prácu“ s vlastnosťami (to môže byť * čokoľvek; napríklad použitie objektu v súčinnosti s iným objektom, * vnútorné spracovanie údajov a podobne). * * Každá trieda sa stará výhradne o svoje „životné funkcie.“ Vytvorené * inštancie tried „oživujú“ hru. Používajú na to programátorské rozhranie * tried, to jest ich verejné metódy. */ public class Adventúra extends GRobot { private final static Písmo písmoKonzoly = new Písmo("Verdana", Písmo.NORMÁLNE, 14); // Definície miestností: private final Miestnosť škola = new Miestnosť("škola", "Si v škole."); private final Miestnosť ulica = new Miestnosť("ulica", "Si na ulici."); private final Miestnosť park = new Miestnosť("park", "Si v parku."); // Definície predmetov: private final Predmet kniha = new Predmet("kniha", "Toto je kniha."); private final Predmet lopta = new Predmet("lopta", "Toto je lopta."); private final Predmet list = new Predmet("list", "Toto je list."); // Definícia avatara: private final Avatar avatar = new Avatar(škola); // Konštruktor public Adventúra() { // Priradenie vlastností jednotlivým inštanciám miestností. // V tomto štádiu rozprogramovania to súvisí najmä s prepojením // miestostí navzájom. Názov a opis miestnosti sú priradené priamo // v pri konštrukcii (to jest pri new Miestnosť("…", "…") – pozri // vyššie). Okrem toho tu môžu byť uvedené rôzne prepojenia – // napríklad sú tu vložené predmety do jednotlivých miestností. // Škola: škola.prepojMaS(ulica); škola.vložPredmet(kniha); // Ulica: ulica.prepojMaS(škola); ulica.prepojMaS(park); ulica.vložPredmet(lopta); // Park: park.prepojMaS(ulica); park.vložPredmet(list); // Definícia obsluhy udalostí s jedinou reakciou spracúvajúcou // potvrdenie údajov v príkazovom riadku. new ObsluhaUdalostí() { public void potvrdenieÚdajov() { spracujPríkaz(); } }; // Nastavenie iného písma vnútornej konzoly sveta (na zlepšenie // čitateľnosti). Svet.písmo(písmoKonzoly); // Zobrazenie a aktivácia vstupného riadka. Svet.neskrývajVstupnýRiadok(); Svet.začniVstup("Zadaj príkaz:"); // Výpis počiatočného stavu hry. vypíšStav(); } /** * Výpis aktuálneho stavu hry. */ public void vypíšStav() { // Vypíše sa opis miestnosti, v ktorej sa práve nachádza avatar. avatar.kdeSom().vypíšOpis(); // Vypíše sa zoznam dverí. avatar.kdeSom().vypíšZoznamDverí(); // Výpis predmetov prítomných/viditeľných v miestnosti. avatar.kdeSom().vypíšZoznamPredmetov(); // Výpis zoznamu predmetov v inventári avatara. avatar.vypíšInventár(); // Vynechanie prázdneho riadka. Svet.vypíšRiadok(); } /** * Pokus o prechod do miestnosti identifikovanej zadaným názvom. Ak * metóda uspeje, vráti true, inak vráti false. */ public boolean choďDo(String názovMiestnosti) { // Hľadajú sa dvere: Miestnosť prechod = avatar.kdeSom().hľadajDvere(názovMiestnosti); if (null != prechod) { // Zmena miestnosti a vrátenie hodnoty true, ktorá v tomto // prípade znamená úspešnosť akcie. avatar.presuňDo(prechod); return true; } // Hodnota false informuje o neúspešnosti vykonania požadovanej akcie. return false; } /** * Pokus o zobratie predmetu identifikovaného zadaným názvom. V prípade, * že je akcia úspešná vráti metóda hodnotu true, inak false. */ public boolean zober(String názovPredmetu) { // Hľadá sa predmet v aktuálnej miestnosti: Predmet predmet = avatar.kdeSom().hľadajPredmet(názovPredmetu); if (null != predmet) { // Zobratie predmetu pozostáva z dvoch čiastkových akcií: // odstránenie predmetu zo zoznamu predmetov aktuálnej miestnosti // a vloženie predmetu do inventára avatara. Návratová hodnota // true signalizuje, že akcia bola úspešná (to de facto znamená, // že predmet bol nájdený v aktuálnej miestnosti, pretože žiadne // iné podmienky nie sú v súčasnosti overované). avatar.kdeSom().odstráňPredmet(predmet); avatar.vložPredmet(predmet); return true; } // Hodnota false informuje o neúspešnosti vykonania požadovanej akcie. return false; } /** * Pokus o položenie predmetu identifikovaného zadaným názvom. V prípade, * že je akcia úspešná vráti metóda hodnotu true, inak false. */ public boolean polož(String názovPredmetu) { // Hľadá sa predmet v inventári avatara: Predmet predmet = avatar.hľadajPredmet(názovPredmetu); if (null != predmet) { // Podobne ako zobratie predmetu, aj položenie pozostáva z dvoch // čiastkových akcií: odstránenie predmetu z inventára // a vloženie do zoznamu predmetov aktuálnej miestnosti. Opäť, // návratová hodnota true signalizuje, že akcia bola úspešná. avatar.odstráňPredmet(predmet); avatar.kdeSom().vložPredmet(predmet); return true; } // Hodnota false informuje o neúspešnosti vykonania požadovanej akcie. return false; } // Rozpoznanie príkazu a spustenie prislúchajúcich akcií. public void spracujPríkaz() { // Definícia reťazca „príkaz“ (s hodnotou prevzatou zo vstupného // riadka) a deklarácia reťazca „parameter.“ String príkaz = Svet.prevezmiReťazec(), parameter; // Vypísanie príkazu (ozvena) a jeho prevod na malé písmená. vypíšText(modrá, príkaz); príkaz = príkaz.toLowerCase(); // Ak sa zadaný príkaz začína slovom „choď“ (rovnako v ďalších // prípadoch): if (príkaz.startsWith("choď ")) { // Prvých päť znakov (to jest aj medzera za slovom) sa preskočí // a zvyšok textu sa uloží do premennej „parameter.“ parameter = príkaz.substring(5); // Pokus o prechod do zadanej miestnosti (to jest tej, // ktorej meno je v premennej „parameter“). if (choďDo(parameter)) { // V prípade úspechu sa vymaže obrazovka // a vypíše sa nový stav hry. strop.vymažTexty(); vypíšStav(); } else // (Výpis chybového stavu – rovnako v ďalších prípadoch…) vypíšText(červená, "Odtiaľto sa tam nedá ísť!", true); } else if (príkaz.startsWith("zober ")) { // Principiálne rovnaké získanie parametra ako pri príkaze choď. parameter = príkaz.substring(6); // Pokus o zobratie predmetu if (zober(parameter)) // V prípade úspechu sa vypíše pozitívna spätná väzba vypíšText(zelená, "Zobral si predmet: " + parameter + ".", true); else vypíšText(červená, "Nič také tu nevidíš!", true); } else if (príkaz.startsWith("polož ")) { // Principiálne rovnaké získanie parametra ako pri príkaze choď. parameter = príkaz.substring(6); // Pokus o zobratie predmetu if (polož(parameter)) // V prípade úspechu sa vypíše pozitívna spätná väzba vypíšText(zelená, "Položil si predmet: " + parameter + ".", true); else vypíšText(červená, "Nič také nemáš!", true); } else if (príkaz.startsWith("pomoc")) { vypíšText(zelená, "Pomocník"); vypíšText(zelená, "K dispozícii sú nasledujúce príkazy: choď, " + "zober, polož, pomoc a koniec. Väčšina príkazov vyžaduje " + "zadanie parametra. Napríklad: choď ulica, zober kniha " + "a pod.", true); } else if (príkaz.startsWith("koniec")) { Svet.koniec(); } else { vypíšText(červená, "Neznámy príkaz!", true); } } /** * Vlastná metóda na výpis textov. Prijíma farbu textu, text a argument * určujúci, či sa má po vypísaní textu vynechať jeden prázdny riadok. */ public static void vypíšText(Farba farba, String text, boolean vynechajRiadok) { Svet.farbaTextu(farba); Svet.vypíšRiadok(text); if (vynechajRiadok) Svet.vypíšRiadok(); } /** * Vlastná metóda na výpis textov. Správa sa ako predchádzajúca metóda, * ale neprijíma argument určujúci, či sa má po vypísaní textu vynechať * jeden prázdny riadok. Správa sa tak, ako keby bolo zadané false. */ public static void vypíšText(Farba farba, String text) { vypíšText(farba, text, false); } /** * Vlastná metóda na výpis textov. Správa sa ako predchádzajúca metóda, * ale neprijíma argument určujúci farbu textu. Správa sa tak, ako keby * bola zadaná čierna. */ public static void vypíšText(String text) { vypíšText(čierna, text, false); } /** * Vlastná metóda na výpis textov. Správa sa ako predchádzajúca metóda, * ale namiesto argumentu typu String prijíma argument typu StringBuffer. * To je užitočné, pretože viaceré metódy ďalších tried tohto projektu * skladajú svoj výstup práve do premennej typu StringBuffer. */ public static void vypíšText(StringBuffer text) { vypíšText(čierna, text.toString(), false); } // Vytvorením novej inštancie adventúry sa automaticky spustí // konštruktor Adventúra(), ktorý inicializuje novú hru (vytvorí // prepojenia medzi miestnosťami a pod.). public static void main(String[] args) { new Adventúra(); } }
~
import knižnica.*; /** * Trieda slúži na definíciu rôznych vlastností miestnosti. */ public class Miestnosť { // Zoznam dverí vedúcich z tejto miestnosti do ďalších (predvolene je // prázdny). private final Zoznam<Miestnosť> dvere = new Zoznam<Miestnosť>(); // Zoznam predmetov, ktoré sú prítomné (viditeľné) v tejto miestnosti // (predvolene je prázdny). private final Zoznam<Predmet> zoznamPredmetov = new Zoznam<Predmet>(); // Názov tejto miestnosti – jediný konštruktor tejto triedy vyžaduje // jeho zadanie. private String názov; // Slovný opis miestnosti – jediný konštruktor tejto triedy vyžaduje // jeho zadanie. private String opis; /** * Konštruktor vyžaduje zadanie názvu a slovného opisu miestnosti. */ public Miestnosť(String názov, String opis) { priraďNázov(názov); priraďOpis(opis); } /** * Vloženie predmetu do zoznamu predmetov tejto miestnosti. */ public void vložPredmet(Predmet predmet) { zoznamPredmetov.pridaj(predmet); } /** * Odstránenie predmetu zo zoznamu predmetov tejto miestnosti. */ public void odstráňPredmet(Predmet predmet) { zoznamPredmetov.odober(predmet); } /** * Nájdenie predmetu v zozname predmetov podľa názvu. */ public Predmet hľadajPredmet(String názovPredmetu) { // Hľadám predmet (pri hľadaní používam metódu porovnajNázov). // Keď ho nájdem, vrátim nájdenú inštanciu predmetu. for (Predmet predmet : zoznamPredmetov) if (predmet.porovnajNázov(názovPredmetu)) return predmet; // Inak vrátim null. return null; } /** * Zostavenie a výpis zoznamu predmetov, ktoré sú prítomné (viditeľné) * v tejto miestnosti, na obrazovku. */ public void vypíšZoznamPredmetov() { if (zoznamPredmetov.veľkosť() <= 0) return; StringBuffer zoznam = new StringBuffer( "Vidíš tu nasledujúce predmety: " + zoznamPredmetov.daj(0).názov()); for (int i = 1; i < zoznamPredmetov.veľkosť(); ++i) zoznam.append(", " + zoznamPredmetov.daj(i).názov()); zoznam.append("."); Adventúra.vypíšText(zoznam); } /** * Vytvorenie prepojenia s inou miestnosťou, to jest pridanie inštancie * inej miestnosti do vnútorného zoznamu dverí tejto miestnosti. Do tých * miestností, ktoré sú v tomto zozname dverí jestvuje jednosmerný * priechod z tejto miestnosti (čiže hráč môže opustiť túto miestnosť * a vstúpiť do hociktorej miestnosti v zozname dverí; z toho vyplýva, * že v skutočnosti nejestvuje žiadna konkrétna trieda „Dvere.“) * Na to, aby bol priechod obojsmerný, musí byť definované aj spätné * prepojenie. */ public void prepojMaS(Miestnosť ináMiestnosť) { dvere.pridaj(ináMiestnosť); } /** * Nájdenie miestnosti v zozname dverí podľa názvu. */ public Miestnosť hľadajDvere(String cieľováMiestnosť) { // Hľadám dvere (pri hľadaní používam metódu porovnajNázov). // Keď ich nájdem, vrátim nájdenú inštanciu miestnosti. for (Miestnosť cieľ : dvere) if (cieľ.porovnajNázov(cieľováMiestnosť)) return cieľ; // Inak vrátim null. return null; } /** * Zostavenie a výpis zoznamu dverí na obrazovku. */ public void vypíšZoznamDverí() { if (dvere.veľkosť() <= 0) return; StringBuffer zoznam = new StringBuffer( "Môžeš ísť na tieto miesta: " + dvere.daj(0).názov()); for (int i = 1; i < dvere.veľkosť(); ++i) zoznam.append(", " + dvere.daj(i).názov()); zoznam.append("."); Adventúra.vypíšText(zoznam); } /** * Priradenie nového názvu. Túto metódu používa konštruktor, ale môže * poslúžiť aj na zmenu názvu miestnosti počas hry. */ public void priraďNázov(String novýNázov) { názov = novýNázov; } /** * Táto metóda zistí, či sa názov tejto miestnosti zhoduje so zadaným * reťazcom. To je využiteľné pri hľadaní konkrétnej miestnosti * v zozname miestností. (Riešenie porovnávania názvu s pomocou * samostatnej metódy je užitočné, lebo otvára možnosti ďalšieho * rozširovania modelu: v prípade potreby sa do tejto metódy môže pridať * ďalšie spracovanie názvu na porovnanie, čo sa vďaka tomu, že názov * nebudeme nikdy porovnávať priamo prejaví celoplošne.) */ public boolean porovnajNázov(String názovNaPorovnanie) { return názov.equalsIgnoreCase(názovNaPorovnanie); } /** * Táto metóda vráti názov tejto miestnosti. */ public String názov() { return názov; } /** * Priradenie nového slovného opisu miestnosti. Túto metódu používa * konštruktor a môže poslúžiť na zmenu slovného opisu miestnosti počas * hry. */ public void priraďOpis(String novýOpis) { opis = novýOpis; } /** * Táto metóda slúži na výpis slovného opisu miestnosti na obrazovku. */ public void vypíšOpis() { if (null != opis) Adventúra.vypíšText(opis); } }
~
// import knižnica.*; // (Zatiaľ priamo nepoužíva žiadnu triedu rámca.) /** * Trieda slúži na definovanie vlastností predmetov v hre. */ public class Predmet { // Názov tohto predmetu – jediný konštruktor tejto triedy vyžaduje jeho // zadanie. private String názov; // Slovný opis tohto predmetu – jediný konštruktor tejto triedy vyžaduje // jeho zadanie. private String opis; /** * Konštruktor vyžaduje zadanie názvu a slovného opisu predmetu. */ public Predmet(String názov, String opis) { priraďNázov(názov); priraďOpis(opis); } /** * Priradenie nového názvu. Túto metódu používa konštruktor, ale môže * poslúžiť aj na zmenu názvu predmetu počas hry. */ public void priraďNázov(String novýNázov) { názov = novýNázov; } /** * Táto metóda zistí, či sa názov tohto predmetu zhoduje so zadaným * reťazcom. To je využiteľné pri hľadaní konkrétneho predmetu. * (Pozri aj informácie v opise metódy Miestnosť.porovnajNázov.) */ public boolean porovnajNázov(String názovNaPorovnanie) { return názov.equalsIgnoreCase(názovNaPorovnanie); } /** * Táto metóda vráti názov tohto predmetu. */ public String názov() { return názov; } /** * Priradenie nového slovného opisu predmetu. Túto metódu používa * konštruktor a môže poslúžiť aj na zmenu slovného opisu predmetu počas * hry. */ public void priraďOpis(String novýOpis) { opis = novýOpis; } /** * Táto metóda slúži na výpis slovného opisu predmetu na obrazovku. */ public void vypíšOpis() { if (null != opis) Adventúra.vypíšText(opis); } }
~
import knižnica.*; /** * Trieda slúži na reprezentáciu avatara hráča v hre. */ public class Avatar { // Zoznam predmetov, ktoré vlastní avatar (predvolene je prázdny). private final Zoznam<Predmet> inventár = new Zoznam<Predmet>(); // Aktuálna miestnosť, v ktorej sa avatar práve nachádza. private Miestnosť kdeSom; /** * Konštruktor vyžaduje zadanie začiatočnej pozície avatara, to jest * miestnosti, v ktorej sa hra začína. */ public Avatar(Miestnosť začiatok) { kdeSom = začiatok; } /** * Vloženie predmetu do inventára. */ public void vložPredmet(Predmet predmet) { inventár.pridaj(predmet); } /** * Odstránenie predmetu z inventára. */ public void odstráňPredmet(Predmet predmet) { inventár.odober(predmet); } /** * Nájdenie predmetu v inventári podľa názvu. */ public Predmet hľadajPredmet(String názovPredmetu) { // Hľadám predmet (pri hľadaní používam metódu porovnajNázov). // Keď ho nájdem, vrátim nájdenú inštanciu. for (Predmet predmet : inventár) if (predmet.porovnajNázov(názovPredmetu)) return predmet; // Inak vrátim null. return null; } /** * Zostavenie a výpis zoznamu predmetov (inventára), ktoré avatar * vlastní, na obrazovku. */ public void vypíšInventár() { if (inventár.veľkosť() <= 0) return; StringBuffer zoznam = new StringBuffer( "Vlastníš tieto predmety: " + inventár.daj(0).názov()); for (int i = 1; i < inventár.veľkosť(); ++i) zoznam.append(", " + inventár.daj(i).názov()); zoznam.append("."); Adventúra.vypíšText(zoznam); } /** * Táto metóda slúži na zmenu polohy avatara, čiže na prechod do inej * miestnosti. */ public void presuňDo(Miestnosť miestnosť) { kdeSom = miestnosť; } /** * Táto metóda vráti aktuálnu polohu avatara, čiže inštanciu miestnosti, * v ktorej sa práve nachádza. */ public Miestnosť kdeSom() { return kdeSom; } }
Poznámka: Tento projekt je starší. Bude potrebné ho aktualizovať tak, aby bol kompatibilný s najnovšou verziou programovacieho rámca GRobot. (Stalo sa.)
Na tejto stránke je publikovaný ukážkový projekt pre textovú adventúru. Ide len o návrh malej časti rozhrania pre textovú adventúru. Termín textová adventúra označuje hru komunikujúcu s hráčom výhradne textovou formou. Aj napriek negrafickej orientácii projektu sú v ňom používané niektoré časti skupiny tried grafického robota. Na vygenerovanie prázdneho projektu odporúčam použiť Generátor projektov BlueJ (dostupný v sekcii Softvér na prevzatie).
Triedy projektu.
Zdrojové súbory projektu na prevzatie (bez skupiny tried grafického robota):
textova‑adventura‑old.zip
6,75 kB (6,59 KiB), 26. 10. 2013
~
/** * Na programovaní textovej adventúry sa dá pekne predviesť podstata * objektového modelovania. Budeme pracovať s bežnými pojmami z reálneho * sveta, ale namiesto ich reálneho zobrazovania budeme pracovať s textovými * opismi, čo je charakteristické pre tento druh hry. * * Na ukážku je v tomto projekte vytvorených niekoľko jednoduchých tried * reprezentujúcich miestnosti, predmety a hráča (avatara). * * Pri objektovom modelovaní ide o to, aby: * – vlastnosti boli vyjadrené premennými, ktoré sú súkromné, * – ku každej vlastnosti bolo poskytnuté programátorské rozhranie, to jest * definícia jednej alebo viacerých verejných metód, ktoré slúžia na * prácu s touto vlastnosťou, * – rozrhanie sa môže skladať z troch základných „druhov“ metód: * – metódy na zápis vlastností, * – metódy na čítanie vlastností, * – metódy na „inú prácu“ s vlastnosťami (napr. použitie)… * * Každá trieda sa stará výhradne o svoje „životné funkcie“. Vytvorené * inštancie tried „oživujú“ hru. Používajú na to programátorské rozhranie * tried, to jest ich verejné metódy. */ public class Adventúra extends GRobot { private final static Písmo písmoKonzoly = new Písmo("Verdana", Písmo.NORMÁLNE, 14); // Definície miestností: private final Miestnosť škola = new Miestnosť("škola", "Si v škole."); private final Miestnosť ulica = new Miestnosť("ulica", "Si na ulici."); private final Miestnosť park = new Miestnosť("park", "Si v parku."); // Definície predmetov: private final Predmet kniha = new Predmet("kniha", "Toto je kniha."); private final Predmet lopta = new Predmet("lopta", "Toto je lopta."); private final Predmet list = new Predmet("list", "Toto je list."); // Definícia avatara: private final Avatar avatar = new Avatar(škola); // Konštruktor public Adventúra() { // Priradenie vlastností jednotlivým inštanciám miestností. // V tomto štádiu rozprogramovania to súvisí najmä s prepojením // miestostí navzájom. Názov a opis miestnosti sú priradené priamo // v pri konštrukcii (to jest pri new Miestnosť("…", "…") – pozri // vyššie). Okrem toho tu môžu byť uvedené rôzne prepojenia – // napríklad sú tu vložené predmety do jednotlivých miestností. // Škola: škola.prepojMaS(ulica); škola.vložPredmet(kniha); // Ulica: ulica.prepojMaS(škola); ulica.prepojMaS(park); ulica.vložPredmet(lopta); // Park: park.prepojMaS(ulica); park.vložPredmet(list); // Definícia obsluhy udalostí s jedinou reakciou spracúvajúcou // potvrdenie údajov v príkazovom riadku. new ObsluhaUdalostí() { public void potvrdenieÚdajov() { spracujPríkaz(); } }; // svet.písmo(písmoKonzoly); // Zobrazenie a aktivácia vstupného riadka. svet.neskrývajVstupnýRiadok(); svet.začniVstup("Zadaj príkaz:"); // Výpis počiatočného stavu hry. vypíšStav(); } /** * Výpis aktuálneho stavu hry. */ public void vypíšStav() { // Vypíše sa opis miestnosti, v ktorej sa práve nachádza avatar. avatar.kdeSom().vypíšOpis(); // Vypíše sa zoznam dverí. avatar.kdeSom().vypíšZoznamDverí(); // Výpis predmetov prítomných/viditeľných v miestnosti. avatar.kdeSom().vypíšZoznamPredmetov(); // Výpis zoznamu predmetov v inventári avatara. avatar.vypíšInventár(); // Vynechanie prázdneho riadka. svet.vypíšRiadok(); } /** * Pokus o prechod do miestnosti identifikovanej zadaným názvom. Ak * metóda uspeje, vráti true, inak vráti false. */ public boolean choďDo(String názovMiestnosti) { // Hľadajú sa dvere: Miestnosť prechod = avatar.kdeSom().hľadajDvere(názovMiestnosti); if (null != prechod) { // Zmena miestnosti a vrátenie hodnoty true, ktorá v tomto // prípade znamená úspešnosť akcie. avatar.presuňDo(prechod); return true; } // Hodnota false informuje o neúspešnosti vykonania požadovanej akcie. return false; } /** * Pokus o zobratie predmetu identifikovaného zadaným názvom. V prípade, * že je akcia úspešá vráti metóda hodnotu true, inak false. */ public boolean zober(String názovPredmetu) { // Hľadá sa predmet v aktuálnej miestnosti: Predmet predmet = avatar.kdeSom().hľadajPredmet(názovPredmetu); if (null != predmet) { // Zobratie predmetu pozostáva z dvoch čiastkových akcií: // odstránenie predmetu zo zoznamu predmetov aktuálnej miestnosti // a vloženie predmetu do inventára avatara. Návratová hodnota // true signalizuje, že akcia bola úspešná (to de facto znamená, // že predmet bol nájdený v aktuálnej miestnosti, pretože žiadne // iné podmienky nie sú v súčasnosti overované). avatar.kdeSom().odstráňPredmet(predmet); avatar.vložPredmet(predmet); return true; } // Hodnota false informuje o neúspešnosti vykonania požadovanej akcie. return false; } /** * Pokus o položenie predmetu identifikovaného zadaným názvom. V prípade, * že je akcia úspešá vráti metóda hodnotu true, inak false. */ public boolean polož(String názovPredmetu) { // Hľadá sa predmet v inventári avatara: Predmet predmet = avatar.hľadajPredmet(názovPredmetu); if (null != predmet) { // Podobne ako zobratie predmetu, aj položenie pozostáva z dvoch // čiastkových akcií: odstránenie predmetu zo inventára // a vloženie do zoznamu predmetov aktuálnej miestnosti. Opäť, // návratová hodnota true signalizuje, že akcia bola úspešná. avatar.odstráňPredmet(predmet); avatar.kdeSom().vložPredmet(predmet); return true; } // Hodnota false informuje o neúspešnosti vykonania požadovanej akcie. return false; } // Rozpoznanie príkazu a spustenie príslušných akcií. public void spracujPríkaz() { // Definícia reťazca „príkaz“ (s hodnotou prevzatou zo vstupného // riadka) a deklarácia reťazca „parameter“. String príkaz = svet.prevezmiReťazec(), parameter; // Vypísanie príkazu (ozvena) a jeho prevod na malé písmená. vypíšText(modrá, príkaz); príkaz = príkaz.toLowerCase(); // Ak zadaný príkaz začína slovom „choď“ if (príkaz.startsWith("choď ")) { // Prvých päť znakov (to jest aj medzera za slovom) sa preskočí // a zvyšok textu sa uloží do premennej „parameter“. parameter = príkaz.substring(5); // Pokus o prechod do zadanej miestnosti (to jest tej, // ktorej meno je v premennej „parameter“). if (choďDo(parameter)) { // V prípade úspechu sa vymaže obrazovka // a vypíše sa nový stav hry. strop.vymažTexty(); vypíšStav(); } else vypíšText(červená, "Odtiaľto sa tam nedá ísť!", true); } else if (príkaz.startsWith("zober ")) { // Principiálne rovnaké získanie parametra ako pri príkaze choď. parameter = príkaz.substring(6); // Pokus o zobratie predmetu if (zober(parameter)) // V prípade úspechu sa vypíše pozitívna spätná väzba vypíšText(zelená, "Zobral si predmet: " + parameter + ".", true); else vypíšText(červená, "Nič také tu nevidíš!", true); } else if (príkaz.startsWith("polož ")) { // Principiálne rovnaké získanie parametra ako pri príkaze choď. parameter = príkaz.substring(6); // Pokus o zobratie predmetu if (polož(parameter)) // V prípade úspechu sa vypíše pozitívna spätná väzba vypíšText(zelená, "Položil si predmet: " + parameter + ".", true); else vypíšText(červená, "Nič také nemáš!", true); } else if (príkaz.startsWith("pomoc")) { vypíšText(zelená, "Pomocník"); vypíšText(zelená, "K dispozícii sú nasledujúce príkazy: choď, " + "zober, polož, pomoc a koniec. Väčšina príkazov vyžaduje " + "zadanie parametra. Napríklad: choď ulica, zober kniha " + "a pod.", true); } else if (príkaz.startsWith("koniec")) { svet.koniec(); } else { vypíšText(červená, "Neznámy príkaz!", true); } } /** * Vlastná metóda na výpis textov. Prijíma farbu textu, text a argument * určujúci, či sa má po vypísaní textu vynechať jeden prázdny riadok. */ public static void vypíšText(Farba farba, String text, boolean vynechajRiadok) { svet.farbaTextu(farba); svet.vypíšRiadok(text); if (vynechajRiadok) svet.vypíšRiadok(); } /** * Vlastná metóda na výpis textov. Správa sa ako predchádzajúca metóda, * ale neprijíma argument určujúci, či sa má po vypísaní textu vynechať * jeden prázdny riadok. Správa sa tak, ako keby bolo zadané false. */ public static void vypíšText(Farba farba, String text) { vypíšText(farba, text, false); } /** * Vlastná metóda na výpis textov. Správa sa ako predchádzajúca metóda, * ale neprijíma argument určujúci farbu textu. Správa sa tak, ako keby * bola zadaná čierna. */ public static void vypíšText(String text) { vypíšText(čierna, text, false); } /** * Vlastná metóda na výpis textov. Správa sa ako predchádzajúca metóda, * ale namiesto argumentu typu String prijíma argument typu StringBuffer. */ public static void vypíšText(StringBuffer text) { vypíšText(čierna, text.toString(), false); } // Vytvorením novej inštancie adventúry sa automaticky spustí // konštruktor Adventúra(), ktorý inicializuje novú hru (vytvorí // prepojenia medzi miestnosťami a pod.). public static void main(String[] args) { new Adventúra(); } }
~
/** * Trieda slúži na definíciu rôznych vlastností miestnosti. */ public class Miestnosť { // Zoznam dverí vedúcich z tejto miestnosti do ďalších (predvolene je // prázdny). private final GRobot.Zoznam<Miestnosť> dvere = new GRobot.Zoznam<Miestnosť>(); // Zoznam predmetov, ktoré sú prítomné (viditeľné) v tejto miestnosti // (predvolene je prázdny). private final GRobot.Zoznam<Predmet> zoznamPredmetov = new GRobot.Zoznam<Predmet>(); // Názov tejto miestnosti – jeho zadanie vyžaduje jediný konštruktor. private String názov; // Slovný opis miestnosti – jeho zadanie vyžaduje jediný konštruktor. private String opis; /** * Konštruktor vyžaduje zadanie názvu a slovného opisu miestnosti. */ public Miestnosť(String názov, String opis) { priraďNázov(názov); priraďOpis(opis); } /** * Vloženie predmetu do zoznamu. */ public void vložPredmet(Predmet predmet) { zoznamPredmetov.pridaj(predmet); } /** * Odstránenie predmetu zo zoznamu. */ public void odstráňPredmet(Predmet predmet) { zoznamPredmetov.odober(predmet); } /** * Nájdenie predmetu v zozname podľa názvu. */ public Predmet hľadajPredmet(String názovPredmetu) { // Hľadám predmet (pri hľadaní používam metódu porovnajNázov). // Keď ho nájdem, vrátim nájdenú inštanciu. for (Predmet predmet : zoznamPredmetov) if (predmet.porovnajNázov(názovPredmetu)) return predmet; // Inak vrátim null. return null; } /** * Zostavenie a výpis zoznamu predmetov, ktoré sú prítomné (viditeľné) * v tejto miestnosti, na obrazovku. */ public void vypíšZoznamPredmetov() { if (zoznamPredmetov.veľkosť() <= 0) return; StringBuffer zoznam = new StringBuffer( "Vidíš tu nasledujúce predmety: " + zoznamPredmetov.daj(0).názov()); for (int i = 1; i < zoznamPredmetov.veľkosť(); ++i) zoznam.append(", " + zoznamPredmetov.daj(i).názov()); zoznam.append("."); Adventúra.vypíšText(zoznam); } /** * Vytvorenie prepojenia s inou miestnosťou, to jest pridanie inštancie * inej miestnosti do vnútorného zoznamu tejto miestnosti. Tie * miestnosti, ktoré sú v zozname dverí, do tých jestvuje jednosmerný * prechod, čiže hráč môže opustiť túto miestnosť a vstúpiť do hociktorej * miestnosti v zozname dverí. (Z toho vyplýva, že v skutočnosti * nejestvuje žiadna konkrétna trieda „Dvere“.) Na to, aby bol prechod * obojsmerný, musí byť definované aj spätné prepojenie. */ public void prepojMaS(Miestnosť ináMiestnosť) { dvere.pridaj(ináMiestnosť); } /** * Nájdenie miestnosti v zozname dverí podľa názvu. */ public Miestnosť hľadajDvere(String cieľováMiestnosť) { // Hľadám dvere (pri hľadaní používam metódu porovnajNázov). // Keď ich nájdem, vrátim nájdenú inštanciu. for (Miestnosť cieľ : dvere) if (cieľ.porovnajNázov(cieľováMiestnosť)) return cieľ; // Inak vrátim null. return null; } /** * Zostavenie a výpis zoznamu dverí na obrazovku. */ public void vypíšZoznamDverí() { if (dvere.veľkosť() <= 0) return; StringBuffer zoznam = new StringBuffer( "Môžeš ísť na tieto miesta: " + dvere.daj(0).názov()); for (int i = 1; i < dvere.veľkosť(); ++i) zoznam.append(", " + dvere.daj(i).názov()); zoznam.append("."); Adventúra.vypíšText(zoznam); } /** * Priradenie nového názvu. Túto metódu používa konštruktor, ale môže * poslúžiť aj na zmenu názvu miestnosti počas hry. */ public void priraďNázov(String novýNázov) { názov = novýNázov; } /** * Metóda zistí, či sa názov tejto miestnosti zhoduje so zadaným * reťazcom. To je využiteľné pri hľadaní konkrétnej miestnosti * v zozname miestností. */ public boolean porovnajNázov(String názovNaPorovnanie) { return názov.equalsIgnoreCase(názovNaPorovnanie); } /** * Metóda vráti názov tejto miestnosti. */ public String názov() { return názov; } /** * Priradenie nového slovného opisu miestnosti. Túto metódu používa * konštruktor a môže poslúžiť na zmenu slovného opisu miestnosti počas * hry. */ public void priraďOpis(String novýOpis) { opis = novýOpis; } /** * Táto metóda slúži na výpis slovného opisu miestnosti na obrazovku. */ public void vypíšOpis() { if (null != opis) Adventúra.vypíšText(opis); } }
~
/** * Trieda slúži na definovanie vlastností predmetov v hre. */ public class Predmet { // Názov tohto predmetu – jeho zadanie vyžaduje jediný konštruktor. private String názov; // Slovný opis tohto predmetu – jeho zadanie vyžaduje jediný konštruktor. private String opis; /** * Konštruktor vyžaduje zadanie názvu a slovného opisu predmetu. */ public Predmet(String názov, String opis) { priraďNázov(názov); priraďOpis(opis); } /** * Priradenie nového názvu. Túto metódu používa konštruktor, ale môže * poslúžiť aj na zmenu názvu predmetu počas hry. */ public void priraďNázov(String novýNázov) { názov = novýNázov; } /** * Metóda zistí, či sa názov tohto predmetu zhoduje so zadaným * reťazcom. To je využiteľné pri hľadaní konkrétneho predmetu. */ public boolean porovnajNázov(String názovNaPorovnanie) { return názov.equalsIgnoreCase(názovNaPorovnanie); } /** * Metóda vráti názov tohto predmetu. */ public String názov() { return názov; } /** * Priradenie nového slovného opisu predmetu. Túto metódu používa * konštruktor a môže poslúžiť na zmenu slovného opisu predmetu počas * hry. */ public void priraďOpis(String novýOpis) { opis = novýOpis; } /** * Táto metóda slúži na výpis slovného opisu predmetu na obrazovku. */ public void vypíšOpis() { if (null != opis) Adventúra.vypíšText(opis); } }
~
/** * Trieda slúži na reprezentáciu avatara hráča v hre. */ public class Avatar { // Zoznam predmetov, ktoré vlastní avatar (predvolene je prázdny). private final GRobot.Zoznam<Predmet> inventár = new GRobot.Zoznam<Predmet>(); // Aktuálna miestnosť, v ktorej sa avatar nachádza. private Miestnosť kdeSom; /** * Konštruktor vyžaduje zadanie začiatočnej pozície avatara, to jest * miestnosti, v ktorej sa hra začína. */ public Avatar(Miestnosť začiatok) { kdeSom = začiatok; } /** * Vloženie predmetu do inventára. */ public void vložPredmet(Predmet predmet) { inventár.pridaj(predmet); } /** * Odstránenie predmetu z inventára. */ public void odstráňPredmet(Predmet predmet) { inventár.odober(predmet); } /** * Nájdenie predmetu v inventári podľa názvu. */ public Predmet hľadajPredmet(String názovPredmetu) { // Hľadám predmet (pri hľadaní používam metódu porovnajNázov). // Keď ho nájdem, vrátim nájdenú inštanciu. for (Predmet predmet : inventár) if (predmet.porovnajNázov(názovPredmetu)) return predmet; // Inak vrátim null. return null; } /** * Zostavenie a výpis zoznamu predmetov (inventára), ktoré avatar * vlastní, na obrazovku. */ public void vypíšInventár() { if (inventár.veľkosť() <= 0) return; StringBuffer zoznam = new StringBuffer( "Vlastníš tieto predmety: " + inventár.daj(0).názov()); for (int i = 1; i < inventár.veľkosť(); ++i) zoznam.append(", " + inventár.daj(i).názov()); zoznam.append("."); Adventúra.vypíšText(zoznam); } /** * Metóda slúži na zmenu polohy avatara, čiže na prechod do inej * miestnosti. */ public void presuňDo(Miestnosť miestnosť) { kdeSom = miestnosť; } /** * Metóda vráti aktuálnu polohu avatara, čiže inštanciu miestnosti, * v ktorej sa nachádza. */ public Miestnosť kdeSom() { return kdeSom; } }