ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1...

31
1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS 428 Professor Darko Marinov Spring 2010 Authors Drew Glass Josh Glovinsky Hyun Soon Kim David Kristola Michael Lai Henry Millson John Svitek

Transcript of ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1...

Page 1: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

1

ROGUEANDROID A Diablo inspired role-playing game for Android

University of Illinois CS 428

Professor Darko Marinov Spring 2010

Authors Drew Glass

Josh Glovinsky Hyun Soon Kim David Kristola

Michael Lai Henry Millson

John Svitek

Page 2: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

2

CONTENTS RogueAndroid ................................................................................................................................................................ ........... 1

Figures ................................................................................................................................................................ ..................... 3

Description ................................................................................................................................................................ ............ 4

Process .................................................................................................................................................................................... 4

Requirements and Specifications ................................................................................................................................. 7

Choose a Character ........................................................................................................................................................ 7

Displaying and Populating the Dungeon .............................................................................................................. 8

Moving the Character ................................................................................................................................................... 8

Looking Around .............................................................................................................................................................. 8

Character Attacking Monster .................................................................................................................................... 8

Monster Attacking Character .................................................................................................................................. 10

Picking up Items ........................................................................................................................................................... 10

Ending the Game .......................................................................................................................................................... 11

Architecture ................................................................................................................................................................ ........ 11

Overview................................................................................................................................................................ .......... 11

Metaphor ................................................................................................................................................................ ......... 12

Stakeholders ................................................................................................................................................................ .. 13

Views ................................................................................................................................................................................. 13

Principles ................................................................................................................................................................ ......... 14

Design ................................................................................................................................................................ .................... 15

Overview................................................................................................................................................................ .......... 15

Model ................................................................................................................................................................ ................ 15

View ................................................................................................................................................................ ................... 19

Controller ................................................................................................................................................................ ........ 21

Miscellaneous ................................................................................................................................................................ 25

Future Plans ................................................................................................................................................................ ........ 25

Immediate Extensions ............................................................................................................................................... 25

High-Level Goals ........................................................................................................................................................... 26

Personal Reflections ................................................................................................................................................... 26

Appendix ................................................................................................................................................................ .............. 30

How to install Eclipse and the Android SDK ..................................................................................................... 30

Page 3: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

3

Installation of the RogueAndroid Source Files ................................................................................................ 30

Installation of other files for Development ....................................................................................................... 30

Playing and Debugging the Game .......................................................................................................................... 30

Installing RogueAndroid on an Android Device .............................................................................................. 30

FIGURES Figure 1 Choose Character Screen .................................................................................................................................... 7

Figure 2 UML Use Case Diagram ....................................................................................................................................... 9

Figure 3 Combat Game Play Screen ............................................................................................................................... 10

Figure 4 Boss Monster Screen .......................................................................................................................................... 11

Figure 5 Game Over Screen ............................................................................................................................................... 11

Figure 6 Model-View-Controller Diagram ................................................................................................................... 12

Figure 7 dungeon.txt ............................................................................................................................................................ 13

Figure 8 UML Model Class Diagram ............................................................................................................................... 16

Figure 9 UML Travel Action Sequence Diagram ....................................................................................................... 18

Figure 10 UML Attack Action Sequence Diagram .................................................................................................... 19

Figure 11 UML View Class Diagram ............................................................................................................................... 20

Figure 12 UML Controller Class Diagram .................................................................................................................... 22

Figure 13 UML Touch and Scroll Sequence Diagram .............................................................................................. 23

Figure 14 UML Game Startup Diagram ......................................................................................................................... 24

Figure 15 Coordinate System ........................................................................................................................................... 25

Page 4: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

4

DESCRIPTION RogueAndroid is a fast paced tile based role-playing game for Android devices based on the classic game Diablo. RogueAndroid provides an easy-to-use interface including "swiping" technology to view other sections of the map, "touch" technology to attack and travel, and "auto pickup" of items to increase attack and defense bonuses.

In RogueAndroid, the game’s quest is to search the dungeon for the Red Dragon and to slay it. Many dangerous enemies are encountered along the way and a fight is always just around the corner. Magic potions can be used to heal and restore hit points lost during battles with monsters. Other items such as swords and shields can be used to raise attack and defense to increase the chance of defeating the Red Dragon and winning the game.

Currently RogueAndroid supports three character classes: warrior, ranger and mage and two monster types: dragon and orc. There are various items supported including swords, helmets, shields, and healing potions. RogueAndroid is built using Rokon, an Android OpenGL game engine, Android SDK, Java 1.6, a newly developed tile engine, and a completely integrated testing suite.

PROCESS Rather than jump in and start coding, the RogueAndroid team met to discuss the project in a series of meetings before work actually began. Before starting development process, the team discussed how the XP process would work given the challenges the team faced. In addition to some serious though common challenges faced by a new project team – unfamiliarity with the technology, platform (Android), development environment, language (Java), and libraries (Rokon) – the team faced several challenges that are uncommon in normal work environments (though perhaps they are common in open source projects).

The first challenge was that the team was geographically distributed. This meant that the XP practice of pair programming would be difficult. The 10 time zones our team spanned and unpredictable working hours made pair programming nearly impossible. Instead, we came up with a collaborative development method that worked for our team. Once the user stories for the iteration were determined, the team members would select tasks to work on. For larger tasks, two or more team members would work on it collaboratively, sharing the coding duties. For tasks assigned to one person, the coder would partner with the other team members working tasks in the same story. This meant that two or more team members were working together on all tasks. But this in and of itself did not mean we were doing collaborative development. We needed something more.

