GCM – Maj: Angular RPG. Potwory w świecie gry.

Chyba nikogo nie zaskoczy fakt, że post o grze majowej pojawia się w czerwcu 🙂 Dobra wiadomość jest taka, że tworzenie gry tekstowej w AngularJS idzie pełną parą i wszystko wskazuje na to, że projekt będzie skończony w pierwszym tygodniu czerwca 😉

Tymczasem do gry dodałem wstępną implementację systemu przeciwników. Losowo pojawiają się oni w wybranych lokacjach i atakują gracza gdy ten wejdzie na ich teren. Gracz może oczywiście oddać 🙂 Póki co nie ma żadnego systemu walki, ale odpowiednie pod niego fundamenty już stoją.

Tworzenie gry tekstowej w AngularJS

Jak zwykle, w aktualną wersję gry zagrać można klikając w obrazek powyżej.

Nie ma co owijać w bawełnę, przejdę od razu do konkretów. Postaram się opisać wszystkie nowości we w miarę logicznym porządku. Jeśli jednak coś będzie nie zrozumiałe, lub coś pominę, dajcie znać. Wszystko chętnie wytłumaczę 🙂 . Zacznę od nowego pliku czyli monsterService.js:

Jak widać jest to dość prosty serwis przypisany do głównego modułu. Posiada on zdefiniowane dwa elementy: metodę update oraz obiekt monsters. Zacznę od tego drugiego. Klucze w polach tego obiektu to łańcuchy znaków równe rodzajom potworów. Przypisane do nich wartości to funkcje, które są konstruktorami instancji danego potwora. Każdy z tych konstruktorów przyjmuje dwa argumenty, pierwszy będzie unikatowym (dla danej lokacji) identyfikatorem potwora, a drugi wartością decydującą kiedy nastąpi pierwszy atak (potwory mogą być tworzone w grupach, nie chcę aby wszystkie atakowały na raz). Przeznaczenie konkretnych pól obiektów potworów powinno być jasne. Nie wszystkie póki co są wykorzystywane, te które są, opiszę gdy będą wykorzystywane w jakimś kodzie.

Funkcja update tego serwisu, przyjmować będzie listę obiektów stworzonych z opisanych powyżej konstruktorów. Dla każdego potwora z tej listy, sprawdzam czy już czas aby zaatakował. Jeżeli tak i jeżeli jego nastawienie jest wrogie (wartość pola attitude to aggresive), wartość pola attacking ustawiana jest na true, a licznik czas do kolejnego ataku jest zerowany. Jest to system bardzo podobny do systemu zarządzania akcjami gracza 🙂 .

Kolejne nowości pojawiły się w serwisie lokacji, czyli w pliku roomService.js. Każdy obiekt lokacji ma dwa nowe pola encounters oraz monsters. Oto przykład:

Pierwsze pole, to tablica zawierająca informacje o tym jakie potwory można spotkać w danej lokacji, z jaką częstotliwością i w jakiej ilości. Każdy element tej tablicy to obiekt przechowujący te informacje dla osobnego potwora. Drugie nowe pole to lista potworów, które aktualnie się tu znajdują. Póki co, na początku gry jest ona pusta dla wszystkich lokacji.

Do uzupełnienia tej tablicy służy nowa funkcja znajdująca się w serwisie roomService, spawnMonsters:

spawnMonsters jako argument otrzymuje nazwę aktualnego pokoju. Następnie dla każdego obiektu w polu encounters danego pomieszczenia, wybierana jest losowo liczba pomiędzy 0 a 1. Jeżeli wylosowana liczba jest mniejsza niż szansa na danego potwora, losowana jest kolejna liczba, tym razem z zakresu ilości możliwych potworów. Kolejny krok to dodanie do tablicy monsters przetwarzanej lokacji tyle nowych obiektów potworów aktualnego. Dla każdego potwora, poprzez konstruktor, ustawiane jest unikatowe name oraz lastAttack.

Kolejną nową funkcją w tym serwisie jest clearRoom:

Funkcja otrzymuje dwa argumenty, nazwę lokacji oraz unikatowe name potwora. Następnie tablica monsters danego pokoju jest przeszukiwana aż znaleziony zostanie odpowiedni przeciwnik. Po odnalezieniu, wróg jest usuwany z tablicy.

I to tyle jeśli chodzi o serwis potworów. Kolejne zmiany, które opiszę, to nowe funkcje w serwisie playerService, które pozwalają graczowi na atakowanie.

Pierwsza z nich to attack:

Jak widać, nic specjalnego. Funkcja jako argument przyjmuje referencje do obiektu potwora. W jej wnętrzu wywoływana jest metoda clearRoom serwisu lokacji, z argumentami równymi, obecnej lokacji gracza, oraz nazwą potwora. Następnie pole performingAction ustawiane jest na true, a pole currentAction na attacking. Działa to prawie identycznie jak w przypadku funkcji walking.

Druga nowość w serwisie gracza, to nowe pole obiektu actionsattacking:

Tak jak w przypadku chodzenia, atakowanie, zajmuje postaci trochę czasu i na chwilę ‚zamraża’ możliwość korzystania z innych akcji. Mechanizm ten opisałem już w poprzednim poście 🙂 .

I tak dochodzę do najważniejszego póki co pliku w grze czyli controller.js, głównego kontrolera. Zmian tutaj jest parę, najważniejsza to z pewnością nowy wygląd pętli gry:

Ok, to lecimy. Na początku aktualizowana jest postać gracza. Następnie, jeżeli w aktualnym pomieszczeniu znajdują się jakieś potwory, wywołuję metodę serwisu monsterService, update. Jako argument przekazuję listę potworów z aktualnej lokacji. Kolejny krok to wywołanie metody kontrolera checkAttackers.
Następna część pętli wywołuje się, jeżeli gracz właśnie wszedł do nowej lokacji. Teraz najpierw sprawdzam, czy lista potworów nowego pokoju jest pusta, jeżeli tak wywołuję metodę spawnMonsters z serwisu potworów. Dalsza część pętli powinna być już zrozumiała.

W kontrolerze pojawiło się też kilka innych nowych metod, ale ich działanie powinno być jasne. Jeżeli coś jednak nie będzie miało sensu, daj znać w komentarzach, chętnie spróbuję wytłumaczyć co miałem na myśli 🙂

Ostatnia zmiana, jaką chciałem dziś przedstawić znajduje się w pliku html. Fragment ten znajduje się pod definicją przycisków odpowiedzialnych za poruszanie się po świecie:

Ten element z dyrektywą ng-repeat, powoduje, że gdy gracz wejdzie do pomieszczenia, w którym znajdują się przeciwnicy, w aplikacji pojawi się ilość przycisków równa ilości potworów. Przyciśnięcie przycisku spowoduje, że postać zaatakuje danego potwora. Nie będę dokładnie opisywał jak to działa (można zerknąć w kod, nie jest zbyt skomplikowane), bo póki co walka nie jest zaimplementowana do końca 😉 Na tę chwilę naciśnięcie przyciska automatycznie zabija potwora, a ataki potworów nic nie robią. Ale to już niedługo się zmieni 🙂

Tyle wystarczy na jeden post. Jeżeli nie chcesz przegapić kolejnych wpisów o AngularRPG, to zachęcam do polubienia mojej strony na facebooku. Zawsze zamieszczam tam informacje o wszystkich nowościach. Jest to też dobre miejsce na kontakt ze mną. Na wszystkie pytania zawsze odpowiem :).

Dodaj komentarz

Twój adres email nie zostanie opublikowany. Pola, których wypełnienie jest wymagane, są oznaczone symbolem *