dungeon master joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă...

55
1 UNIVERSITATEA „ALEXANDRU IOAN CUZA” IAŞI FACULTATEA DE INFORMATICĂ LUCRARE DE LICENŢĂ Dungeon Master Joc de strategie tactic pe platforma Android Propusă de Busuioc D. George Alexandru Sesiunea: Februarie, 2017 Coordonator știinţific Asistent, dr. Vasile Alaiba

Upload: others

Post on 21-Jan-2020

9 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

1

UNIVERSITATEA „ALEXANDRU IOAN CUZA” IAŞI

FACULTATEA DE INFORMATICĂ

LUCRARE DE LICENŢĂ

Dungeon Master – Joc de strategie tactic pe

platforma Android

Propusă de

Busuioc D. George Alexandru

Sesiunea: Februarie, 2017

Coordonator știinţific

Asistent, dr. Vasile Alaiba

Page 2: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

2

UNIVERSITATEA „ALEXANDRU IOAN CUZA” IAŞI

FACULTATEA DE INFORMATICĂ

LUCRARE DE LICENŢĂ

Dungeon Master - Joc de strategie tactic pe

platforma Android

Propusă de

Busuioc D. George Alexandru

Sesiunea: Februarie, 2017

Coordonator știinţific

Asistent, dr. Vasile Alaiba

Page 3: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

3

DECLARAŢIE PRIVIND ORIGINALITATE ŞI RESPECTAREA

DREPTURILOR DE AUTOR

Prin prezenta declar că Lucrarea de licență cu titlul „Dungeon Master” este scrisă de mine şi nu a

mai fost prezentată niciodată la o altă facultate sau instituţie de învățământ superior din ţară sau

străinătate. De asemenea, declar că toate sursele utilizate, inclusiv cele preluate de pe Internet,

sunt indicate în lucrare, cu respectarea regulilor de evitare a plagiatului:

− toate fragmentele de text reproduse exact, chiar şi în traducere proprie din altă limbă,

sunt scrise între ghilimele şi deţin referinţa precisă a sursei;

− reformularea în cuvinte proprii a textelor scrise de către alţi autori deţine referinţa

precisă;

− codul sursă, imagini etc. preluate din proiecte open source sau alte surse sunt utilizate

cu respectarea drepturilor de autor şi deţin referinţe precise;

− rezumarea ideilor altor autori precizează referinţa precisă la textul original.

Iaşi,

Absolvent Busuioc George Alexandru

_________________________

(semnătura în original)

Page 4: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

4

DECLARAŢIE DE CONSIMŢĂMÂNT

Prin prezenta declar că sunt de acord ca Lucrarea de licență cu titlul „ Dungeon Master”, codul

sursă al programelor şi celelalte conţinuturi (grafice, multimedia, date de test etc.) care însoţesc

această lucrare să fie utilizate în cadrul Facultăţii de Informatică. De asemenea, sunt de acord ca

Facultatea de Informatică de la Universitatea „Alexandru Ioan Cuza” Iași să utilizeze, modifice,

reproducă şi să distribuie în scopuri necomerciale programele-calculator, format executabil şi

sursă, realizate de mine în cadrul prezentei lucrări de licenţă.

Iaşi,

Absolvent Busuioc George Alexandru

_________________________

(semnătura în original)

Page 5: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

5

Cuprins

1. Introducere .............................................................................................................................................6

1.1 Motivație ........................................................................................................................................6

1.2 Context ...........................................................................................................................................7

1.3 Aplicații asemănătoare ...................................................................................................................8

1.4 Cerințe funcționale .......................................................................................................................12

1.5 Abordare tehnică ..........................................................................................................................13

2. Contribuții ............................................................................................................................................15

3. Proiectare ..............................................................................................................................................17

3.1 Arhitectura soluției .......................................................................................................................17

3.2 Modelarea datelor .........................................................................................................................22

3.2.1 Modelarea datelor pe aplicația client ....................................................................................22

3.2.2 Modelarea datelor pe server .................................................................................................27

3.3 Interfața cu utilizatorul .................................................................................................................28

4. Implementare ........................................................................................................................................33

5. Manual de utilizare ...............................................................................................................................45

5.2 Meniul principal ...........................................................................................................................45

5.3 Meniul de creare a unui erou ........................................................................................................46

5.4 Interfața utilizatorului ...................................................................................................................48

5.5 Desfășurarea unui joc ...................................................................................................................49

6. Concluzii ..............................................................................................................................................54

7. Referințe ...............................................................................................................................................55

Page 6: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

6

1. Introducere

1.1 Motivație

Consider că fiecare dintre noi a jucat un joc de societate la un moment dat. Unul dintre cele

mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor,

de cele mai multe ori am prefera o variantă mai accesibilă, cu o durată mai scurtă de timp si care

să ne permită participarea la joc de la distanță.

Care ar fi problema sau neajunsul însă pentru un astfel de joc? Toate jocurile de acest tip au

nivelele deja prestabilite. Dacă nu ai reusit într-un astfel de joc să îți învingi adversarul, o vei lua

de la capăt iar modul în care se va desfășura jocul se va repeta. Vei încerca noi tactici si vei

continua să faci acest lucru până vei reuși să descoperi o strategie prin care să câștigi. De aici

reiese faptul că odată ce a fost descoperită o astfel de strategie și vei decide să reiei jocul de la

acel nivel, dificultatea va fi semnificativ redusă deoarece strategia este deja știută și astfel jocul

nu mai oferă nici o satisfacție. De luat în considerare este faptul că uneori căutarea unei strategii

poate deveni o rutină iar jucătorul își va pierde răbdarea, ceea ce va duce la abandonarea

completă a jocului.

Una din soluții ar fi creearea unui joc care de fiecare dată cand este jucat să ofere alte

provocări față de jocul precedent, alte specificații sau o altă abordare. Această soluție presupune

un joc care stimulează capacitatea jucătorului de a lua decizii rapide la fiecare moment și fără

posibilitatea de a planifica totul din timp. Acest lucru duce la explorarea mai multor strategii în

timpul jocului și adaptarea lor la fiecare pas.

Să luăm exemplul unui joc de defensivă în care jucătorul trebuie să împiedice inamicii să

ajungă într-un anumit punct. În primă fază jucătorul va lua pe ghicite anumite decizii pentru a

observa ce strategie îl va duce la câștigarea jocului. În cazul în care jucătorul va pierde, va relua

nivelul precedent si va încerca să modifice strategia anterioară acolo unde consideră că nu a fost

optimă. Inamicii vor veni în aceeași ordine, la aceleași intervale de timp și în același număr de

fiecare dată când nivelul este jucat. Astfel pentru a ajunge la o strategie care să conducă spre

victorie sunt necesare mai multe instanțe ale aceluiași nivel. Acest lucru va face ca jucătorul să își

piardă răbdarea după câteva eșecuri, având în vedere faptul că a trebuit sa repete aceleași

evenimente de mai multe ori fără succes.

Page 7: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

7

Pe de altă parte, dacă punctul care trebuie apărat își modifică poziția la fiecare instanță a

nivelului, va obliga jucătorul să găsească strategii noi pentru jocul curent. Mai mult, cum ar fi

dacă ordinea inamicilor s-ar schimba puțin? Poate aceste lucruri vor veni în ajutorul jucătorului

sau poate îl vor împotmoli și mai mult. Cert este că nu știe ce îl așteaptă iar prin acest lucru se

menține atenția jucătorului și speranța lui că acest joc va fi acela în care strategia lui îl va

conduce la victorie.

1.2 Context

Conceptul de joc de societate a apărut încă de la începutul erei noastre având drept scop

divertismentul jucătorilor. Primele jocuri de societate erau competitive, scopul jocului fiind

eliminarea oponentului sau a oponenților. În timp s-a dezoltat și ideea de jocuri cooperative în

care jucatorii se aliază și creează o strategie pentru a înfrânge jocul. Jocurile de societate se joacă

pe o tablă de joc și urmăresc un set de reguli prestabilite.

Jocurile video au evoluat considerabil in ultimii ani devenind chair o adevarată industrie în

acest sens. Totodată acestea au căutat să se extindă și pe alte platforme, altele decât cele specifice

precum consolele video sau cele deja consacrate cum ar fi calculatorul, ajungând inevitabil si pe

dispozitivele mobile.

În prezent există diverse implementări ale jocurilor de societate, atât pentru jocuri

consacrate precum Monopoly sau Șah, cât și pentru jocuri mai puțin cunoscute. Acestea își

propun să păstreze cât mai multe caracteristici din versiunea originală a jocului dar totodată să

utilizeze avantajele dispozitivului pentru care sunt destinate.

Întrucăt mă consider un pasionat atât al jocurilor de societate cât și al jocurilor video, am

ales să dezvolt o aplicație bazată pe ture, inspirată din jocurile clasice Dungeons&Dragons în

care fiecare sesiune de joc este unică, relativ scurtă si poate fi accesată de oriunde deoarece este

disponibilă pe dispozitivul mobil sau tabletă.

Page 8: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

8

1.3 Aplicații asemănătoare

Dungeon Hunter 51

Această aplicație este un joc pentru telefoane mobile și tablete dezvoltat de Gameloft care

urmărește evoluția unui erou în de tip ce caută să devină cel mai mare căutător de comori. Cadrul

jocului este unul fantastic și conține numeroase funcționalități care fac jucătorul mereu să se

întoarcă.

Jocul conține o campanie prestabilită unde jucătorul urmărește un lanț de nivele și unde

fiecare etapă este dependentă de cea de dinainte. Astfel, pentru a parcurge toată campania, acest

mod trebuie parcurs în ordine la cea mai mică dificultate. Pe parcurs se vor dezlega dificultăți mai

mari pentru același nivel. Acesta este un mod foarte bun de a-ți îmbunătăți eroul, în schimb jocul

devine repetitiv prin faptul că te forțează să revii în locurile deja parcurse.

Figura 1: Harta de campanie Dungeon Hunter 5

Fiecare nivel al jocului presupune ca eroul să ajungă la capătul lui eliminând toți inamicii

pe care îi întămpină folosind două sau trei abilități stabilite de obiectele echipate pe caracter.

Inamicii sunt mereu aceiași dar în funcție de dificultate ei pot fi mai slabi sau mai puternici. La

1 Pagina oficială Dungeon Hunter 5, http://www.dungeonhunter5.com/

Page 9: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

9

fel ca în majoritatea jocurilor harta este mereu aceeași. În caz de eșec nivelul trebuie reluat de la

capăt și va urma același șir de evenimente.

Spre deosebire de marea majoritate a jocurilor pe mobil, acesta oferă posibilitatea de a cere

ajutorul unui aliat de a te asista în timpul jocului. Dezavantajul este că jucătorul aliat este

controlat de un robot și nu de persoana fizică a cărui personaj îi aparține, ceea ce duce la o

experiență mai scăzută a jocului atunci când vine vorba de joc de echipă.

Aplicația conține însă multe moduri prin care poți îmbunătăți eroul tău, începând de la

obiecte pe care le poți lua în timpul jocului până la diferite bonusuri obținute în timpul unor

evenimente organizate de producători. Ca și interacțiune online poți comunica cu persoanele de

pe server pe conversația publică sau cu persoanele înscrise din aceeași echipă.

Figura 2: Interfața și un exemplu de nivel al jocului

Kingdom Rush2

Kingdom Rush este o aplicație pentru mobil și tablete dezvoltată de Armor Games. Este un

joc popular de tip defensiv unde dintr-unul sau mai multe puncte vor pleca grupuri de inamici,