Collaborative development was a major challenge because of what we call Spare Time Development. No methodology that we were aware of is designed for developers who are working in their spare time. Even if we had been geographically co-located, it was unlikely that a pair of individuals working on shared tasks would find mutually acceptable times to sit down and pair program. We did find ways to do collaborative development, however. We developed

Page 5: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

5

collaboratively through a combination of Skype sessions with both team members working on the same code, rapid check-in/check-out cycles, and passing the code back and forth between team members with each filling in their contribution or revising or refactoring the work of others. The latter case was a kind of off-line pair programming, where the virtual keyboard was passed from individual to individual, each adding their portion as author, and then acting as reviewer each time the code was passed back to them. These approaches worked surprisingly well, helping to share knowledge across the team while improving the quality of the code. These approaches worked so well for coding, in fact, that we often used the same techniques in our pair homework assignments.

We found it difficult to find meeting times that worked, even though we met only once a week. As team members dealt with work, travel, business commitments, family, and personal issues, the process of finding time for team meetings became very challenging. Compounding this was the 10 hour spread in time zones. We started with a set meeting time each week, and quickly learned that such an arrangement was impossible. Rather than a set time which one or more team members would inevitably miss, the project manager would request the team members post their availability over the weekend. The team meeting time was the one that accommodated the greatest number of individuals.

RogueAndroid was built using an agile development process. We used XP, and adopted or adapted the practices based on our needs. Some practices were straight XP. We developed and published a set of coding standards. We employed continuous integration using SVN, which formed the cornerstone of the collaborative development process we developed, as outlined above. Small releases were ensured by the milestone reviews. We employed simple design, and used YAGNI as a design filter. Sustainable pace was ensured by the non-school commitments of everyone on the team.

Throughout the project the system metaphor guided the way. During our first meeting we discussed what we were trying to build, and everyone on the team came away with a clear understanding of what it was and how it would look and feel and play. We were lucky in that our rogue-like game metaphor was well-known, so much so that we adopted the name RogueAndroid. Evolving our work to meet the ideal of the system metaphor drove the planning game.

We adapted the planning game to suit our unique situation. At the start of an iteration we gathered ideas for the release by allowing anyone on the team to post them to the wiki for a period of a few days. We then met as a team and prioritized the ideas, which were broken out into tasks and individuals would volunteer for those tasks. We wrote a user story that accomplished those tasks. This is rather backwards to the recommended planning game approach (though more in line with the reality discussed in A Rational Design Process: How And Why To Fake It), but better reflected the reality of what the XP practice of Whole Team meant in our context.

Whole team was indeed, in our case, the whole team. Each of us contributed as customer as well as implementer. This was initially confusing to the team, because of the assumption we had made that the customer was the reviewer at the milestone meeting. We quickly learned that while the reviewer played a portion of the customer role, they would not be providing requirements or user

Page 6: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

6

stories. It was up to the team to put on our customer hats and fill that role. Wearing both hats, but being a team comprised of engineers, meant that some engineering tasks were prioritized above work that a customer may have required earlier. Design improvement rescued us from these cases.

Design improvement – iterative development – was the hallmark of our effort. For example, we created an initial spike for milestone one to demonstrate that our chosen game engine worked, and was a suitable basis for the project. The spike demonstrated the concept to the customer, and then was refactored into the basis of first iteration development. The history is still there: by comparing RogueAndroidSpike.java with Game.java, remnants can be found of the initial spike, overwritten by generations of iterative improvements. This iterative process can be found in virtually every class in the game, where collective code ownership is evidenced by not only new code and iterative improvements to the class by multiple authors, but also by the statement that the author of each file is the team rather than an individual. This collective code ownership was obvious during the code reviews, where multiple team members could speak authoritatively about the files under discussion, each adding their own perspective and history on the code, while referencing portions of code not written by anyone present in that particular review.

All of the design improvement meant that we needed to refactor constantly. Some of these refactoring were at the class level, but sometimes they were far more extensive, as in the case of the architecture. Initially we had a ball of mud, and quickly realized that we needed to formalize an architecture before we wrote any more code. After much discussion, we settled on Model-View-Controller, because it separated the concerns of the game engine (view) from the input code (controller) and the core game logic (model). We then refactored the code around that architecture, while preserving as much of the original class structure as possible. As the iterations passed, it became clear that we were devolving once again into a ball of mud. We decided to refactor again, and this time we needed a way to ensure that it would not devolve again. The solution was to refactor the classes into formal model, view, and controller components. The components were then reflected in the refactored source tree, such that the folder structure mirrored the architecture. Classes were moved into the new folder structure, and the code refactored appropriately. The separation of concerns was more obvious and enforceable. We were not done refactoring at a grand scale, however, as we later decided to invert the dependencies of the view and the model.

These types of wholesale refactorings would not have been possible were it not for the large number of unit tests the team wrote. While some members did indeed do test first development, others wrote their unit tests at the time they committed the code. In either case, the team had a standard that all tests must pass before code could be checked in. Breaking the tests was a serious offense, which needed to be rectified as soon as discovered. There weren't many instances of this, and the team members quickly jumped into help when they occurred.

It was quite an accomplishment having so many tests, because writing tests for Android is a challenge. Rather than use a standard JUnit test, the Android group chose to create their own test runner, which employed an odd syntax and in an unfamiliar context, and was poorly documented. We tried doing standard JUnit tests, but found them difficult to implement. The team finally adopted

Page 7: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

7

the Android JUnit test framework, and all tests were written for that framework. One unwelcome code change necessitated by this was the need to make all tested methods public. This exposed internal class methods outside the class, violating both good programming practice and our own coding standards. There were many comments in the code to the effect that a method that should be private was made public so it could be tested under Android JUnit.

Even with the XP process adapted to our unique needs, ultimately it likely would not have worked without the diligent efforts of our project manager, Drew Glass. While the team to a large degree self-policed the coding standards and adherence to the architecture, without the project manager the process itself may have devolved into a ball of mud.

REQUIREMENTS AND SPECIFICATIONS

CHOOSE A CHARACTER Upon starting the game, the user is presented a choice of characters to play (Figure 1 and Figure 2). The choice is simply a stylistic one, and different choices will make the character look differently while playing the game. There are no differences to the actual game play between the choices. After choosing a character, the game’s title screen is displayed while the graphical assets are loaded into memory.

Figure 1 Choose Character Screen

Page 8: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

8

DISPLAYING AND POPULATING THE DUNGEON The dungeon is created using a static layout, so the layout of the tiles that make up the dungeon will remain the same between plays. Some tiles in the dungeon are open and appear like grass, and others are impassible walls and appear as stone. The character is placed in the top-left corner of the dungeon. The dungeon is randomly populated with items, such as swords, armor, or potions, which are represented by understandable sprites. Monsters, such as dragons and orcs, are also placed into the dungeon at random locations. These monsters are represented by animated sprites. Finally, a single boss monster is placed at the opposite end of the dungeon, represented by an oversized dragon sprite. The player’s current and maximum hit points are displayed at the top of the screen.

MOVING THE CHARACTER The user can move the character around the screen by touching the location they want the character to move to. When the user taps the screen, the character will begin moving towards that location, even if it is occupied by a monster or an item. If the user taps the screen where a wall is located, or if the simplest path from the user to the touched location is blocked by a wall, the character will move as far as possible, adjacent to the wall. When the character is moving, the camera will follow the movement to keep the character on screen. During movement, the character faces in the proper direction and performs a ‘walking’ animation. If a monster blocks the character during travel, the character will stop adjacent to the monster.

LOOKING AROUND The user can look around the dungeon by swiping the screen, and this can be done regardless of what the character is doing (standing still, moving, or attacking). The user can swipe to examine the entirety of the dungeon, though the camera will not scan further than the boundary of the dungeon. At any time, the user can immediately center the camera back on the character’s location by tapping the screen.

CHARACTER ATTACKING MONSTER If the character is adjacent to a monster, the user can tap on a monster to attack it (Figure 3). The character must be adjacent to a monster to begin attacking. Once engaged, the character will continue to attack the monster until the monster dies, the character dies, or the user directs the character to move to a different location. During the attack, the character will face the monster and perform an ‘attacking’ animation. Upon each melee round, the player has a random chance to hit the monster, and if successful, the monster loses some hit points. If the monster’s hit points drop to zero, the monster dies, and its sprite is removed from the screen.

Page 9: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

9

Figure 2 UML Use Case Diagram

Page 10: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

10

Figure 3 Combat Game Play Screen

MONSTER ATTACKING CHARACTER If the character moves to within a predefined distance from a monster, ten tiles, the monster will begin moving towards the character. When adjacent to the character, the monster will attack and continue attacking until the monster or the character dies. If the character moves away from the monster, the monster will continue moving towards the player as long as the player is within the predefined distance. During movement, the monster faces the proper direction and performs a ‘walking’ animation. While attacking, the monster faces the character and performs an ‘attacking’ animation. Monsters will not move through walls. When attacking, upon each melee round, the monster has a random change to hit the character, and if successful, the character loses some hit points. If the character’s hit points drop to zero, he dies and his sprite is removed from the screen. The character’s current hit points display on the screen will reflect any changes in hit points.

PICKING UP ITEMS If the character moves onto or through a tile containing an item, the item is automatically picked up. If the item is a potion, the character’s health is replenished to its maximum amount. Other items that are picked up are added to the character’s inventory. These items affect the amount of damage taken or received by the character when fighting monsters. When a player picks up an item, the item’s sprite disappears from the screen.

Page 11: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

11

ENDING THE GAME The player can end the game by dying or killing the boss monster (Figure 4). If the player’s hit points drop to zero, or if the boss monster’s hit points drop to zero, a ‘Game Over’ message is displayed on the screen (Figure 5). The user can then tap the screen to restart the game.

Figure 4 Boss Monster Screen

Figure 5 Game Over Screen

A video demonstration of RogueAndroid running on the Droid phone here:

https://code.google.com/p/rogueandroid/

ARCHITECTURE

OVERVIEW RogueAndroid is a single-player top-down hack-and-slash role-playing game, inspired by games like Rogue and Diablo, for mobile phones using the Android operating system. The user controls a character on a two-dimensional dungeon using intuitive touch gestures to move and attack

RogueAndroid is built on top of Rokon, an Android OpenGL game engine, which in turn is built on the Android OS framework.

Page 12: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

12

METAPHOR In order to provide structure and separation of concerns, we adopted a Model-View-Controller architecture (Figure 6). Unlike a traditional MVC implementation, we chose to reverse the normal Model/View dependency and eliminate the Observer design pattern.