vor urmări o anumită cale iar scopul jucătorului este de a-i împiedica pe aceștia să ajungă la

destinație.

2 Pagina oficială Kingdom Rush http://www.kingdomrush.com/

Page 10: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

10

Jocul se poate juca doar de către o singură persoană simultan și conține o campanie formată

din douăsprezece nivele. Fiecare nivel este diferit și cu cât se progresează pe hartă își vor face

apariția noi tipuri de inamici, culminând în anumite nivele cu un lider puternic. Împiedicarea

acestora se va face prin construirea de turnuri de diferite tipuri care vor elimina, bloca, încetini

sau teleporta în spate unitățile, urmărind calea.

Fiind un joc care nu necesită conexiune la internet tot progresul în această campanie se va

salva local în memoria telefonului sau a tabletei. Aplicația oferă trei astfel de spații unde se poate

salva progresul.

Figura 3: Un exemplu de nivel din Kingdom Rush

Jocul mai oferă posibilitatea de a chema un erou pe câmpul de luptă pentru a te ajuta. Acest

erou este controlabil de către jucător și se poate poziționa oriunde pe hartă, chiar și în calea

Page 11: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

11

inamicilor. Dezavantajul este că acest erou își va folosi abilitățile doar când consideră el că este

necesar și nu la comandă. Totodată eroul este predefinit și nu poate fi modificat în niciun fel.

Numărul de douăsprezece nivele nu este unul tocmai satisfăcător având în vedere faptul că

fiecare dintre ele nu va aduce nimic deosebit față de precedentul. În schimb jocul oferă la fiecare

nivel parcurs două noi moduri în care poate fi terminat acel nivel. Fie inamicii vin într-un singur

grup, fie jocul provoacă jucătorul să construiască doar anumite tipuri de turnuri.

Figura 4: Selecția de eroi din Kingdom Rush

Page 12: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

12

1.4 Cerințe funcționale

Jucătorul poate crea un nou erou bazat pe un set de rase și clase prestabilite de către joc și

salvarea lui local pentru a putea fi folosit în viitoarele jocuri. Pe ecran se va putea selecta rasa

eroului și în funcție de această selecție se va putea selecta și specializarea. Acestea vor influența

atributele caracterului iar numărul maxim de eroi este 5.

Jucătorul are posibilitatea de a șterge oricare dintre eroii deja creați de el.

Jucătorul are posibilitatea alegerii de a juca singur împotriva jocului sau de a forma o

echipă cu alți doi jucători pentru a-l înfrânge împreună. Pentru jocul în echipă este necesară o

conexiune la internet pentru a se conecta la un server, spre deosebire de cel singur unde nu este

nevoie.

Utilizatorul va putea crea un erou la începutul fiecărui joc. Jucătorul va avea o listă de eroi

deja creați și va avea posibilitatea de a alege unul dintre ei pentru a fi folosit în următorul joc.

Totodată va fi prezent și un buton pentru crearea imediată a unui erou.

Va fi posibilă întreruperea jocului și afișarea unui meniu de pauză atunci când jucătorul

apasă pe butonul de pauză într-un joc cu un singur jucător.

În timp ce jocul este întrerupt jucătorul are opțiunea de abandonare a jocului și întoarcerea

la meniul principal, apasând pe butonul de abandon.

Pe parcursul jocului eroul poate fi mutat pe hartă folosind butonul de mișcare și selectând

pătratul destinație. Pătratul trebuie să fie în limita zonei în care eroul se poate mișca, determinat

de atributul viteză al acestuia.

Jucătorul poate decide să atace unul sau mai mulți inamici. Pentru aceasta el va folosi

butonul de atac, urmat de una dintre abilitățile eroului. În funcție de abilitate el poate ataca un

singur inamic sau o multitudine de inamici aflați în raza abilității.

Când jucătorul consideră că este necesar, poate folosi o abilitate de ajutor care va

reîmprospăta sau modifica anumite atribute ale eroului. Acestea diferă în funcție de abilitățile

alese și de specializarea caracterului în joc.

În orice moment se pot inspecta atributele oricărui erou sau inamic prezent pe tabla de joc.

Eroii și inamicii au moduri de prezentare diferite pentru a semnala informațiile relevante.

Page 13: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

13

În cazul în care jucătorul și-a folosit toate acțiunile posibile ale eroului sau decide că nu

poate contribui cu nimic la această rundă, își va putea încheia tura.

Pentru fiecare acțiune care necesită o aruncare a zarului, jucătorul are opțiunea de a face

acest lucru prin butonul de aruncare a zarului.

Utilizatorul poate mișca poziția jocului astfel încât poate explora toată harta generată la fel

și o opțiune de a mări sau micșora obiectele de pe ecran.

1.5 Abordare tehnică

Aplicația folosește pentru partea de client framework-ul multiplatformă libGDX cu

limbajul de compilat în JAVA, iar pentru partea de server Node.js cu limbaj de scripting

JavaScript. Comunicarea între client și server pentru un joc cooperativ se va realiza prin

biblioteca Socket.IO.

LibGDX este un framework cu sursă deschisă pentru dezvoltarea de jocuri video scrisă în

limbajul de programare JAVA. Aceasta oferă posibilitatea de a dezvolta jocuri atât

bidimensionale cât și tridimensionale pe mai multe platforme precum Windows, Android, iOS

dar folosind același cod de bază. (1) Totodată oferă și anumite extensii pentru creearea de

concepte mult mai avansate decât cele din biblioteca standard.

Android SDK este un set de instrumente care facilitează crearea de aplicații specifice

sistemului de operare Android. Pachetul conține atât instrumente pentru debugging și testare, cât

și un emulator complet funcțional configurabil pentru orice dispozitiv Android. (2) Acest pachet

ajută framework-ul libGDX în rularea codului compilat pentru Android.

Java este un limbaj de programare orientat obiect și concurent dezvoltat inițial de Sun

Microsystems în anul 1995. Acesta a fost gândit ca cei care dezvoltă aplicații să poată scrie codul

o singură dată și să poată fi rulat pe orice platformă. (3) Acest lucru este posibil datorită unei

mașini virtuale care este capabilă să execute cod scris specific pentru mașina gazdă. Bibliotecile

standard facilitează un mod generic de a accesa caracteristicile mașinii gazdă precum grafica sau

rețeaua acesteia.

Node.js este un mediu de programare dezvoltat peste JavaScript engine V8 oferit de

Chrome cu un singur fir de execuție. Oferă psobilitatea de a crea servere flexibile bazate pe

Page 14: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

14

evenimente și transfer de date asincron. Din această cauză server-ul Node.js nu va fi niciodată

blocat și este preferat pentru aplicațiile scalabile. (4)

JavaScript este un limbaj de programare de nivel înalt orientat pe obiecte, dinamic și

interpretat. Deși inițial acest limbaj a fost dezvoltat pentru a introduce noi funcționalități

paginilor web, în ziua de azi este folosit în aproape orice domeniu IT deoarece este un limbaj

ușor de utilizat. Acesta folosește un API pentru a lucra cu date de tip text, șiruri, date

calendaristice și expresii regulate, dar nu include componente de intrare sau ieșire precum

rețelistică sau grafică. Acest limbaj a fost standardizat, având prima ediție publicată in 1997. (5)

Socket.IO este o bibliotecă JavaScript pentru aplicații în timp real. Aceasta facilitează

comunicare bidirecțională între clienți și conține două componente, biblioteca ce rulează pe

partea de client și biblioteca pentru server. Exact ca și Node.js, comunicarea este bazată pe

evenimente. (6)

Page 15: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

15

2. Contribuții

Dungeon Master este un joc tridimensional bazat pe ture care urmărește evoluția unuia sau

a mai multor personaje care întâmpină pe parcursul jocului diferiți monștri și hazarde în incinta

unei temnițe înfățișată sub forma unei grile (eng: grid). Jucătorul are posibilitatea de a-și crea

propriul erou și de a porni într-o aventură. Eroul va avea un set de abilități prestabilite dintre care

jucătorul va putea alege. Fiecare aventură, fiecare monstru și fiecare temniță va fi unică pentru

fiecare joc generat pseudo-aleatoriu. Fiecare creatură eliminată va genera eroului sau grupului de

eroi puncte de experiență care pot fi folosite pentru a evita anumite hazarde. Acțiunea jocului va

avea loc pe o hartă împărțită în plăci (eng: tile) formate din mai multe pătrate (eng: squares).

Fiecare aventură va începe cu două plăci și restul se vor „descoperi” pe parcursul jocului (ca și

cum personajul ar merge prin întuneric). Scopul jocului este de a îndeplini obiectivul setat la

început. Obiectivele pot varia de la eliminarea unui monstru specific, până la descoperirea unui

artefact. Neîndeplinirea obiectivului sau eliminarea unuia dintre personaje va semanala încheierea

jocului.

Cele mai importante contribuții în acest sens sunt următoarele:

Generarea pseudo-aleatorie a plăcilor ce vor constitui harta jocului.

Generarea pseudo-aleatorie a inamicilor ce vor fi plasați pe hartă. Se vor lua totuși în

calcul numărul de jucători prezenți precum și specializările lor.

Implementarea unui server bazat pe evenimente pentru a facilita jocul de echipă în trei

jucători.

Pentru a atinge acest obiectiv am decis să împart proiectul în două componente, server și

client, și să le dezvolt separat. Totodată structura lucrării va urma aceeași manieră, fiecare capitol

va prezenta deciziile luate în cadrul dezvoltării precum și detalii de implementare exemplificate și

explicate.

Pe partea de client am folosit framework-ul libGDX pentru a realiza mecanismul necesar

jocului. Am ales această bibiliotecă deoarece este foarte intuitivă de folosit, oferă control asupra

multor funcționalități de nivel jos și se prezintă cu multe utilități pentru a îmbunătăți experiența

jucătorului.

Page 16: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

16

Pe partea de server am ales să folosesc Node.js pentru gestionarea clienților într-un joc de

echipă. Alegerea aceasta a fost datorată sistemului asincron al serverului și al faptului că serverul

va hiberna dacă nu are de rulat nici o operație, aducând un plus de performanță.

Comunicarea între client și server va fi facilitată de către Socket.IO. Această alegere se

datorează faptului că biblioteca este bazată pe evenimente, la fel ca și serverul.

Page 17: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

17

3. Proiectare

3.1 Arhitectura soluției

Aplicația este împarțită în două proiecte pentru fiecare capăt al comunicării, client și server. În

continuare voi prezenta arhitectura aplicației, ce se împarte în două componente descrise pe larg.

Figura 5: Arhitectura aplicației

Clientul este responsabil în mare parte de afișarea pe ecran a tuturor obiectelor vizuale ce

compun aplicația, dar totodată și de foarte multă logică ce ajută la desfășurarea jocului și

interacțiunea obiectelor între ele. Pentru randarea obiectelor tridimensionale pe ecran biblioteca

foloseste un motor OpenGL ES 2.0 și un wrapper pentru 3.0. (7) Proiectul conține trei module

principale:

1. Un modul standard Java peste care a fost aplicat framework-ul libGDX împreună

cu toate dependețele acestuia: ca orice modul Java acesta va avea nevoie de un mediu de

dezvoltare necesart rulării și compilării codului sursă. Pentru proiectul curent am folosit jre

1.8.0.

2. La crearea unui modul libGDX, fiind un framework în care se pot crea aplicații

multiplatformă, se pot specifica ce module pot fi instalate. În cazul de față am ales Android

și pentru acesta am ales ca și mediu de dezvoltare Android API 22 Platform. În acest modul