This architecture can be thought of as being like the system around a Mars rover. The scientific community is the user. They communicate their desires to the rover ground control team (the controller), which is responsible for interpreting the user desires into specific rover commands. These commands are transmitted to the rover (the model), which interacts with the Martian environment based on the commands from ground control. The rover transmits back to Earth its measurements where a data processing team (the view) processes raw data and makes useful information available to the scientific community. Sometimes data passes directly from ground control to data processing.

RogueAndroid’s user communicates with the software through the Controller, which interprets touch gestures and passes information to the Model, and sometimes the View. The Model simulates the game world where the character travels the dungeon and fights monsters. Events that happen in the Model are communicated to the View so that they may be represented graphically for the user. In this way there is a separation of concerns between the packages. The Controller package has Controller classes to interpret user gestures. The Model package has Model classes to simulate the game world, and the View package has View classes to generate the display image.

Figure 6 Model-View-Controller Diagram

Page 13: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

13

STAKEHOLDERS Stakeholders generally fall into two categories: users and developers. The users are interested in an engaging game experience, and the developers are interested in creating that engaging game experience. Additionally, the developers are interested in well-factored and tested software that is easy to understand and to enhance. Furthermore, it is best when the game code does not need to be modified in order to make changes to the game. This leads to a data-driven design.

Note that many of the normal stakeholder concerns are not applicable here. Cost and time to market are simply not factors due to the nature of the open source software.

VIEWS An architectural view is a representation of an aspect of an architecture that addresses one or more concerns held by one or more of the stakeholders.

Functional View The Functional View looks at the structure of the software. In this instance, Model-View-Controller represents the structure of RogueAndroid. MVC addresses the Separation of Concerns concern of the developers.

Information View There are two halves to the information handling aspect of RogueAndroid that need to be addressed in the architecture. The first is driven by the data-driven concern of the developers. The obvious answer to meet this concern is to use configuration data to drive the function of the software. RogueAndroid uses an XML configuration file along with a textual file that represents the dungeon map. The “dungeon.txt” file uses a simple ASCII-map scheme to allow a developer to configure a dungeon map with any text editor.

Figure 7 dungeon.txt

Page 14: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

14

The second half of the information aspect is flow of data through the software. As previously mentioned, a Model-View-Controller structure is used, but without the traditional Observer design pattern. Instead, information flows from the top (the Controller) down to the bottom (the View) through simple method calls.

In the future RogueAndroid may address data persistence from one invocation of the game to another. Android does not support a normal file system.

Concurrency View Android provides each Android activity with a process and an initial thread. Applications (activities) are allowed to spawn new threads, but this is not required. RogueAndroid does not add any threads. All processing is carried out in the single thread provided. This eliminates any need for thread synchronization.

Performance View With all processing taking place in a single thread, it is important to avoid blocking that thread of execution. With the absence of a file system or any need for external communications, there are no blocking operations in the current version of RogueAndroid.

The next source of performance problems is computational. For the most part, the RogueAndroid algorithms are straightforward and simple. Graphics algorithms always have a potential to cause performance issues. All of the graphics work is, however, done in the Rokon game framework. RogueAndroid supplied a tile engine to the Rokon code base, and that tile engine uses the OpenGL libraries to efficiently render the game map visible on the screen.

PRINCIPLES A software architecture addresses the “ilities” such as usability, reliability, evolve-ability, and performance. Not all of these aspects can be captured in a view of the architecture. Some are addressed through the use of guiding principles. The following paragraphs name and explain the core principles used in the development of RogueAndroid.

Enjoyable Game First and foremost, a game is supposed to be fun. It does not have to be intellectually challenging or even complex; it just needs to provide a challenge in an entertaining way. RogueAndroid strives to do just this. A game is not fun if it is difficult to use or if it is difficult to understand.

Data-Driven Design In order to enhance the ease of changing the game, parameters are read in from a configuration file instead of hard-coded in the source code.

Ubiquitous Language Terms used when talking about the game are also used within the source code. This enhances readability and understandability of the design.

Page 15: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

15

Test-Driven Development While it is a challenge to create and maintain unit tests for the source code, there is a clear benefit when it is time to refactor the code. Therefore Test-Driven Development is a guiding principle to help enhance evolve-ability of the code.

Dependency Injection Dependency Injection directly supports Test-Driven Development by purposefully designing the code to be separable into stand-alone classes. By coding against an interface instead of an implementation of another class, that implementation can be replaced in a test environment. This also sets the conditions for a compose-able, and therefore evolve-able, program. For instance, a preliminary tile engine was created to get the project going, and over time a high-performance tile engine was built to replace it. The change from one tile engine to the other was accomplished by modifying a single line of code where the tile engine was injected into the game.

Separation of Concerns This principle is a leading reason for the choice of Model-View-Controller. By separating control of the game from modeling the game and from viewing the game, the code for any aspect can focus on a limited amount of complexity. This contributes to simplicity, understandability, reliability, and evolve-ability.

Component Based Design In the future, the plan was to use a component based design to aggregate capabilities into central classes like Character and Monster instead of creating a deep inheritance structure. This will simplify the overall structure of the code while providing a powerful and flexible approach to distinguishing between different “types” of characters and monsters. The Type Object pattern can help implement the component based design principle.

DESIGN

OVERVIEW The main concerns of the system’s design are the details of the Model-View-Controller architecture and the data-driven design.