numit sugestiv „android” se pot specifica anumite dependențe și configurări specifice

mediului în care va fi rulat jocul. În cazul de față am adăugat permisiunea <uses-

permission android:name="android.permission.INTERNET" /> care îmi va facilita accesul

Page 18: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

18

la internet. Tot aici am setat în activitatea aplicației ca modul de afișare să fie mereu pe

orizontală. Am luat această decizie pentru a avea o interfață mult mai utilă pentru utilizator.

Acest lucru l-am realizat prin adăugarea liniei

android:screenOrientation="sensorLandscape"

în activitatea principală a fișierului AndroidManifest.xml. De specificat faptul că

datorită unor constrângeri ale modului de interpretare Android, toate resursele folosite

în proiect trebuie încărcate în acest modul în directorul „assets”.

3. Ultimul modul este și cel mai important. Deoarece libGDX este un framework

multiplatformă, nu te va forța să scrii cod specific platformei destinație. Acesta va folosi

diferite operații backend pentru a accesa procesele specifice mașinii și pentru a compila și

porni codul sursă. În cazul nostru aceastea vor fi realizate cu ajutorul Android SDK. În

acest modul numit „core” se va scrie tot codul sursă al aplicației. Astfel libGDX urmează

sloganul „Write once, run anywhere” (scrii o singură dată, utilizezi peste tot). Codul sursă

este scris în JAVA și urmează principiile POO. De menționat însă este faptul că același cod

sursă ar fi putut fi scris și în modulul precedent, dar acest lucru ar fi făcut ca aplicația să

poată fi accesată doar de pe un dizpozitiv Android. Deoarece am vrut ca pe viitor să pot

extinde acest joc, codul sursă a fost scris în acest modul.

Page 19: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

19

Figura 6: Modulele ce compun clientul

Trebuie menționat faptul că un framework dedicat jocurilor va gestiona diferit modulele

față de un API sau widget dedicat redării grafice. Astfel el va pune la dispoziție o metodă care va

fi mereu apelată la fiecare cadru randat de către aplicație. Deci pentru jocul nostru această metodă

va fi apelată de 60 de ori pe secundă. Aceasta va servi la modificarea poziției obiectelor pe ecran

și pentru ca jucătorul să fie mereu avertizat și ținut la curent de orice schimbare.

Pentru ca utilizatorul să se bucure de o experiență de joc mai dinamică am ales ca marea

majoritate a graficii jocului să fie compusă din obiecte tridimensionale, atât obiecte create

dinamic cât și unele încărcate la începerea jocului. Din fericire libGDX oferă destule

funcționalități de gestionare ale acestor obiecte, cât și redarea lor pe ecran. Având acel strat de

grafică putem crea obiecte detaliate, aplica diferite „modifiers” (procese ce manipulează obiectul)

și la final aplicarea unei texturi. Trebuie avut grijă însă că marea majoritate a performaței jocului

scade considerabil odată cu creșterea calității texturilor și modelelor folosite. De aceea marea

majoritate a modelelor și texturilor vor fi create la încărcarea jocului și folosite pe tot parcursul

Page 20: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

20

lui atunci când este nevoie. Alte obiecte sunt create dinamic doar atunci când este nevoie după

care vor fi scoase din memorie. Toate aceste resurse au fost încărcate în folderul „assets”.

Un alt rol pe care îl are clientul este de a percepe orice atingere sau mișcare pe ecran și

trimiterea acestor evenimente către stratul de logică al jocului pentru a fi interpretate. În

continuare clientul va valida aceste evenimente și va răspunde corespunzător.

Un alt aspect de luat în considerare atunci când se dezvoltă un joc de echipă online (sau

orice aplicație client-server) este volumul de logică și validări care va trebui să fie împărțit între

client și server. Astfel o aplicație care va face validările pe server va fi mult mai robustă și

pregătită impotriva jucătorilor care vor încerca să trișeze. Pe de altă parte aplicațiile care au o

mare parte din validări pe partea de client, vor fi mai expuse trișorilor, dar se vor comporta mult

mai bine în cazul în care internetul tinde să aibe scăpări sau latență. Strict legat de dezvoltarea

unui astfel de joc putem totodată menționa că nu este eficient să se trimită la server orice input al

jucătorului pentru a fi validat, deoarece ar fi o irosire de bandă și timp. În continuarea aceste idei

este mai eficient ca un client să trimită doar anumite tag-uri la care serverul să reacționeze și să

trimită în continuare celorlalți clienți informația pentru a fi interpretată de fiecare în parte. Spre

exemplu dacă un jucător a fost eliminat în timpul unei runde, clientul va trimite un tag

«Player1Died» la server iar serverul va valida tag-ul și îl va trimite la ceilalți clienți unde fiecare

în parte va ști ce animații sau sunete să gestioneze. Având în vedere faptul că aplicația dezvoltată

de mine are și un mod single care nu necesită acces la internet ar fi trebuit să dezvolt aceleași

validări și pe client și pe server. Dat fiind timpul restrâns pentru dezvoltarea acestei aplicații, am

decis ca majoritatea validărilor să fie pe client.

Comunicarea între client și server va fi gestionată de un serviciu numit Socket.IO.

Aceasta conține două biblioteci specifice fiecărui capăt de comunicare, o bibliotecă pentru partea

de client și una pentru partea de server. Acest lucru este datorat faptului că deși această bibliotecă

este construită peste alte protocoale de transport în timp real, în timpul negocierilor de conexiune

va căuta mereu protocolul creat special pentru Socket.IO astfel ignorând protocoalele WebSocket

standardizate. În concluzie o conexiune folosind Socket.IO va funcționa doar când atât clientul,

cât și serverul vor folosi respectiva bibliotecă. (6)

Serverul are rolul de a asculta orice cerere de conectare, de creare a conexiunilor cu oricare

client și de a intercepta orice cerere din partea clienților, de a o valida și de a trimite mai departe

răspunsul către ceilalți clienți. Arhitectura serverului se bazează foarte mult pe sistemul de

Page 21: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

21

gestionare a conexiunilor oferit de Socket.IO dar totul este gestionat de mediul Node.js. Astfel

serverul conține un singur modul și folosește mediul de interpretare oferit de motorul JavaScript

Google V8.

Robustețea acestui server vine din faptul că, spre deosebire de majoritatea serverelor care

trimit la intervale periodice informații către clienți, acesta este bazat pe evenimente, ceea ce face

ca informațiile să fie transmise doar când este nevoie. Acest lucru este foarte util pentru creșterea

perfomanței jocului, un aspect important pentru o aplicație destinată telefoanelor mobile. Având

în vedere faptul că jocul este bazat pe ture și doi jucători nu vor face cereri la server în același

moment, impactul asupra scăderii performanței va fi minim ceea ce face ca arhitecura bazată pe

evenimente să fie cea optimă.

Totodată serverul are rolul de a emite începerea jocului atunci când s-a acumulat numărul

necesar de clienți pentru o sesiune de joc și închiderea acesteia atunci când jocul a ajuns la

finalitate. Dat fiind folosirea unui server asincron Node.js comunicarea va fi facilitată prin

„callbacks”. Avantajul folosirii unui server cu operații non-blocante este faptul că un client nu se

va bloca așteptând anumite operații care ar putea dura o lungă perioadă de timp, astfel clientul se

bucură de toate funcționalitățile până când ajunge răspunsul. Acest aspect este important pentru

aplicații din punct de vedere al experienței utilizatorului dat fiind și faptul că jocul va rula pe o

mașină cu resurse limitate.

Page 22: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

22

3.2 Modelarea datelor

În continuare voi prezenta în detaliu entitățile ce compun modulele descrise în subcapitolul

anterior, cât și relațiile dintre acestea.

3.2.1 Modelarea datelor pe aplicația client

Figura 7: Diagrama de clase a aplicației client

După cum se poate observa și în figura 8, am creat un obiect de bază GameManager care

va avea grijă ca tot ce se întamplă în joc și toate entitățile care vor fi create să fie gestionate

corect. Acest obiect este jocul propriu-zis care va avea grijă ca de fiecare dată jocul să se

comporte normal, să valideze toate input-urile utilizatorului, să configureze conexiunea la

internet și să redea pe ecran toate modificările.

În principal toată logica jocului depinde de două mari clase care sunt extinse pentru a oferi

funcționalități mai specifice. Acestea sunt GameObject și Abilities. Pentru buna organizare a

proiectului am creat și anumite clase ajutătoare care vor avea rolul ori de a gestiona anumite

funcționalități, ori de a oferi anumite informații relevante pentru desfășurarea jocului.

GameObject-ul descrie orice obiect grafic tridimensional aflat în scenă. Practic pentru

orice model tridimensional afișat, acesta va avea în spate un astfel de GameObject. De subliniat

aici faptul că aceste obiecte se referă strict la cele tridimensionale și nu la cele bidimensionale

cum ar fi butoanele interfeței grafice.

Page 23: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

23

Pentru acest joc am extins această clasă abstractă în 3 noi clase pe care le-am considerat ca

fiind relevante: Square, Hero și Monster.

Pentru a explica motivul creării entității Square trebuie explicat mai întâi modul de gândire

al jocului în ceea ce privește harta. Jocul este unul bazat pe ture, astfel fiecare jucător va avea o

tură a lui în care va putea face anumite acțiuni. Toate aceste acțiuni trebuie să se întâmple într-un

spațiu de joc, o tablă. Asemenea unui joc de șah, tabla are mai multe diviziuni pentru a putea

organiza fiecare piesă de joc și defini anumite mutări permise. În cazul nostru cea mai mică

diviziune a tablei o semnifică Square care în plan grafic nu este nimic altceva decât un pătrat al

hărții. Totodată se poate observa că această entitate a fost extinsă iar în 3 clase pentru a oferi

funcționalități și mai specifice: NormalSquare, SpawnSquare, Wall. Aceste noțiuni vor fi

explicate mai în detaliu întru-un alt paragraf.

Hero este o entitate mobilă (prin mobilă mă refer la faptul că pe parcursul jocului această

entitate are posibilitatea de a fi mutată pe hartă) care este în mare parte gestionată de utilizator.

Aceasta reprezintă eroul jucătorului pe tablă. Fiecare jucător își poate personaliza eroul și astfel

modificările vor fi vizibile în joc.

Această entitate stă la baza jocului. Fiecare jucător va avea o singură astfel de entitate pe tot

parcursul jocului și va putea să o mute pe tabla de joc sau va putea folosi abilități ale acesteia.

Aceste acțiuni vor fi folositoare pentru îndeplinirea obiectivului fiecărui joc.

Monster este tot o entitate mobilă dar gestionată in totalitate de GameManager. Jucătorul

nu are acces la nici o funcționalitate a acesteia, reprezintând principalul obstacol în împlinirea

obiectivului de către jucători. Reprezintă entitatea anti-erou și se va deplasa pe harta de joc sau va

folosi abilități exact ca un erou. Deși nu este controlată de jucător, informațiile privind această

entitate pot fi inspectate folosind interfața grafică.

De menționat faptul că pentru a crea un joc unic de fiecare dată monștrii vor fi creați într-un

mod pseudo-aleatoriu. În schimb pentru a menține o doză de echilibru între eroi și inamici, la

generarea monstrului se va ține mereu cont de numărul de jucători prezenți și de specializarea lor.

În schimb entitatea care se va ocupa îndeosebi de crearea de Squares va fi Tile. Harta

acestui joc se va construi în timp ce eroii o vor explora. Pentru a evita construirea hărții prin

pătrate am adăugat o noua diviziune a hărții, de data aceasta una care cuprinde mai multe pătrate.

O grupare de astfel de entități va forma o placă (Tile). Un Tile este o entitate de 4x4 Squares.

Page 24: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

24

Totodată această entitate este responsabilă de poziția pseudo-aleatorie a pătratelor ce o formează

și anumite funcționalități pentru a putea identifica cadrul său pe harta de joc.

După cum am menționat mai sus un Tile poate avea 3 tipuri de Squares. Cel mai ușor de

recunoscut este Wall (perete) care nu reprezintă nimic altceva decât obstacole în calea eroilor. Al

doilea tip este SpawnSquare (~pătrat de invocare) care reprezintă un pătrat special unde un

inamic își va face apariția pe hartă pentru prima dată. Cel de-al treilea este NormalSuqare care,

după cum îi spune și numele, nu are atribute speciale, este o divizie în plus pe harta de joc.

Abilities sunt entități fără o formă precisă, reprezentând abstractizarea modului de atac sau

reîmprospătare a eroilor. Sunt singura sursă de a elimina inamicii de pe tablă. Pentru a specializa

fiecare tip de abilitate, această clasă a fost extinsă în alte 3 clase: ActiveAbilities,

UtilityAbilities, PasiveAbilities.

ActiveAbilities sunt abilitățile care vor răni inamicii și pot avea diferite raze de acțiune în

funcție de specializarea eroului. Ele trebuie acționate de jucător. PasiveAbilities sunt abilitățile

care nu necesită acțiuni adiționale pentru a fi activate și își vor face efectul pe tot parcursul

jocului. UtilityAbilities sunt tipurile de abilități care vor afecta eroul care le activează și de

obicei vor reîmprospăta anumite atribute ale eroului.

MonsterAbilities este o clasă separată care reprezintă abilitățile folosite de către inamici.

Aceste entități sunt diferite prin modul logic de gândire față de cele ale eroilor. Totodată acestea

au incorporate și acțiunea de mișcare deoarece un inamic fiind controlat de către GameManager,

nu va fi mutat de către un input al utilizatorului.

PredefinedAbilities și PredefinedMonsterAbilities sunt două clase ajutătoare, câte una

pentru fiecare entitate mobilă, care vor popula posibilele abilități selectate pentru erou sau alese

pentru monstru. Acestea vor fi instanțiate doar o singură dată la încărcarea jocului.

AbilitiesManager este clasa care va gestiona orice abilitate folosită pe parcursul jocului,

fie că aceasta a fost acționată de un erou sau de un inamic. GameManager-ul îi va transmite că o

anumită enitate vrea să folosească o abilitate iar în funcție de sursa acțiunii, manager-ul va

acționa ca atare.

Pentru o abilitate folosită de un erou, AbilitiesManager va pregăti pentru execuție acea

abilitate prin clonarea ei. După caz acesta va activa sau dezactiva anumite părți ale interfeței

Page 25: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

25

grafice. În primă fază va aștepta un input din partea utilizatorului, mai specific, o țintă pentru

abilitate. După ce un astfel de input a fost comunicat de GameManager, AbilitiesManager-ul va

valida selecția. Va verifica dacă obiectul selectat este o țintă validă pentru abilitate și dacă se află

în raza de acțiune a acesteia. În caz afirmativ îi va face cunoscut utilizatorului faptul că trebuie

apăsat butonul de aruncare zar. După aruncare se verifică dacă abilitatea va lovi ținta, se vor

calcula efectele și abilitatea va fi consumată.

Similar se întâmplă și pentru cazul în care un inamic invocă o abilitate. Diferența este faptul

că nu va aștepta input-ul utilizatorului și va face calculele automat. Totodată având în vedere că

pot fi mai mulți monștri care se vor activa la tura eroului, AbilitiesManager se va asigura că

abilitățile acestora se vor executa în ordine și într-un mod în care utilizatorul poate înțelege ce se

întâmplă.

Pathfinder este una dintre cele mai importante entități. Ea este responsabilă de calcularea

traiectoriilor, distanțelor și căilor atât pentru entitățile mobile cât și pentru abilități. Dacă

utilizatorul va dori să își deplaseze eroul, se va invoca Pathfinder-ul care va calcula cea mai

scurtă cale din punctul în care se află eroul, până în punctul unde se vrea a fi mișcat și va returna

această cale. Totodată această enitate mai este folosită pentru a calcula raza în care un erou se

poate mișca sau folosi o abilitate, sau raza de acțiune a unei abilități (în cazul în care eroul poate

ataca cu aceeași abilitate mai mulți monștri). Această cale sau zonă va fi mai apoi trimisă la

GameManager care se va ocupa de deplasarea obiectelor pe acea cale.

Alternativa folosirii acestei clase ar fi fost doar un validator care verifică poziția finală și

teleportarea obiectului în acea poziție. Dezavantajul este faptul că nu se fac verificări în privința

blocării drumului până în aceea poziție. Astfel eroul sau monstrul pur și simplu ar evita

obstacolele sau pereții hărții, ceea ce ar duce la un ritm de joc neinteresant. Fiind un joc

tridimensional și cu scopuri precise, mișcarea pe hartă aduce un plus de dinamism jocului.

GameCamera este entitatea responsabilă cu ce anume vedem pe ecran. Deși harta și

obiectele de pe ea sunt construite în memorie, pe ecran putem vedea doar o parte, astfel această

entitate, în funcție de mărimea ecranului, va afișa anumite cadre. Proprietățile camerei pot fi

modificate de către utilizator. Jucătorul poate să mute cadrul în oricare direcție a ecranului sau

poate mări sau micșora obiectele de pe el.

Page 26: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

26

Construirea interfeței grafice este posibilă cu ajutorul clasei integrate în libGDX scene2d.

Deși această clasă oferă mult mai multe, deoarece jocul este tridimensional, a fost folosită doar

pentru construirea interfeței grafice. Aceasta conține doar elemente bidimensionale precum

butoane, imagini portret sau etichete.

Se poate observa faptul că toate elementele grafice de pe ecran sunt de diferite tipuri (atât

bidimensionale cât și tridimensionale). Din această cauză fiecare tip de obiect va avea diferite

moduri de interpretare a acțiunilor pe ecran, va avea un alt InputListener. Astfel pentru ca jocul

să interpreteze corespunzător fiecare acțiune a sa, am definit 3 astfel de InputListener, unul

pentru camera jocului, unul pentru obiectele tridimensionale și unul pentru interfață. Pentru ca

jocul să trateze toate cele 3 inputuri am folosit un multiplexor oferit de libGDX. Ordinea în

multiplexor a acestora este importantă deoarece este aceeași ordine în care evenimentele vor fi

verificate. Astfel pe primul plan avem interfața grafică, urmată de stratul obiectelor

tridimensionale și la final camera. Dacă una dintre acțiuni a fost consumată de interfață,

evenimentul nu va fi transmis în continuare și la celalalte InputListeners.

Pentru ca jocul să acționeze în timp real, libGDX va redesena fiecare cadru al ecranului de

60 de ori la fiecare secundă (acesta fiind modulul ideal, anumite resurse limitate ale dispozitivului

sau redesenarea unor obiecte care necesită un timp îndelungat pot micșora numărul de cadre

desenate). De aceea framework-ul ne pune la dispoziție metoda render(), metodă ce va fi apelată

de fiecare dată când jocul va redesena un cadru. În această metodă trebuie specificat ce obiecte

vor fi afișate pe ecran și anumite operații care trebuie făcute între cadre. În cazul de față

redesenăm la fiecare cadru toate obiectele tridimensionale, redesenăm scena pe care se află

interfața grafică, actualizăm camera jocului (care este indirect responsabilă de cadrele redate) și

tot aici verificăm dacă poziția obiectelor mobile trebuie actualizată.

Totodată în GameManager sunt configurate toate evenimentele care vor fi ulterior folosite

pentru comunicarea pe internet între joc si server.

Page 27: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

27

3.2.2 Modelarea datelor pe server

Serverul are rolul de a negocia conexiunea cu clineții care vor să se conecteze și de a

facilita o bună desfășurare a jocului. Acesta este configurat pe platforma Node.js.

Serverul creat este un server HTTP cu ajutorul extensiilor oferite de Node.js și anume

express.js. După cum am specificat și în capitolul anterior acesta va folosi biblioteca de server a

platformei Socket.IO. Toate aceste configurări sunt ușor de realizat, motiv pentru care am ales

lucrul cu Node.js.

Serverul a fost setat să asculte la orice IP care folosește portul 8081. Folosind Socket.IO am

setat callback-urile pentru crearea unei conexiuni cu un client la fel și pentru deconectarea lui.

Totodată pentru fiecare conexiune realizată am setat evenimentele pentru care serverul o să

asculte pe acest socket.

var app = require('express')();

var server = require('http').Server(app);

var io = require('socket.io')(server);

var players = [];

var activePlayer;

server.listen(8081, function() {

console.log("Server is now running...");

});

Secțiunea de cod 1: Configurearea serverului HTTP

Serverul modelează în principal 2 entități: players și activePlayer.

Players reprezintă un vector de jucători care menține id-ul socketului și poziția fiecăruia.

La fiecare conectare a unui nou client, se va crea un nou obiect player și va fi adăugat în colecție.

Atunci când numărul de jucători a ajuns la 3 serverul va emite o cerere de începere a jocului la

fiecare client.

ActivePlayer este o entitate pe care o menține serverul pentru a ști a cărui jucător îi este

tura. Astfel de fiecare dată când un client va emite un eveniment prin care își exprimă încheierea

turii, acesta va ști care este următorul jucător la tură. Totodată serverul va emite startul turei la

clientul respectiv.

Page 28: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

28

3.3 Interfața cu utilizatorul

Interfața cu utilizatorul este probabil cea mai importantă componentă a unui joc sau a unei

aplicații Android în general. Contează mult ca această interfață să fie intuitivă, să fie înțeleasă

foarte ușor de către utilizator și să îi vină în ajutor pentru a utiliza eficient aplicația.

Ca orice joc video am început prima interacțiune cu utilizatorul prin înfățișarea unui meniu

principal. Acest meniu conține patru butoane: Singleplayer, Multiplayer, Create Hero, Exit. În

spatele acestor butoane este plasată o imagine sugestivă.

Schema 1: Meniul principal

Acest meniu este cât se poate de clasic dar intuitiv. Butonul Singleplayer semnifică

începerea unui joc fără aliați, Multiplayer semnifică conectarea la internet și începerea unui joc

cu încă doi jucători aliați. Create Hero îl va duce într-un alt cadru unde va avea posibilitatea de

creare a unui nou erou iar Exit va scoate jucătorul din aplicația curentă.

Fiind un joc setat într-un cadru fantastic, acest lucru trebuie reflectat și în interfața

utilizatorului, de aceea am creat texturi pentru butoane care sunt specifice acestei teme. Imaginile

au fost realizate de mine cu ajutorul programului Adobe Photoshop.

Page 29: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

29

Unul din cele mai complexe cadre este cel de construire a erolui reprezentat în schema[2].

Schema 2: Meniul de creare a unui erou

Centrat în partea de sus a paginii avem titlul acestei secțiuni. Pe primul rând din chenar

avem trei butoane, fiecare cu un portret sugestiv, care va semnifica speța eroului ce va fi creat. Pe

următorul rând avem specializările posibile, această specializare va influența abilitățile afișate în

următoarele rânduri. Meniul este făcut în așa fel încât jucătorul poate selecta o singură speță și o