MODEL The model is a representation of RogueAndroid’s application domain data (Figure 8). It also provides an interface with the controller to determine access to the data and how the data will be updated. The model is an approximation of the fantasy world in the game. All of the model classes are located in the rogueandroid.cs428.sp10.model package. Most of the model classes have an onGameLoop method to process updates to the models. The main components of the model are the Dungeon, Items, Entities and Actions.

Page 16: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

16

Figure 8 UML Model Class Diagram

Page 17: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

17

Dungeon Like a real life dungeon, the Dungeon class contains the map for the game and keeps track of the entities’ and items’ locations. Dungeon is instantiated in the onLoad method in the Game class. It is a data driven class in that the DungeonReader class parses the map of the Dungeon from the dungeon.txt file located in the /resources/raw folder. Blocked tiles are represented as ‘#’ and open tiles are represented as ‘.’ in dungeon.txt (see Figure 7). The map is stored in a matrix in the dungeon instance. The data driven design allows the maps of the game to be easily designed and updated, and it is easy to see what tiles are opened or closed by simply looking at the dungeon.txt file. After the dungeon object is instantiated, it is populated with items and entities. The Dungeon provides an interface for registering and getting items and entities. Item and entity objects are stored in respective Java ArrayLists. The onGameLoop method checks for dead entities and marks them for removal from the Dungeon. Overall, the Dungeon is necessary so that entities can efficiently discover where other entities are located and so that the character knows where the items are located and can pick them up.

Items Items in the game represent fantasy world items like potions, scrolls, swords and helmets. The items have unique attributes that increase the character’s ability to win the game. Items are created by an ItemMaker class in the onLoad method of the Game class. The ItemMaker class loads the item data like attack and defense bonus from the Config. After an item object is created, it is registered in the dungeon object.

Entities Entities are the most interactive part of the user’s experience. Entities are both the character and monsters which are similar enough to each other to have a Java interface class, Entity. The most significant difference between the two is that the character is controlled by the user while the monsters are controlled by a simple artificial intelligence. All entities inherit from the EntityClass which implements Entity. EntityClass handles actions for the entities in the onGameLoop and much of the other functionality of entities related to actions.

Character The character is the user’s agent in the game in that the character follows the commands of the user. The Character class is the representation of the character and is instantiated in the onLoad method of the Game class. The character object is then registered in the dungeon object.

Monsters Monsters are the enemies of the character and have their own class, Monster, which inherits from the EntityClass. Like the items, the monster objects are created with a MonsterMaker class and are then registered in the dungeon. The monster objects load their information from the Config. Monsters are different from the character in that they have their own AI, which is performed in the executeAI method. A monster will only travel to the character when it is within ten tiles of the character. The monster will then attack the character when it is next to the character.

Page 18: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

18

Boss The boss uses the Monster class like monsters but has slightly larger sprite to emphasize that it is the boss. It also has significantly higher data driven hit points, attack points and defense points so that it is more challenging than other monsters.

Actions The Action interface is implemented by AttackAction and TravelAction which are responsible for changing the state of the model. They are the Model’s interface with the Controller. Actions are set on entities whose onGameLoop methods call the onGameLoop methods in the actions. If a travel action is set on an entity, it will pick a step towards the destination (Figure 9). If the step is not obstructed, the entity will make the step. This will continue until the entity reaches its destination.

Figure 9 UML Travel Action Sequence Diagram

Page 19: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

19

An attack action has an attacker and a defender (Figure 10). A random number between zero and nine is generated and added to the attacker’s attack bonus which is subtracted from the defender’s defense bonus. If the number is greater than zero, that attack occurs and the defender takes the damage. If the defender’s hit points reach zero, the attack action ends. This is a simple attack algorithm, but it produces a playable game. The defender is removed from the dungeon when it dies and its displayable representation in the View is removed.

Figure 10 UML Attack Action Sequence Diagram

VIEW The View displays the game objects from the model (Figure 11). The View classes are located in the rogueandroid.cs428.sp10.view package. The significant parts of the view are the View, TileEngine, and Displayable classes.

View

Page 20: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

20

The View class is responsible for preventing the screen from scrolling when the edge of the map has been reached by a swipe and updating the screen location of the displayables when the screen is scrolled. The view object is instantiated in the onLoad method of the Game class. The displayable entities and items are added to the view with the addDisplayables method. The view’s on onGameLoop method is called in the onGameLoop method of the Game class. This effectively keeps the displayable entities and items attached to the map when it’s scrolled by calling the update method in the displayable entities and items to change their screen locations. When the screen is scrolled, the clipScrollX and clipScrollY methods are called to prevent the screen from scrolling beyond the bounds of the map.

Figure 11 UML View Class Diagram

Page 21: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

21

Displayables Displayables are the graphical representation of the model. The Displayable class is an interface that is implemented by DisplayableEntitiy, DisplayableItem and DisplayableText. All of these classes are responsible for their respective screen locations and animations.

The DisplayableEntity class displays the character and monsters on the screen. Displayable entity objects are instantiated after its respective model is instantiated. The DisplayableEntity class loads the path for the PNG and tile size from the Config. Then it creates the texture and sprite using the Rokon framework. After the sprite is made, the screen location of the sprite is set. DisplayableItem and DistplayableText function in a similar manner but they do not have animations, and DisplayableText creates a Rokon Text with a font instead of a sprite with a PNG. The use of the Displayable interface follows the Dependency Injection principle and allows the use of a mock Displayable for testing other classes.