singură specializare. În dreapta putem vedea proprietățile erolui. Acestea se vor modifica în

funcție de alegerile făcute în stânga. Poziționarea în dreapta a atributelor erolui este foarte

avantajoasă pentru utilizator deoarece va vedea aproape imediat ce avantaje și dezavantaje aduce

selecția lui. Totodată abilitățile au o zonă puțin separată pentru a fi inspectate pe larg de către

utilizator. În mijlocul părții de jos se poate observa un chenar pentru text. Acesta semnifică locul

unde se va scrie numele eroului. Astfel utilizatorul își poate personaliza fiecare erou cu un nume

original. În cazul în care utilizatorul este mulțumit cu eroul creat sau s-a răzgândit în privința

creării acestuia, are ca opțiune terminarea sau ieșirea din acest meniu, fiecare opțiune fiind

reprezentată de butonul Back și Done.

Înainte de începerea unui joc, fie el online sau nu, jocul îți va cere să selectezi un erou

pentru a-l folosi în jocul ce urmează.

Page 30: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

30

Schema 3: Meniul de selecție a unui erou

Într-un chenar jocul va afișa cele 5 posibile alegeri pe care jucătorul le are. Fiecare erou are

identificată o casuță cu portretul speței și numele său sub ea. În momentul în care utilizatorul nu

are cinci eroi creați vor apărea doar cei care există.

În capătul de jos al ecranului sunt 3 butoane. Primul buton, ca și în ecranul prezentat

anterior, este pentru întoarcerea în meniul precedent în cazul în care utilizatorul se răzgândește să

înceapă jocul. Al doilea (cel din mijloc) este pentru a șterge eroul selectat. Ultimul buton

continuă cu începerea jocului în cazul în care utlizatorul s-a decis asupra unui erou.

Cea mai importantă interfață este în schimb cea în care utilizatorul a pornit un joc și toate

elementele grafice sunt afișate pe ecran.

Page 31: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

31

Schema 4: Interfața în timpul unui joc

Utilizatorul trebuie să se poate bucura de toate funcționalitățile oferite de joc fară prea mult

efort. Astfel am divizat ecranul în 3 zone.

Prima zonă este cea din partea stângă a ecranului. Aici putem vedea o serie de butoane și un

chenar text. Acele butoane vor fi cele mai folosite în timpul jocului astfel le-am aranjat unele sub

altele într-o manieră logică. Primul buton este Move (a mișca) și va fi acțiunea principală a unui

erou. În acest joc, fiind un joc tactic, este foarte importantă poziționarea eroului pe hartă atât

pentru a evita inamici sau obstacole, cât și pentru a folosi abilități specifice. Al doilea buton este

Use ability (folosește abilitate). După poziționare este important să îți menții numărul de inamici

sub control astfel folosirea abilităților este recomandată. De aceea am așezat acest buton exact

sub butonul de mișcare. Al treilea buton este cel de încheiere a turei (End Turn). După ce eroul

și-a folosit toate acțiunile posibile de mișcare sau folosire a abilității, acesta poate semnala

încheierea turei lui. Desigur acest buton poate fi folosit oricând chiar și fără ca eroul să fi făcut o

acțiune. Ultimul buton este cel de Roll die (aruncare de zar). Acest zar este folosit la toate

abilitățile jocului pentru a verifica dacă abilitatea va fi executată cu succes. Deși este un buton

mult mai folosit decât cel de încheiere a turei, din punctul de vedere al unui utilizator, este mult

mai bine poziționat înafara acestor butoane. Ultima secțiune din stânga este reprezentată de un

chenar de tip text. Acest chenar are rolul de a afișa toate evenimentele ce se petrec în timpul

Page 32: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

32

jocului. Vor fi afișate ultimele 3 acțiuni fie ale jucătorului, fie ale inamicilor sau a hazardelor.

Totodată acesta va avertiza încheierea unei ture și începerea alteia, precum și toate informațiile

legate de abilități sau zaruri aruncate. Am plasat acest chenar într-o zonă în care să nu încurce

spațiul de joc, dar în același timp să fie ușor de verificat sau urmărit.

A doua zonă este formată din cinci butoane mari și unul mai mic rotund în dreapta. Această

reprezentare urmează schema clasică a unui joc bazat pe rol, unde abilitățile sunt afișate în josul

ecranului sub formă de iconițe. Deoarece nu pe toate dispozitivele cu interacțiune touch avem

posibilitatea de a mișca un cursor fară a atinge ecranul (hover) am preferat ca pe butoane să fie

scris numele abilității ce vor fi folosite. Avem 5 butoane care desemnează cele 5 abilități alese în

timpul creării eroului. Butonul mic din dreapta semnifică butonul de pauză al jocului. În timp ce

pentru un joc fară internet acesta va pune pauză jocului, într-un joc de echipă acesta doar va afișa

un meniu de pauză dar fără a întrerupe jocul.

A treia zonă reprezintă informații referitoare la atributele eroului folosit de respectivul

utilizator și sunt afișate în partea de sus a ecranului. Iarăși aceasta urmărește schema unui joc de

rol. Astfel avem patru etichete în bara principală și încă două în colțul din dreapta exact sub bară.

În cea mai din stânga margine avem un portret reprezentând eroul. Am luat această decizie pentru

ca jucătorul, inafară de modelul afișat pe hartă, să mai folosească un punct de reper vizual.

Consider că acest detaliu aduce o foarte mare contribuție pozitivă din punctul de vedere al

experienței utilizatorului în aplicație. În continuare am ordonat cele patru etichete după

importanța lor în joc: punctele de viața ale eroului, armura sa, punctele de viteză pe hartă și

numărul de puncte de viață ale eroului atunci când va fi infrânt. Cele două etichete separate nu au

fost incluse în această bară deoarece, deși reprezintă entități care contribuie la erou, ele sunt

mereu resetate la fiecare joc și valorile lor sunt mereu modificate. Este o separare benefică pentru

utilizator.

După cum am precizat și în capitolele anterioare, o parte din interacțiunea cu jocul se va

realiza și cu obiectele tridimensionale din scenă dar interfața grafică va veni mereu în ajutorul

utilizatorului.

Page 33: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

33

4. Implementare

Pentru acest capitol am ales să prezint o funcționalitate pe care am considerat-o dificilă și

complexă din punct de vedere a implementării. În acest sens am ales mișcarea obiectelor (și mai

specific a eroilor) pe hartă.

Mișcarea obiectelor pe hartă de către utilizator presupune 4 procese în cadrul jocului:

1. Selectarea obiectului care va fi mutat și selectarea obiectului destinație.

2. Calcularea ariei unde se poate mișca obiectul.

3. Calcularea căii între sursă și destinație.

4. Translatarea obiectului urmărind calea calculată.

Voi începe prin expunerea selectării unui obiect. În libGDX, spre deosebire de alte

framework-uri pentru dezvoltat jocuri, nu oferă eventListeners (ascultare de evenimente) pentru

obiecte tridimensionale, astfel că acest tip de eveniment trebuie simulat.

Pentru început am făcut ca GameManager-ul să asculte evenimentele ce vor avea loc pe tot

ecranul prin folosirea unui InputAdapter.

Prin aceasta a trebuit să implementez mai multe metode ce se vor apela la atingerea

ecranului. Cele mai importante sunt:

@Override

public boolean touchDown(int screenX, int screenY, int pointer, int button)

@Override

public boolean touchUp(int screenX, int screenY, int pointer, int button)

Prima metodă va fi apelată atunci când pe ecran este apăsat un punct, iar cea de-a doua va fi

apelată atunci când utilizatorul ridică degetul de pe ecran. În metoda touchDown am adaugat:

public boolean touchDown(int screenX, int screenY, int pointer, int button) {

selectingGameObjectIndex = getObject(screenX, screenY);

return selectingGameObjectIndex >= 0;

}

Page 34: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

34

Pentru a putea implementa o selecție naturală a obiectelor am definit două variabile de tip

întreg: selectingGameObjectIndex și selectedGameObjectIndex. Prima variabilă va marca

indexul obiectului selectat atunci când abia am apăsat pe ecran iar cea de-a doua va fi indexul

obiectului atunci când am ridicat degetul. Totodată vedem apelul unei metode noi getObject.

Corpul metodei arată astfel:

private Vector3 position = new Vector3();

private int getObject (float screenX, float screenY) {

cameraRay = mainCamera.getPickRay(screenX, screenY);

int result = -1;

float distance = -1;

for (int i = 0; i < instances.size; ++i) {

final GameObject instance = instances.get(i);

instance.transform.getTranslation(position);

position.add(instance.center);

float dist2 = cameraRay.origin.dst2(position);

if (distance >= 0f && dist2 > distance)

continue;

if (Intersector.intersectRaySphere(cameraRay, position, instance.radius, null)) {

result = i;

distance = dist2;

}

}

return result;

}

Metoda primește ca parametri poziția pe axa X și poziția pe axa Y a punctului care a fost

atins pe ecran. Mai întâi vom lua raza camerei din punctul în care a fost atins ecranul. Această

rază poate fi văzută ca o linie dreaptă care începe din camera jocului și se îndreaptă pe aceleași

coordonate X și Y spre spațiul Z [Figura 9].

Vom defini două variabile locale: result care va conține indexul celui mai apropiat obiect

găsit și distance care va fi distanța dintre obiect și originea acestuia. Toate obiectele

tridimensionale sunt ținute într-un vector global numit instances. Acest nume este datorat

faptului că, deși foarte multe obiecte folosesc același model, trebuie creată o instanță pentru

fiecare copie a acelui model în scenă. Astfel fiecare obiect este o instanță a acelui model.

Totodată am definit o variabilă globală position care va lua mereu coordonatele în spațiu ale

punctelor. Vom itera prin toate obiectele jocului și vom pune în position poziția fiecăruia.

Page 35: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

35

Figura 8: Exemplul unei raze3

Pentru a lua centrul obiectului vom adăuga la vectorul de poziție a acestuia vectorul

centrului. În continuare calculăm distanța dintre obiect și originea razei din cameră și verificăm

dacă această distanță este mai mare decât cea precedentă. În caz afirmativ vom ignora acest

obiect și vom trece la următorul deoarece ne interesează cel mai apropiat obiect de cameră. În

continuare verificăm dacă obiectul se intersectează cu raza noastră. Acest lucru este posibil cu

ajutorul unei funcții linGDX, intersectRaySphere din clasa Intersector, care va calcula dacă

raza va intersecta marginile obiectului. În caz afirmativ vom lua indexul obiectului și vom

actualiza dinstanța minimă. În final dupa iterarea prin toate obiectele vom returna indexul celui

mai apropiat obiect.

Pentru a calcula limitele unui model avem nevoie de anumite operații. Pentru ușurință

aceste calcule au fost făcute în constructorul clasei GameObject.

public final Vector3 center = new Vector3();

public final Vector3 dimensions = new Vector3();

private final static BoundingBox bounds = new BoundingBox();

public GameObject (Model model, float x, float y, float z, String id) {

super(model, x, y, z);

this.id = id;

calculateBoundingBox(bounds);

bounds.getCenter(center);

bounds.getDimensions(dimensions);

radius = dimensions.len() / 2f;

}

3Sursa pozei https://www.codeproject.com/Articles/35139/Interactive-Techniques-in-Three-dimensional-Scenes

Page 36: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

36

Din fericire libGDX conține o clasă ajutătoare BoundingBox care ne va ajuta la aceste

calcule. După creareea obiectului vom apela metoda calculateBoundingBox (această metodă

este definită în clasa ModelInstance pe care GameObject o extinde) având ca parametru de ieșire