TileEngine The TileEngine class displays the map, a set of tiles, for the game and scrolls the map. It is an interface because two engines were used during the project: a sprite based engine and a hardware accelerated engine. The interface was made to facilitate the switch from the sprite based engine to the hardware accelerated engine, and to simplify testing classes that interact with the tile engine by using a mock tile engine. TileEngineBackground is the hardware accelerated engine and implements TileEngine. It is instantiated in the onLoad method with the tile size and textures for walls and grass from the Config as well as the dungeon matrix for the map. TileEngineBackground creates ScrollingTiledBackground, our contribution to Rokon. ScrollingTiledBackground generates on OpenGL, hardware accelerated background from a tile set. Only the tiles for the portion of the map that is on the screen are drawn by the engine. When the map is scrolled, the tiles are redrawn accordingly. This greatly increases the performance of the game.

Animations The Animation class is an interface implemented by the TravelAnimation and AttackAnimation classes. Animations in the sprites are handled by Rokon. The TravelAnimation and AttackAnimation classes tell Rokon on what frames to start and stop the animations in the sprites.

CONTROLLER The controller translates the user’s interactions with the screen into an action to be performed on the model (Figure 12). User interaction is restricted to touching and swiping the screen. The Controller classes are located in the rogueandroid.cs428.sp10.controller package. The classes in the controller, Controller and Touch, set actions in the Model and scroll the View.

Page 22: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

22

Controller and Touch The Controller class is responsible for handling the user’s touches on the screen (Figure 13). Touch events start in the Rokon game engine object and propagate through the RogueAndroid game object to the controller object. A touch event will call the onTouchDown method where the location of the touch is set and an instance of Touch is created. If the user continues to touch the screen, onTouch is called. Then, Touch calls checkSwipe to determine if the user is swiping the screen. If so, the scroll method is called in the view object. When the user lets go of the screen, onTouchUp is called. If no swipe occurs and the user has touched an empty tile, the travel action is set on the character. If the user touches a monster, the attack action is set on the character. Occasionally onTouch and onTouchUp are called without onTouchDown being called. The controller object handles this by creating instances of Touch if necessary.

Figure 12 UML Controller Class Diagram

Page 23: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

23

Figure 13 UML Touch and Scroll Sequence Diagram

Page 24: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

24

Figure 14 UML Game Startup Diagram

Page 25: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

25

MISCELLANEOUS Outside the MVC packages are a few classes that are used to support the entire game.

Coordinate Systems RogueAndroid uses three coordinate systems to track locations. All three coordinate systems inherit from the Coordinate class. DungeonTileCoordinate represents the tile coordinate system of the game world (the large squares seen in Figure 15). DungeonPixelCoordinate is fixed to DungeonTileCoordinate and represents pixel locations relative to the tile coordinates (the small red squares in Figure 15). The tile size is defined in the configuration file, but is nominally set at 96 pixels. ScreenPixelCoordinate uses the same scale as DungeonPixelCoordinate, but it floats relative over the dungeon and represents the part of the game world that is visible through the display (the small blue squares in Figure 10). All three coordinate systems start at (0, 0) in the upper left hand corner. Positive X is to the right and positive Y is down.

Figure 15 Coordinate System

FUTURE PLANS This project has been developed by members of graduate and undergraduate school and this was a final project to be graded by software engineering course teaching assistants. The members’ priorities are indeed to get a good grade, but some of the members have a passion to continue work on this project even after the class has ended. This RogueAndroid game will be uploaded to Google Code in order to share this with other developers that have an interest to continually work on this game and possibly put more functionalities and aspects to the game. To date, this is the most sophisticated game that uses Rokon.

IMMEDIATE EXTENSIONS We accomplished our goal for this project during the semester by completing a basic structure of the game with the ability to move around, fight monsters, collect items, and win by killing a boss

Page 26: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

26

monster. However, some of the features have minor bugs or incomplete implementations, but they do not ultimately affect game play.

Auto scrolling of the screen when the character moves near the boundary of the dungeon has some minor errors, and opening up inventory window to manage the inventory has not been completed yet. The data driven design is not complete in that the character’s information is still hard coded as well as some of the start up screen data. There are also some inconsistencies in the x and y coordinates used in the dungeon and throughout the game.

Another immediate extension includes improving the monster AI. A monster should only travel to the character if it can see the character, in other words, if the shortest path to the character is not blocked. The monster would then attack the character when it is next to the character. If the monster’s health is critically low, it should start to flee. These design decisions were made to make the monster’s behavior more representative of the real world.

Other extensions include adding more levels to the game and increasing the functionality of the items, inventory and different character classes.

We leave all other extensions of work for high-level goals for future developers and current members that choose to continue to work after the class ends.

HIGH-LEVEL GOALS Beyond integrating this game with actual Android phones, there are other future development such as putting NPCs to the game so that player can accept and accomplish quests that are given by those NPCs and multiple players can play in one dungeon map using wifi and 3G technologies that Android phones provide. Functionality extensions can be made easily since the structure of game is well organized and each part of game is well defined.

The final goal of this project after the class is to complete all features of the game and release the application on the Android market to users of Android phones as an application. This project can be provided with no-charge to the Android Market, and members of our group think that this is not a far away future. After the release, developers can continue work on fixing bugs that are found by the game users.

PERSONAL REFLECTIONS Drew Glass RogueAnroid has been an exceptional project from the start to the finish. As a team, we had several things working against us: physical distribution, an unfamiliar development process, and a new application platform. This was my first time working ona project with such a large geographical distribution: Pittsburg, PA to Korea. I believe that we were successful despite this because of online meetings and the wiki. We were able to have online meetings where we could talk to each other and share screens. This allowed us to become familiar with each others voices. This resulted in us being able to instill a certain amount of trust in each other. The wiki also helped us mitigate the challenges of distribution. It was much easier to keep track of what was going on in the project by

Page 27: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

27

recording the project information on the wiki rather than email. The wiki provided a structure to the information as well as real time documentation and project transparency.

Before the project, none of the group members had worked with the XP process. This had the potential to cause many problems with the project. Also, at the same time, we were learning the process in class. Overall, the class requirement to “stick to the XP process and make requests to change it” helped us be successful. If at the beginning we did not have that structure and had the opportunity to choose our own process, it could have taken much longer to get the project off the ground. But since we had a process to follow right away, we could start developing immediately when the project started. After a couple iterations, we found parts of XP that were not really working for us. Because of the distrubuted nature of our team, it was much easier for us to tweak the planning game rather than strictly follow the XP planning game rules. This lab like nature to the XP process made it a much more enjoyable experience as well as a successful experience.

I think what attracted people to this project is the exciting nature of Android. Right now in the mobile device world, it’s at the cutting edge of technology. This was a good opportunity for us to learn about Android in a structured environment with elements of self pacing. But having all of the team members learning a new platform on a short schedule project can be disastrous. At the sametime, adversity can bring out the best in people. I think that most of the group members came into the project looking for a challenge and were willing to put in the hard work, because they knew that there would be a pay off. During the project, we ran into many problems with the platform that were only solved by team work. I personally learned a lot about the importance of being able to rely upon new team members to ensure progress and build trust.

Josh Glovinksy The RogueAndroid project was very exciting learning experience. Before starting this project, I had little java experience and no Android SDK experience. At this point I now feel comfortable enough to develop applications using both java and the Android SDk. I was blessed to be teamed up with a great group of programmers where I could learn new concepts at an exponential rate. Having experienced developers on the team who were willing to expose others to proper coding techniques was key to my growth as a developer this semester. I was truly impressed with how successful the project ended up being and I look forward to continuing development on RogueAndroid as an Open Source project.

Hyun Soon Kim Not only the project itself was successful but also interactions with other group members were exceptionally successful while continuing work on this project. It was such a great experience to make game architecture based on Android SDK and every one of group members developed his implementation skills in both coding style and architecture. I strongly believe this fact since I am the one who contributed in this project the least and still got lots of development of my skills as a software engineer. I would like all of the group members to continue work on this even after the class ends but this will not happen since everyone has his own schedule to continue.

Page 28: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

28

I am thankful to all other group members who contributed their effort to this project and I hope this project can be continuously developed by future developers including myself.

David Kristola Many of the projects I have contributed to professionally involved collaboration with colleagues in different locations, occasionally over time zones, and sometimes across company boundaries. This class project has not been representative of any of my past experiences; it has been much harder. Spare Time Development imposes a very unique set of ground rules on the process of completing an assignment.

That said, somehow we managed to arrive at this point with a product that we can demonstrate. Communication has been a major challenge. As Dr. Alistair Cockburn points out, the discussion at a white board between two people is a very high-density form of communication. Remove the instant feedback, the unspoken body language, and the graphical representations, and you are left with a very low-density form of communication. And then there are the gaps that must be bridged. Communication is about conveying the essential information while skipping over already-understood information. But what information can safely be assumed to be “already understood” information? This project has shown me that I still have plenty to learn about communicating. I just hope that I have improved those skills by some measure.

With the hard work of my fellow team members, we have managed to produce not just a class project deliverable, but also a good foundation for a future Android application. Given more time we could make it better, but time has run out. That is the fate of all software projects.

Michael Lai I believe that this was a very good opportunity to learn about the Android platform in a team setting. None of us had prior experience with Android, but other members of the group were Java or mobile veterans which helped immensely with the development process. I believe that the group made an excellent choice in using the Rokon game engine, so we didn't have to start a game from scratch. Our process dictated that we develop a quick tile engine based upon the sprites for a spike, and then another based upon the Rokon background which would take multiple iterations. The initial tile engine was completed relatively quickly, but mine took three iterations to complete. Therefore we developed the tile engine in parallel and to accommodate this, the group implemented a tile engine class that could easily switch to mine once it was completed. The development of my tile engine was very challenging since it was not built into the Rokon engine, and I had to extend the existing Background system and research how existing tile engines were created. There was some documentation on the web regarding how to make an OpenGL tile engine, but none that would be OpenGL ES and would work on the Android platform. So my first experience diving into OpenGL programming was daunting, and there is not great documentation on how to program in OpenGL ES out on the web. However after spending lots of time experimenting with code and reading the OpenGL documentation out there, I managed to create a rather simple Tile Engine based upon textures. I am pleased that I know a little more about two dimensional OpenGL ES programming, but at the same time know I only used a fraction of the API methods that are available, and maybe one day will buy a book to finish what I started. The

Page 29: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

29

combination of pressure to succeed with support from my groups, resulted in the background engine working as great as it does. My only regret is that throughout the project I really only focused on my small part of the project, and had to spend most of my time and effort developing and fixing bugs in the engine, and not spending much time developing any other major component. I would like to commend my other group members for their great efforts in developing the other major portions of the game.