variabila bounds. Acum am aflat toate informațiile despre marginile obiectului. Deoarece centrul

limitelor nu coincide cu originea modelului, vom pune această valoare în variabila center. Totuși

am optat ca aceste limite să nu fie cât obiectul în sine așa că formăm o rază egală cu jumătate din

limitele obiectului.

Revenind la metoda touchDown vedem că, dacă la apăsare, a fost selectat un astfel de

obiect, metoda va returna true și va atribui indexul lui variabilei selectingGameObjectIndex, în

caz contrar, va returna false.

Utilizatorul poate mișca degetul pe ecran fără să îl ridice o bună perioadă de timp, de

aceea m-am asigurat că odată ce el va ridica degetul de pe ecran, obiectul selectat la atingerea

ecranului coincide cu cel care este selectat atunci când a ridicat degetul. Astfel în metoda

touchUp avem:

public boolean touchUp(int screenX, int screenY, int pointer, int button) {

if (selectingGameObjectIndex >= 0) {

if (selectingGameObjectIndex == getObject(screenX, screenY)) {

resolveTouchObject();

}

selectingGameObjectIndex = -1;

return true;

}

return false;

}

Dacă aceste două obiecte coincid vom rezolva posibilele rezultate în metoda

resolveTouchObject. Dacă selectăm pentru prima dată un obiect, se va apela metoda setSelected

având ca parametru selectingGameObjectIndex.

private void setSelected (int value) {

if (selectedGameObjectIndex == value) {

selectedGameObjectIndex = -1;

return;

}

selectedGameObjectIndex = value;

}

Page 37: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

37

Prima dată verificăm dacă există un obiect selectat și acesta coincide cu noua selecție. În

cazul selectării primului obiect acest test va fi evitat. Dacă ar fi fost pozitiv atunci obiectul ar fi

fost deselectat . După setăm această selecție ca obiectul selectat.

Dacă după prima selecție (în cazul în care am selectat mai întâi un erou) dacă urmărim din

nou firul aplicației vom ajunge iar în resolveTouchObject(). De data aceasta avem o altă

verificare.

if (selectedGameObjectIndex != -1 &&

instances.get(selectedGameObjectIndex) == myHero &&

(instances.get(selectingGameObjectIndex).getGameObjectType().equals("NormalSquare") ||

instances.get(selectingGameObjectIndex).getGameObjectType().equals("SpawnSquare")) &&

lastAction == Action.MOVE) {

resolveMoveTouch();

}

În cazul acesta verificăm dacă eroul selectat este eroul utilizatorului, dacă butonul de

mișcare este apăsat și dacă obiectul următor selectat este unul valid pentru a se deplasa (dacă este

un pătrat normal sau unul de invocare, validarea însă dacă aceste pătrate sunt ocupate se va face

mai târziu). În caz afirmativ se va apela metoda resolveMoveTouch.

În continuare voi prezenta calcularea căii de la erou la punctul selectat ca destinație. Voi

omite prezentarea calculării ariei spațiului unde eroul se poate deplasa deoarece aceasta este

similară. Acestea vor folosi o clasă special implementată numită Pathfinder (~căutător de căi).

Pentru aceste două funcționalități a fost nevoie de implementarea a doi algoritmi (unul fiind

inclus în logica celui de-al doilea): Algoritmul lui Dijkstra și A* (citit A star). Am ales acești

algoritmi nu numai pentru faptul că sunt doi algoritmi cunoscuți, ci și pentru faptul că sunt doi

algoritmi optimi și robuști care garantează performanță mare, memorie redusă de folosire și un

rezultat corect. Astfel în continuare voi prezenta câteva noțiuni despre acești algoritmi.

Algoritmul lui Dijkstra este un algoritm folosit pentru a găsi cea mai scurtă cale între

două noduri într-un graf. Principiul de funcționare a algoritmului este simplu. Se începe cu nodul

sursă și se setează ca nodul curent. Restul nodurilor din graf sunt marcate ca nevizitate. Se ia

fiecare nod adiacent nodului curent și se calculează pentru fiecare un cost pentru deplasare.

Costul de deplasare este întotdeauna calculat ca și costul nodului precedent adunat cu costul

Page 38: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

38

mutării pe nod și este alipit acestuia. După ce toți vecinii au fost verificați, marcăm nodul ca fiind

vizitat. Dacă nodul destinație a fost marcat ca vizitat, oprim algoritmul și vom returna distanța

până la nodul sursă. Daca toate nodurile posibile au fost vizitate dar nu s-a ajuns la nodul

destinație atunci algorimul se va opri și va returna infinit pentru că nu există o cale de la sursă la

destinație. Dacă nu este nici unul din cazurile precedente, se caută nodul cu costul cel mai mic, se

setează ca și nod curent și se continuă algoritmul cu vizitarea vecinilor în buclă până se ajunge la

una din condițiile de oprire. (8)

A* este un algoritm care urmează aproximativ aceeași pași ca și cel a lui Dijkstra. Ceea ce

diferă între acești algoritmi este faptul că la calcularea costului unui nod se va lua în considerare

o euristică care va determina dacă nodul curent se îndreaptă spre nodul destinație sau se

îndepărtează, astfel micșorând mult spațiul de căutare. O altă diferență ar fi că fiecare nod va

avea o referință a părintelui său, astfel că odată ajuns la nodul destinație, pentru returnarea căii, se

va itera prin părinții nodurilor de la țintă la destinație.

Revenind la aplicație, trebuie menționat faptul că odată ce jucătorul a apăsat butonul de

deplasare Pathfinder-ul va calcula spațiul în care eroul se va putea mișca. Având în vedere că

acea funcționalitate este realizată prin apelarea aproximativ a acelorași metode, voi omite

prezentarea acesteia. Diferența este că nu se va seta un nod destinație și tot din acest motiv nu se

va seta nici o euristică pentru a fi calculată la costul deplasării (ar fi rendundant și imposibil).

Corpul metodei resolveMoveTouch cuprinde:

public Pathfinder pathfinder = new Pathfinder();

public Array<Square> highlightedSquares = new Array<Square>();

private void resolveMoveTouch()

{

if(highlightedSquares.contains((Square)

instances.get(selectingGameObjectIndex),false)) {

path = pathfinder.findPath(instances, myHero.heroesPositionSquare,(Square)

instances.get(selectingGameObjectIndex));

///

}

}

Page 39: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

39

Pentru ușurință am folosit pătratele hărții ca fiind nodurile grafului folosit de către cei doi

algoritmi prezentați mai sus. Variabila highligthedSquares conține toate pătratele posibile pe

care eroul curent își poate muta poziția. Astfel întâi verific dacă poziția selectată de utilizator

face parte din pozițiile disponibile pentru acesta. În caz afirmativ voi invoca Pathfinder-ul cu

metoda findPath și voi determina cea mai scurtă cale între pătratul eroului

(myHero.heroesPositionSquare) și pătratul selectat ca și pătrat destinație

(instances.get(selectingGameObjectIndex)).

Primul lucru pe care l-am făcut în această metodă a fost reîmprospătarea instanțelor

jocului (în cazul în care jocului i-au fost adăugate noi plăci pe hartă sau eroii sau inamicii s-au

deplasat), setarea pătratului destinație și inițializarea primului nod din graf ca fiind pătratul sursă.

Am creat o nouă listă notVisited care va fi populată cu nodurile ce urmează a fi verificate.

pathInstances = instances;

this.targetSquare = targetSquare;

notVisited.add(new Node(sourceSquare,null));

node = notVisited.get(0);

Se poate observa folosirea unei noi clase și anume clasa Node:

public class Node {

final float directCost = 1f;

public Node parent;

public Square squareObject;

public float F;

public float G;

public float H;

public Node(Square squareObject, Node node) {

this.squareObject = squareObject;

this.parent = node;

}

}

Primul atribut este o constantă directCost semnificând costul unei mutări urmată de

atributul parent specificând nodul părinte și squareObject semnificând pătratul la care face

referință acest nod. Cele trei variabile F, G și H sunt folosite pentru a calcula costul nodului.

Acestea sunt notații standardizate pentru algoritmul A*.

Page 40: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

40

În continuare, în corpul metodei findPath am construit algoritmul A*:

while(notVisited.size > 0) {

float minF = notVisited.get(0).F;

for (Node node : notVisited)

if (node.F <= minF) {

minF = node.F;

this.minNode = node;

}

if(this.minNode.squareObject.equals(targetSquare)) {

while (!minNode.squareObject.equals(sourceSquare)) {

Path.add(new Vector2(minNode.position.x, minNode.position.y));

if (minNode.parent == null) {

Path.add(new Vector2(sourceSquare.xPosition,

sourceSquare.yPosition));

break;

}

minNode = minNode.parent;

}

Path.reverse();

return Path;

}

checkAndSetSquareNeighbours(minNode, 0);

notVisited.removeValue(minNode, true);

visited.add(minNode);

}

În testul buclei while se verifică daca am trecut prin toate nodurile din spațiul de căutare,

în caz negativ bluca va căuta în continuare o cale. De specificat faptul că acest test va deveni

pozitiv doar atunci când nu se poate ajunge la nodul destinație. Pentru a nu întâmpina anomalii

sau excepții vom inițializa costul minim cu costul primului nod din colecția de noduri nevizitate.

Calculul costului nodului se calculeaza apelând metoda calculateCosts a clasei Node.

public void calculateCosts(GameObject destination, boolean isDiagonal) {

this.H = calculateHeuristic();

if (parent != null)

this.G = parent.G + directCost;

else

this.G = directCost;

this.F = this.G + this.H;

};

În expresia costului am introdus o euristică determinată de distanța euclidiană între nodul

curent și nodul destinație calculată si returnată de metoda calculateHeuristic . După aceasta se

va calcula costul final si se va stoca în variabila F.

Page 41: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

41

În continuare iterez prin toate nodurile nevizitate și găsesc nodul cu costul minim. Dacă

nodul selectat cu costul minim este nodul destinație, atunci pornind de la acest nod iterăm printre

părinții fiecărui nod până ajungem la nodul sursă. Acest lucru este marcat prin faptul că nodul

sursă nu are părinte. La fiecare iterație adăugăm nodul vectorului Path care va returna calea.

Când este găsit nodul sursă, bucla este oprită, se va inversa calea (deoarece aceasta este construită

de la destinație la sursă iar ea va fi folosită vice-versa) și se va returna.

Dacă nodul curent nu este cel final, se va căuta calea în continuare în metoda

checkAndSetSquareNeighbours:

private void checkAndSetSquareNeighbours(Node node, int maximumRange) {

for (GameObject objectInstance : pathInstances)

if (!objectInstance.getGameObjectType().equals("Hero") &&

!objectInstance.getGameObjectType().equals("Monster") &&

!objectInstance.getGameObjectType().equals("Wall"))

if (maximumRange > 0)

//această metodă este folosită pentru a calcula aria de mișcare

setSquareNeighbours(objectInstance, node, maximumRange);

else

setSquareNeighbours(objectInstance, node, 0);

}

Iterăm prin toate obiectele jocului eliminând cele care nu sunt pătrate. Pentru fiecare vom

apela metoda setSquareNeighbours în care verificăm dacă poziția lui coincide cu una din

pozițiile adiacente nodului curent:

if (x != node.squareObject.xPosition || y != node.squareObject.yPosition) {

if (x == objectInstance.transform.getTranslation(position).x &&

y == objectInstance.transform.getTranslation(position).y) {

this.node = new Node((Square) objectInstance, node);

if (!checkCollectionsForExistingItems(visited) &&

!checkCollectionsForExistingItems(notVisited)) {

if (x == y || (x + y) == 2)

this.node.calculateCosts(targetSquare, true);

else

this.node.calculateCosts(targetSquare, false);

notVisited.add(this.node);

}

}

}

Page 42: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

42

În caz pozitiv creăm un nod nou și verificăm dacă cumva acest nod a fost deja iterat și pus

în una din colecțiile visited (pentru nodurile deja vizitate) și notVisited (pentru nodurile încă

nevizitate dar care urmează a fi). Dacă nu este prezent, îi calculez costul și îl voi adăuga în

colecția notVisited pentru a fi testat ulterior.

Trebuie specificat faptul că în jocul prezent costul mișcării pe diagonală este egal cu

costul mișcării directe. Totuși am lăsat loc extinderii acestei funcționalități.

În momentul de față PathFinder-ul este capabil să calculeze o cale de la punctul sursă

până la cel destinație și să returneze poziția fiecărui punct din acea cale. Revenim la corpul

metodei resolveMoveTouch unde în variabila path avem calea care trebuie urmată. Totuși acest

lucru nu este de ajuns pentru a pune obiectul în mișcare.

private void resolveMoveTouch()

{

if(highlightedSquares.contains((Square)

instances.get(selectingGameObjectIndex),false)) {

///

myHero.setPath(path);

myHero.hasMoved = true;

myHero.setFinalPosition(path.get(0).x, path.get(0).y);

}

}

În libGDX și în majoritatea motoarelor de dezvoltare a jocurilor pentru a mișca obiectele

pe scene ele trebuie translatate manual, acest lucru însemnând că fiecare obiect ce se vrea a fi

mișcat trebuie actualizat pe fiecare cadru desenat.

Pentru a realiza acest lucru am creat metode speciale pentru obiecte și am adăugat o

variabilă pentru a semnala faptul că obiectul este în mișcare. Astfel am în clasa GameObject:

public boolean hasMoved= false;

public void setPath(Array<Vector2> path){

this.Path = path;

}

public void setFinalPosition(float finalX, float finalY) {

this.finalPositionX = finalX;

this.finalPositionY = finalY;

}

Page 43: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

43

În metoda setPath adaug calea tocmai calculată pentru a semnala faptul că obiectul

trebuie să o urmeze. În setFinalPosition setez întotdeauna următorul punct pentru a fi urmat din

cale. Inițial setez ca punctul la care trebuie ajuns este primul punct din path și setez variabila

booleană pozitiv pentru a marca faptul că acest obiect trebuie mișcat. Până în acest punct am

pregătit obiectul pentru translație.

În acest moment trebuie calculat la fiecare cadru redat pe ecran cu cât trebuie mișcat

obiectul și în ce direcție. Pentru realizarea acestui lucru am implementat o nouă metodă:

private Vector2 velocity = new Vector2();

private float tolerance = 0.1f;

private float speed = 10f;

public void updatePosition(float deltaTime) {

float angle = (float) Math.atan2(this.finalPositionY -

this.transform.getTranslation(position).y,

this.finalPositionX -

this.transform.getTranslation(position).x);

velocity.set((float)Math.cos(angle) * speed, (float) Math.sin(angle) * speed);

this.transform.translate(velocity.x * deltaTime, velocity.y * deltaTime, 0f);

isNodeReached();

}

Prima dată calculez unghiul în care obiectul trebuie să se deplaseze, astfel în variabila

angle stochez cotangenta diferenței valorilor punctului destinație și a punctului curent. În

variabila velocity setez puterea mișcării obiectului. Acest lucrul îl realizez prin adăugarea unei

viteze fiecărei coordonate a punctului. Aplic cosinus pentru coordonata x și sinus pentru

coordonata y pentru a afla unde anume trebuie poziționat obiectul. Deoarece pe anumite

dizpozitive există riscul ca jocul să prindă momente de latență, această mișcare trebuie filtrată cu

deltaTime. Această variabilă reprezintă timpul scurs între două cadre desenate, astfel deși poate

pe un dizpozitiv merge mai lent jocul, obiectele vor porni și vor ajunge în același timp ca pe un

dispozitiv cu resurse mai mari. În final aplicăm aceste transformări obiectului.

După cum am specificat această operație trebuie realizată la fiecare cadru desenat astfel că

în metoda render a GameManager-ului am scris următoarele linii de cod:

Page 44: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

44

for(HashMap.Entry<String,Hero> entry : heroes.entrySet()) {

if(entry.getValue().hasMoved) {

entry.getValue().updatePosition(Gdx.graphics.getDeltaTime());

}

}

Astfel pentru fiecare obiect care trebuie mișcat aplicăm aceste transformări. În acest

moment obiectul va urmări primul punct din cale urmărind o mișcare rectilinie uniformă dar nu

se va îndrepta spre celelalte deoarece punctul reper nu este resetat. De aceea în updatePosition

avem un apel către metoda isNodeReached.

public void isNodeReached() {

if ((Math.abs(this.transform.getTranslation(position).x –

this.finalPositionX) <= tolerance) &&

(Math.abs(this.transform.getTranslation(position).y –

this.finalPositionY) <= tolerance)) {

this.transform.setTranslation(this.finalPositionX,this.finalPositionY, 2f);

if (Path.size >= 2) {

this.setFinalPosition(Path.get(1).x, Path.get(1).y);

this.Path.removeIndex(0);

} else {

this.finalPositionX = 0;

this.finalPositionY = 0;

this.hasMoved = false;

}

}

}

La fiecare apel trebuie verificat dacă obiectul a ajuns la destinația setată. Deoarece

variabilele raționale nu ne garantează faptul că obiectul va ajunge exact în punctul destinație, am

facut un test adițional în care verific dacă poziția obiectului în mișcare este apropiat de cel

destinație la o anumită toleranță. Această toleranța trebuie bine definită astfel că dacă valoarea

este prea mică va face ca ea să fie ignorată în timp ce dacă este prea mare aceasta va face ca

obiectul să se teleporteze la destinație. Dacă se intră în intervalul acestei toleranțe vor fi tratate

două cazuri. Dacă mai există puncte în cale, noua poziție finală va fi urmatorul nod din aceasta,

altfel înseamnă că am ajuns la punctul final, resetăm poziția finală și marcăm obiectul ca fiind

staționar. În ambele cazuri totuși setăm poziția obiectului exact în poziția finală pentru a nu avea

deviații în mișcarea obiectului. Acest lucru ne este garantat de faptul că punctele căii sunt numere

întregi. În acest moment obiectele se pot mișca pe suprafață de joc în timp real.

Page 45: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

45

5. Manual de utilizare

5.2 Meniul principal

Prima interacțiune pe care o va avea utilizatorul aplicației este meniul principial. Acesta

este punctul de reper pentru toate celelalte funcționalități. Meniul conține patru butoane, fiecare

cu un mesaj sugestiv în engleză:

1. Butonul de joc „Singleplayer” semnifică începerea unui joc cu un singur jucător;

2. Butonul de joc „Multiplayer” semnifică începerea unui joc în mai mulți jucători;

3. Butonul „Create a hero” semnifică creearea unui erou pentru desfășurarea jocului;

4. Butonul „Exit”, unde utilizatorul poate părăsi aplicația.

Imaginea 1: Meniul principal

Desigur, prima intenție a unui jucător va fi de a apăsa butonul pentru un joc cu un singur

jucător pentru a-l testa. În acest moment va fi afișat un chenar simplu și gol deoarece utilizatorul

nu a creat nici un erou. Din fericire acest meniu conține două butoane: butonul de a adăuga un

nou erou sau de a șterge unul deja creeat. În acest caz vom folosi butonul de creare marcat cu

simbolul „+”.

Page 46: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

46

5.3 Meniul de creare a unui erou

Acest meniu este unul complex, conținând informații despre rolul eroului în jocurile ce

vor urma. Meniul este împărțit în mai multe secțiuni.

Pe primul rând se află posibilele tipuri de ființe pe care jucătorul le poate alege. Fiind un

joc fantastic aceste ființe au diverse caracteristici diferite de ale oamenilor. Utilizatorul are 3

opțiuni: Star-elves, Moon-elves, Ferrevum.

Pe al doilea rând se află specializările pe care eroul le poate avea. Utilizatorul are la

dispoziție 3 specializări: Ranger, Warrior, Wizard. Specializarea va influența decisiv rolul erolui

în joc deoarece aceasta va defini ce tipuri de abilități va folosi în joc. De exemplu dacă

specializarea eroului este „wizard” (vrăjitor) acesta va folosi abilități magice care vor fi invocate

de la distanță, în timp ce pentru un „warrior” (războinic) abilitățile acestuia pot fi folosite

împotriva monștrilor adiacenți.

Aceste două selecții de mai sus sunt obligatorii și se poate alege o singură opțiune din

fiecare. Totodată acestea vor influența și atributele erolui. Acestea sunt afișate în partea de sus

dreapta a meniului sub titlul „stats” (atribute).

Imaginea 2: Meniul de creare a unui erou

Page 47: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

47

Eroul are patru atribute: health (puncte de viață), armor (armură), speed (viteză), surge

(reîmporspătare). Fiecare dintre acestea va caracteriza eroul în joc astfel:

1. Punctele de viață semnifică câte puncte de vătămare va putea primi până acesta va

fi înfrânt.

2. Punctele de armură sunt punctele care semnifică cât de rezistent este eroul în

luptă. Dacă valoarea atacului depășește această valoare, armura este pătrunsă iar

eroul va fi rănit, în caz contrar armura rezistă iar eroul nu va suferi nici un efect.

3. Viteza eroului semnifică câte pătrate se va putea mișca eroul pe hartă.

4. Punctele de reîmprospătare semnifică câte puncte de viață va regenera eroul după

ce va fi înfrânt.

Sub acestea sunt două mari secțiuni conținând 10 abilități (Abilities). Utilizatorul trebuie

să aleagă 5 abilități din cele afișate. O dată ce o abilitate este selectată, un meniu va apărea cu

numele, efectele, numărul de atac și numărul de puncte de vătămare. Numărul de atac semnifică

numărul adunat la valoarea zarului de atac. Dacă aceste două valori adunate sunt egale sau mai

mari decât valoarea armurii inamicului, atacul se consideră a fi cu succes. Dacă atacul este cu

succes, inamicului i se retrag din punctele de viață, punctele de vătămare ale abilității.

Pentru a identifica eroul, acestuia i se va atribui un nume. Acest nume poate fi introdus

sub chenarul principal al meniului.

În stânga numelui va fi butonul „back” (înapoi) unde utilizatorul se poate întoarce în

meniul precedent iar în dreapta acestuia este butonul „done” (terminat) unde utilizatorul poate

semnala faptul că este mulțumit cu opțiunile alese și dorește crearea eroului. Eroul nu va fi creat

daca utilizatorul nu a introdus un nume sau nu a selectat exact cinci abilități. Dacă eroul este creat

va apărea pe ecran un mesaj de confirmare.

Acum dacă revenim în meniul de alegere a erolui vom vedea eroii creați. Aceștea pot fi

identificați după nume dar și după poza sugestivă reprezintând tipul eroului. Pentru a reveni la

meniul precedent utilizatorul poate folosi butonul „back”. Pentru a începe jocul jucătorul poate

apăsa butonul de start (start).

Page 48: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

48

5.4 Interfața utilizatorului

Interfața cu utilizatorul conține toate informațiile necesare unui jucător pentru a-și