Henry Millson A geographically distributed team with no platform experience and an unpredictable work schedule would seem to be able to produce nothing of any value. But that ignores the extra effort of people dedicated to success. The team helped a teammate who was lightly engaged, encouraging them to contribute right up to the time that person dropped the class. On teammate signed up to be project manager, and did that job in additional to a full load if coding duties. The team couldn't figure out how the game engine worked, so someone wrote a spike to demonstrate it. The team founder took on a visionary role. Another person donned an architect hat. Another spent time on the user stories. We shared testing, fixed each other's bugs, shared the problems, and celebrated the success. And most of us have not, and will not, ever meet. You can't credit agile development methods or test first programming or exceptional hiring practices alone for this. It was commitment to making the project a success that led to the first working rogue-like game on Android. That development process stuff may have helped, too.

John Svitek This has been an incredibly challenging project to bring to fruition. I found it very impressive that we were able to stick to our original vision of the game and realize it with very few things being cut due to time restraints. We were fortunate to be using the XP process, because without the hard time limits that the various milestones placed on us, we probably would have lost focus sometimes. There were several issues that came up, not the least of which was trying to begin work in an unfamiliar system (Android) and using an unfamiliar framework (Rokon) that was missing the functionality we really needed. Throughout the development, problems such as extreme difficulty with running unit tests continued to pile up, culminating in the loss of one of our team members. However, through it all, we remained dedicated to the end goal of a real, playable game, and through a lot of hard work we were able to achieve that goal. Under the hood, the game has a beautiful architecture and will provide a strong foundation for future development.

The most important thing to come out of this work was proving the viability of Rokon for a real-time Android game. I have a personal interest in this project, and would like to see development continue, and if it does I would try to be a part of it. Regardless, I plan to take the code and begin a personal project with it.

Page 30: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

30

APPENDIX

HOW TO INSTALL ECLIPSE AND THE ANDROID SDK We recommend using the Eclipse platform to install RogueAndroid for development purposes. The latest version of Eclipse can be downloaded at http://www.eclipse.org/. Here is the link that explains how to install the Android SDK and ADT Plugin for Eclipse:

Android SDK installation guide - http://developer.android.com/sdk/index.html

ADT Plugin Updating guide - http://developer.android.com/sdk/eclipse-adt.html

After finishing the above steps, please make sure to create an Android Virtual Device with 2.0.1

version in order to run this program using Android emulator. The icon will be listed on the menu of Eclipse and when clicked, a window named “Android SDK and AVD Manager” will pop up. Use this window to set up an emulator with various memory sizes and versions of Android SDK.

INSTALLATION OF THE ROGUEANDROID SOURCE FILES The RogueAndroid source files can be imported by SVN into Eclipse. SVN does not come with Eclipse. The prefered plugin for SVN on Eclipse is Subversive. A good tutorial for installing it is located here. After the plugin is installed, a new project from SVN repository can be created using this repository: https://csil-projects.cs.uiuc.edu/svn/sp10/cs428/RogueAndroid/trunk/. Another project from SVN repository should be created for the testing suite: https://csil-projects.cs.uiuc.edu/svn/sp10/cs428/RogueAndroid/projecttest/trunk/. After the class, the sources for the game and testing suite will be moved to https://code.google.com/p/rogueandroid/.

INSTALLATION OF OTHER FILES FOR DEVELOPMENT All required libraries such as Rokon and xStream are in the game’s package so that no additional installation is necessary to run the game.

PLAYING AND DEBUGGING THE GAME The game can be played by right clicking on the RogueAndroid package in Eclipse and selecting Run As > Android Application. A run configuration can be set by right clicking on the RogueAndroid package and selecting Run As > Run Configurations. This option gives the abilitiy to set different parameters for the emulator when RogueAndroid is run.

RogueAndroid can be debugged with the logcat feature in the ADT plugin. To see the logcat output of system messages in Eclipse, select Window > Show View > Other >Android > LogCat. Rokon has a Debug class with a print method that can be used to output messages to the logcat. Debug statements should be removed before the product is released to users. The debug function can reduce performance.

INSTALLING ROGUEANDROID ON AN ANDROID DEVICE The RogueAndroid application has not been signed with a private security certificate yet, and as such it cannot be installed using Android's Market or third-party app installers. The application is

Page 31: ROGUEANDROID - Salisbury Universityfaculty.salisbury.edu/~stlauterburg/COSC426/FinalReport...1 ROGUEANDROID A Diablo inspired role-playing game for Android University of Illinois CS

31

signed with the default debug certificate, allowing it to be installed on real hardware using the Android SDK toolkit. RogueAndroid can be installed on any device that supports Android 2.0 or newer.

1. Install the Android SDK located at http://developer.android.com/sdk/index.html

2. Install the latest Android USB driver by following the instructions at http://developer.android.com/sdk/win-usb.html. It is vital to follow the instructions carefully, as by default Windows will install a basic driver for an Android device that can use it as a mass storage device, but does not allow access to the operating system. By using the appropriate Android USB driver, the Android SDK can install applications on the device and use it as a debugging target.

3. Connect the Android device to the Windows computer. On the Android device, pull down the notification bar and ensure that USB debugging is enabled. If it is disabled, tap the debugging section and enable USB debugging.

4. Open a command window and navigate to the /tools directory in the Android SDK. Run the command: adb install <full path of RogueAndoid.apk>

5. RogueAndroid will be installed on the device, and can run as a normal application, even without the USB connection active. While connected, the application can also be debugged directly from Eclipse by choosing the Android device as the debugging target.