desfășura sesiunea de joc. Astfel aceasta a fost structurată pentru ca interacțiunea să fie optimă și

intuitivă.

Imaginea 3: Interfața utilizatorului și afișarea obiectivului

În partea de sus sunt afișate caracteristicile eroului. Pe parcursul jocului aceste valori se

vor modifica, astfel jucătorul va fi anunțat în timp real de orice modificare. În stânga acestor

valori este afișat un portret cu eroul respectiv. În dreapta sunt afișate alte două valori: experience

(experiență) și surges („reîmprospătări”). De-a lungul jocului eroul va înfrunta inamici, odată ce

acești inamici vor fi eliminați fiecare va genera puncte de experiență. Experiența este stocată la

nivel de joc si nu de erou, astfel într-un joc cu mai mulți jucători toți vor contribui la această

valoare. Experiența este utilizată pentru a evita diferite hazarde explicate mai jos. Numărul de

reîmprospătări semnifică de câte ori poate reveni în joc un erou după ce este înfrânt. La fel ca și

experiența, acest număr este la nivel de joc si oricare joc va începe cu valoarea 2.

În partea stângă sunt butoanele pentru diferitele acțiuni ale jucătorului: mutarea erolui,

folosirea unei abilități, încheierea turei și aruncarea zarului. Sub aceste butoane avem un spațiu

rezervat pentru afișarea diferitelor acțiuni ale jocului. Astfel în acest spațiu se pot consulta

Page 49: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

49

ultimele trei evenimente ale jocului și este constant împrospătat. Aici se pot consulta valorile

zarurilor, acțiunile eroilor sau ale inamicilor, efectele hazardelor și altele.

În partea de jos avem cinci butoane, unul pentru fiecare abilitate a erolui. Fiecare buton

conține numele abilității care va fi invocată. După aceste butoane avem un buton rotund pentru

meniul de pauză. Acesta va înterupe jocul curent și se va afișa un meniu cu două opțiuni:

părăsirea jocului curent sau revenirea la acesta.

Diferite părți ale interfeței vor fi indisponibile în anumite momente ale jocului. Acest

lucru este semnalat prin colorarea gri a butoanelor.

5.5 Desfășurarea unui joc

Scopul jocului este de a duce la bun sfârșit obiectivul setat la începutul acestuia.

Obiectivul va fi ales la întâmplare la fiecare start de joc. Un meniu va fi afișat exact la începutul

sesiunii și va conține o descriere cu ce acțiuni trebuie făcute. Acestea pot varia de la eliminarea

unui lider până la distrugerea unei trupe de monștri.

În continuare voi explica anumiți termeni specifici jocului pentru o mai bine înțelegere a

desfășurării acestuia:

Pătrat, este unitatea de măsurare a spațiilor de pe hartă. Acestea pot fi pătrate

normale, ziduri sau pătrate de invocare a inamicilor.

Placă, este o colecție de 16 pătrate care conține diferite tipuri de pătrate.

Hazard, un eveniment aleatoriu în timpul jocului emis la fiecare sfârșit de tură.

Fiind un joc bazat pe ture fiecare jucător va avea tura lui. Fiecare tură se desfășoară în

aceeași ordine astfel:

1. Acțiunile erolui.

2. Explorarea în continuare a peșterii.

3. Rezolvarea unui hazard.

4. Acțiunile inamicilor.

Jocul pornește cu doar două plăci explorate urmând ca eroii să descopere la fiecare tură

noi părți din această peșteră pentru a găsi calea spre împlinirea obiectivului.

Page 50: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

50

Eroul curent poate face două acțiuni. Acțiunile disponibile sunt mutarea eroului sau

folosirea unei abilități. Eroul poate folosi doar o singură acțiune de atac (folosirea unei abilități)

și două de mișcare la fiecare tură (unii eroi nu se vor supune cu exactitate acestor reguli).

Imaginea 4: Marcarea pătratelor unde se poate muta eroul

Pentru ca utilizatorul să își mute caracterul acesta va trebui să apese pe butonul de

„move”. Odată apăsat, toate pătratele unde eroul poate ajunge vor fi marcate cu verde. Aria

acestei zone este determinată de viteza eroului, astfel la o viteză de 2, eroul se va putea mișca 2

pătrate în orice direcție. Se poate mișca și pe diagonală. Dupa aceasta jucătorul va selecta eroul

său dupa care va apăsa pe pătratul unde dorește ca eroul să fie mutat. Dupa ce este mulțumit de

poziție, va apăsa pe același buton dar care are un mesaj diferit „end move” (încheiere mișcare).

Acest lucru va consuma o acțiune.

Pentru a ataca, eroul trebuie să apese pe butonul de folosire a abilităților, după care va

selecta o abilitate din cele 5 afișate. După selecție îi este indicat jucătorului să aleagă o țintă

pentru abilitate. Dacă ținta nu este validă va fi afișat un mesaj de atenționare, în caz contrat este

selectată ținta și utilizatorului îi este indicat să arunce zarul. După ce este apăsat butonul de zar se

va verifica dacă abilitatea este folosită cu succes sau nu. Aceste informații pot fi consultate în

locul rezervat evenimentelor marcate cu „log”.

Page 51: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

51

Succesului unei abilități este calculat astfel: se ia valoarea zarului aruncat, se adună cu

valoarea atacului abilității și se compară cu armura inamicului. Dacă această comparație este mai

mare sau egală se consideră ca abilitatea fiind folosită cu succes. În acest caz se va extrage din

punctele de viață ale țintei numărul de puncte de vătămare.

În cazul în care inamicul are 0 sau mai puține puncte de viață acesta este considerat

distrus, va fi scos de pe hartă și va genera puncte de experiență pentru eroi.

Imaginea 5: Folosirea unei abilități și afișarea informațiilor în Log

Calcularea abilităților este identică pentru inamici iar valoarea zarului este aleasă aleator

și automat de către joc. Fiecare abilitate folosită cu succes de către eroi, monștri sau hazarde vor

fi semnalate prin diferite efecte vizuale precum flăcari sau raze de lumină.

Dacă eroul nu mai are acțiuni, acesta va trebui să apese pe butonul de încheiere a turei

(„end turn”) lucru sugerat și de către joc. După aceasta se va continua tura în modul specificat

mai sus.

În cazul în care un erou și-a încheiat tura pe un pătrat la marginea unei plăci și nu este zid,

acesta va explora o placă nou generată. Fiecare placă va avea un pătrat diferit pentru a simboliza

pătratul unde inamicul își va face apariția. La fiecare placă nou generată se va genera și un nou

inamic. Inamicii vor acționa întotdeauna la tura acelui erou la care au fost invocați.

Page 52: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

52

Inamicii vor fi generați în funcție de viața eroilor, de numărul de jucători și tipul eroilor.

Astfel într-un joc cu un singur erou moon-elf, monștrii vor avea puncte de viață puține, vor

genera puține puncte de experiență și vor avea o probabilitate mai are să fie de tipul opus eroului.

Fiecare monstru are la rândul lui un nume, un tip și o serie de abilități. Abilitățile se vor efectua

în cascadă, astfel dacă prima abilitate nu poate fi folosită o va încerca pe următoarea. Această

căutare se oprește atunci când o abilitate poate fi utilizată sau când nu mai sunt abilități de căutat,

caz în care inamicul nu face nici o acțiune.

Toate aceste informații pot fi consultate atunci când utilizatorul apasă pe un inamic.

Imaginea 6: Caracteristicile unui inamic

După explorare anumite evenimente se vor întâmpla în această peșteră. Un meniu va fi

afișat unde este prezentată o descriere a ceea ce va urma să se întâmple și încă două butoane, unul

pentru a folosi experiența acumulată pentru a evita hazardul și altul pentru continuarea jocului cu

evenimentele descrise. Orice hazard poate fi evitat folosind exact 5 puncte de experiență. Datorită

dificultății, jumătate dintre aceste hazarde au posibilitatea de a fi benefice eroului. Spre exemplu,

un hazard negativ poate fi reducerea armurii unui erou cu 2 pentru următoarele două ture în timp

ce unul pozitiv poate fi regenerarea a două puncte de viață.

Page 53: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

53

După hazard, dacă eroul activ a invocat inamici în această rundă sau runde precedente,

aceștia vor acțiuna în funcție de abilitățile lor. Toate aceste acțiuni vor fi regăsite în spațiul

dedicat evenimentelor. Monștrii acționează în ordinea invocării lor pe hartă.

După toate aceste evenimente se va semnala încheierea turei curente și jocul va continua

cu tura următorului jucător. În cazul unui joc cu un singur jucător, va urma tot tura acelui jucător.

Figură 1: Începerea unei noi turi

Page 54: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

54

6. Concluzii

Scopul acestei aplicații este de a oferi un mod de joc mult mai dinamic din punctul de

vedere al jucătorului și de a testa modul în care acesta reacționează la schimbări. Acestea au fost

realizate cu ajutorul anumitor elemente precum generatea pseudo-aleatorie a hărții de joc și

generarea aleatorie a inamicilor. Toate aceasta contribuie la originalitatea jocului care dorește să

nu plictisească utilizatorul. Totodată aplicația a fost dezvoltată pentru telefoane, oferind

posiblitatea de a fi jucată oriunde și într-o perioadă relativ scurtă de timp. Deoarece aplicația este

destinată pasionaților de jocuri, aceasta este plasată într-un cadru fantastic având elemente

specifice acestui gen: creaturi fantastice și magie.

Deși jocul în sine nu explorează o gamă largă de evenimente și interacțiuni între joc și

utilizator, datorită stilului de joc acesta poate fi îmbunatățit. În acest sens jocului i se pot adăuga

rase noi de eroi, noi specliatități cu abilități specifice, evenimente noi, obiective noi și chiar

suprafață mai mare de joc. Totodată adăugarea de animații personajelor de pe tablă ar putea

aduce un foarte mare plus atmosferei jocului, aducând lucrurile mai aproape de realitate. În

ultimul rând, aplicației i s-ar putea aduce un sistem de răsplată mult mai potent. Căutarea de

artefacte și obiecte magice pe care eroii le pot folosii poate constitui un plus foarte mare jocului.

O aplicație care reușește să își țină utilizatorul mereu atent prin prezentarea de noi elemente

fiecărui joc este o aplicație care ar putea fi considerată de succes din punctul de vedere al

jucătorului.

Page 55: Dungeon Master Joc de strategie tactic pe …alaiba/pub/absolvire/2017...mai vechi dar încă actuale jocuri de societate este șahul. Chiar dacă aceste jocuri au farmecul lor, de

55

7. Referințe

1. Pagina oficială BadLogicGames. [Online] https://libgdx.badlogicgames.com/.

2. Pagina Wikipedia pentru Mediul de dezvoltare Android. [Online]

https://en.wikipedia.org/wiki/Android_software_development.

3. Pagina Wikipedia pentru limbajul Java. [Online]

https://en.wikipedia.org/wiki/Java_(programming_language).

4. Pagina oficială Node.js. [Online] https://nodejs.org/en/about/.

5. Pagina Wikipedia pentru limbajul JavaScript. [Online] https://en.wikipedia.org/wiki/JavaScript.

6. Pagina Wikipedia pentru Socket.IO. [Online] https://en.wikipedia.org/wiki/Socket.IO.

7. Sebastian Di Giuseppe, Andreas Kruhlmann, Elmar van Rijnswou. Building a 3D Game with

LibGDX. 2016.

8. Pagina Wikipedia pentru algoritmul lui Dijkstra. [Online]

https://en.wikipedia.org/wiki/Dijkstra's_algorithm.