Categories
Game Design Game Development

Stop That Hero! Mid-January Progress Update

The last major progress update for Stop That Hero! was in November (see Stop That Hero! November Development Summary), so I thought I’d post about my progress since then.

Between moving, prepping a new office, unpacking, and not realizing how much time was passing, I messed up my project management duties in December. Combined with Christmas and family time, there is very little to report, and I finished 2010 weakly.

January, on the other hand, is looking much better. Here’s an outline of the things I’ve worked on in just the last two weeks:

  • Integrated pathfinding system with game.
  • Created Command system to populate game world with game objects.
  • Updated level definition.
  • Re-architected the rendering system.
  • The Hero can clear towers!

Let’s dig into the details!

Integrated pathfinding system with game

The nature of working with unit tests is that a lot of features get implemented in a vacuum. The code you’re test-driving is interacting with interfaces implemented by mock objects to see if specific, isolated examples run as expected.

Sometimes surprises occur when the new features are integrated with the rest of the production code.

The pathfinding system was one such feature. Everything technically worked, but when using real data, I realized there was a problem.

In my unit tests, I would check if the path gets updated when an entity was at an exact node location.

In the game, the exact center of node (10, 10) is at position (10.5, 10.5), and I didn’t realize how it would look when an entity moved to node (10, 10) by trying to get to position (10, 10).

Even when I got things working and looking correctly, I found a problem. An entity moving through a long path would eventually miss its next target node and continue moving away in the same direction it was last moving. It was a precision problem. Again, an entity was rarely at an exact node location. The entity might be a little further away. Eventually the extra precision adds up to being completely off target.

To fix it for now, I just force the entity to jump to the exact center of a node once it reaches near it. It’s a little jumpier than I would like, but the entity is never allowed to lose precision and be off path. I can correct it later, perhaps with a better implementation for movement, but for now, pathfinding and movement is functional enough.

Created Command system to populate game world with game objects

When a level was loaded, it would make use of an image like the following:

The Tile Map

It’s blown up to make it easier to see, but the real data is a 50×33 PNG. Different colored pixels would represent the terrain, and I also used the pixel color data to create the towers, treasure chests, and hero’s starting spawn point.

However, level-loading time isn’t the only time objects can be created in the game. During a game, the player can create monsters, for instance, and I’m interested in the idea of letting the player create towers instead of being handed them at the start of a session. Also, it was awkward to have the level loader code know so much about all the different kinds of objects that could be created. There was a function to create the Hero entity, and I didn’t like the idea of lots of functions for each type of game object to create.

So I created a Command system. I suppose most game developers call them Events, but the point is that I pushed the responsibility of creating game objects to self-encapsulated pieces of code that can be created and passed around.

So now when the level loader pulls in object data, it requests commands depending on the data. For example, a white pixel specifies a basic Tower, so it requests a CreateTowerCommand. When that command is executed, the game world has a fully functioning Tower.

If I allow the player to build towers or if there is any reason why a tower should get built after the game session starts, it’s a simple matter of requesting a CreateTowerCommand.

It’s pretty powerful stuff, and I wish I had thought to do it long ago! I have commands to create the Hero entity, the towers, the castle, and treasure chests, and as new features get added, I find this command system provides an easy way to centralize and encapsulate certain activities.

I’m sure there are ways to improve it, but for now, it’s working well.

Updated level definition

If a tower is represented by a white pixel, by default the terrain around it is defined by other pixels. A tower spans multiple tiles, but the pixel’s location defines only the entrance of the tower. How do I get the terrain around the tower entrance to act like obstacles?

In the end, I didn’t solve this problem yet, but in trying to, I realized something wrong with my level definition. I was trying to use a single piece of data to define two different things.

I took the level PNG and split it into two. One PNG defines the terrain, and the other defines the objects that should exist in the level. In the image above, the white, red, black, pink, and yellow pixels are in a separate PNG associated with the level.

At the very least, now it is easy to define what the terrain around a tower looks like without worrying about the ability to define the location of the tower. I suppose I could have used the same image in a different way, but again, this works for now.

Re-architected the rendering system

At some point, I realized early architectural decisions were making it hard to separate the player’s interface with the game from the game. While I managed to get the game simulation well structured and easy to work with, I had a messy implementation for rendering, and I had no easy way to implement a UI.

I explained how I got sprites rendering in the correct screen locations based on their in-game world position in Stop That Hero! Sprite Rendering Questions, but the problem is that the sprite objects were mixed into the game’s object model.

Now, imagine switching resolutions on the fly. If the sprites are all there, they have to be replaced by more appropriate sprites. And rendering requires an updated viewport to deal with the new screen resolution.

Now, what does the simulation care about how it’s being rendered? Nothing! Or at least it shouldn’t!

It took a bit of refactoring, but not a lot. I was able to leverage what I had to get to a new solution.

I now have a concept of a View. Now, I’ve looked into Model-View-Controller, and quite frankly, I didn’t think it worked very well for what I was trying to do. This isn’t a simple application with buttons and a database.

But I did like the idea of a separate view and something to process player input. The input processor is still missing, but there is now a View that handles rendering using data from the game world but without being part of the game world.

Or at least, it will. Right now, Sprite data is still part of the entity, and I’d like to change it so that the View worries about Sprites while the game objects have RenderableComponents which merely describe what Sprite the View should get. So if a Tower has a RenderableComponent that says “Use TowerSprite”, then the View can get TowerSprite out of the 800×600 sprite collection or the 400×300 sprite collection, depending on the View’s resolution.

The Hero can clear towers!

For some time, the Hero had the ability to target Towers, find a path to the nearest Tower, and move to it. But then he’d stand there. It was still the nearest target.

It didn’t take me too long to implement a way for the Hero to change the Tower’s target status. Basically, the game had to detect that the Hero was in the Tower’s entrance, and then it requested a ClearTowerCommand. That command will get more code eventually as more features are added to the game, but for now, it takes the Tower’s Targetable component and deactivates it.

Now, the Hero moves to a Tower entrance, and then he searches for the next nearest Tower until there are no more left. While the implementation details could use some cleaning up, this mechanic is such a central part of the game, and it’s great to finally see it in action again.

Conclusion

My last two weeks have been quite productive, and I wish a screenshot could show it, but most of the work is under the hood. Still, simple infrastructure work has already paid off in implementing some game mechanics more easily. I’m pleased with my recent progress.

Categories
Game Development Games Geek / Technical Marketing/Business Personal Development

I’m Going to the GDC (FINALLY)!

I finally purchased a Game Developers Conference pass for the first time!

After years of having to hear about the conference and the summits and the talks and the panels and the awards and the parties after the fact, I am actually going to be a participant!

Now I’ll get to attend the Indie Games Festival!
Now I’ll be able to meet game developers and journalists in-person instead of merely through IRC, Twitter, or blogs!
Now I get to be snubbed by major game developers when they hear I’m an independent game developer!

There were always excuses not to go in the past, such as not being able to request enough time off from a day job or not having the money. And the cost for registering for the pass, booking a plane, and staying at a hotel for a week was a big obstacle.

And cost was still a major stumbling block for me. Until I can make some income on a regular basis, I’m trying to be very careful with how I spend my money.

So how did I justify the massive expense this time?

For one thing, I have a friend currently residing in San Francisco who said I can crash at his place. No need for a hotel now!

Now, the GDC pass was tricky. I could have saved a lot of money by getting an Expo pass, but I wouldn’t be able to participate the entire week. Getting an All Access pass was prohibitively expensive. I opted for the Summits & Tutorials Pass since it seemed to offer the right balance of access and cost. While I won’t be able to attend a number of events, I will be able to go to tutorials and the Independent Games Summit.

Still, it wasn’t chump change, and I still had to book a flight.

My decision to pay so much at this time was based on a few thoughts:

  • I can technically afford to go, and I might be too poor to go next year if my income level doesn’t change from $0.
  • I can finally meet people who are involved in the industry, whether peers or mentors. My involvement has almost always been virtual. At least in Chicago there was the IGDA chapter, but the local game developers tended to be inactive, and they seem to drop like flies.
  • I hear it is an experience.

So, bottom line, I’m going because it is a huge opportunity for me to be more involved in my industry and get to meet other participants.

I’m really excited. I’m actually going to be at GDC, and I’d love to meet you!

Who else is going to GDC?

Categories
Game Design Game Development Marketing/Business Personal Development

Six Months As a Full-Time Indie

Mike Kasprzak wrote about his five years as a full-time indie, and it’s a fantastic read. Especially fascinating was how long it was before he made Smiles and his first real income. After years of burning through savings, suddenly things came together for him, and he was winning prizes and being pretty awesome.

In contrast, I’ve been running my business officially for almost five years, but I’ve only been full-time since the end of May. On the one hand, that means my story won’t be nearly as fascinating or interesting as Kasprzak’s, but on the other hand, existing part-time indies aspiring to make the jump to full-time might appreciate reading how things look for me in the short term.

I wrote about some of the reasons why I went full-time indie, but part of it was freedom. Spending 40-60 hours a week on stuff unrelated to my business meant I was giving my business short shrift. I spent so many years learning about game development, but I could only dedicate a few spare minutes to actually doing it? It wasn’t right. So I quit the day job.

Ah, Freedom!

Did I hit the ground running? No. The World Cup was starting, and I was going to watch as much soccer as I could!

I was even writing about it at my new website, Modern American Soccer, which actually got quite a bit of traffic in the weeks leading up to the first game due to the US Central-time specific calendar I created on Google. In fact, that site was going to advertise the soccer-based social networking game I was going to create with a colleague before that project fell through, so it was related to my games business initially.

Either way, my first month as a full-time indie game developer was spent getting used to not having a day job to worry about. I knew that it meant a month of spending my savings with nothing to show for it, but I decided at the time that it was acceptable. I was taking a break and getting my bearings (and watching soccer).

Now What?

When I finally sat down to do real work related to my business, I found it frustrating to not know what I was doing at any given moment. Not knowing when my next infusion of income was coming from made me feel a bit antsy, and yet I felt a bit overwhelmed by the number of different tasks to accomplish. I wrote about how it felt in the article Clear Goals or Trivial Pursuits, and I realized I needed to define some specific goals to tackle, or at least pave the way to learning what those goals should be.

In July, I hosted MiniLD #20 with the theme Greed and the special rule “Only One of Each”, which was meant to discourage people from reusing content and code. It was one of the more successful MiniLDs, with plenty of submissions, but my game wasn’t one of them. My project, The Old Man and the Monkey Thief, was the first game development project I started since quitting the day job, and I didn’t finish it in time.

Inventory and Treasure!

It was the first game I’ve made that involved a scrolling screen, and I remember feeling incompetent. How can I have thought that I could be a full-time indie developer when I didn’t even know how to make a game with something as basic as a scrolling background? It was a scary thought. Had I made a huge mistake? Was I not as prepared for making a go at a game development business as I thought I was?

Again, one of the reasons why I went full-time was so I could dedicate many more hours towards my games. If I felt incompetent, it is because I didn’t spend nearly as much time on it as I should have, and now is my chance to do otherwise.

Setting Monthly Goals

I decided that August would be the month that I would try to complete three small games in an attempt to learn as much as I could as quickly as I could.

My first project was my MiniLD game, which was taking me much longer than I expected, partly because of how unique everything had to be in the game. I didn’t finish it until right before Ludum Dare #18, and I didn’t feel it was worth releasing.

My second project was my LD #18 project, Stop That Hero!, which involved the most complex AI I’ve ever implemented. That is, I’ve never implemented pathfinding algorithms more complex than “go directly from point A to point B”, and in The Old Man and the Monkey Thief, I learned that there was a lot of problems with a character that couldn’t avoid obstacles well. Stop That Hero! took me three days to finish, but I was fairly pleased with how it turned out and wanted to flesh it out later.

Stop That Hero! is finished

I never did make a third project.

Still, two finished games in a month taught me a lot, and I was getting feedback from friends and colleagues. Even though I failed my August goal of making three games, I made good progress towards it and learned plenty.

Unfortunately, September started without goals set for it. In order to figure out what my goals should be, I spent a good chunk of the first week or so figuring out my options as an indie game developer. I thought it would take me a night to write down the options, but then I thought I could write up an article or two for ASPects, the Association of Software Professionals newsletter. It ended up being four full length articles, and it took me almost the entire month before I submitted all of them. If you’d like to read the articles, for now the only place they’re available is in the ASP members-only archives.

I also caught up on some reading. Business articles, audiobooks, and other literature were consumed. I would highly encourage anyone starting a business to read The E-Myth Revisited. For a long time I ignored it because I thought the E- part of the name meant it was a book about how Internet-based companies aren’t get-rich-quick schemes. I didn’t know it was a book about why most small businesses fail and what you can do to succeed.

Anyway, I spent the latter half of September analyzing the heck out of Stop That Hero! and trying to figure out what design directions to take it in. This time coincided with the creation of an organized daily schedule. It gave me some much needed structure, and I felt much more productive and focused, and I didn’t feel like I was letting anything fall through the cracks. I had time for writing, reading, organizing, and most importantly, game developing.

The October Challenge

While I wanted to flesh out and sell Stop That Hero!, I was having difficulty figuring out out how long to allow the project to run. I didn’t want to put together a skimpy game in a matter of weeks. Who would pay for it? And I didn’t want to spend six months working on it since that would be half of my burn rate. I don’t want to spend all of my savings on one game, and I don’t want to put together disposable games. I learned that Flashbang Studios used 8-week projects, but they had entire teams working on their games. Did I need longer? Could I afford to take longer?

Then Mike Kasprzak announced the Ludum Dare October Challenge, and I had my deadline. Make a game and sell it by the end of the month? I could do that! It took me only three days to make the prototype, so a full month should be plenty of time to make Stop That Hero! with multiple campaigns and different game modes. Right?

I wrote an October Challenge post-mortem, but suffice it to say that I didn’t get the game finished in time. Read the post-mortem for more details about what went right and what went wrong, but one of the biggest problems was not realizing how much technology I didn’t have to leverage.

Hacking a dinky game together virtually from scratch in a weekend is one thing, but making a full-scale game requires a lot of infrastructure and technology that I didn’t have. Rather than go without, I did research and development, which took up a lot of time. Tracking entities and game objects in a way that didn’t require a ton of dependencies was surprisingly difficult, and I wrote about my difficulties in implementing a component-based system in State of the Art Game Objects.

Of course, developing infrastructure is not developing the game. It’s just laying down the groundwork for a game. Kasprzak took time off to work on a framework after PuffBOMB HD, but it sounds like a lot of it was already in a game and he was cleaning it up and improving on it. While I had some prototype code, a lot of it needed to be reimplemented. Stop That Hero!‘s pathfinding algorithm was fairly hacked together, leaked memory like crazy, and required a few other algorithms to compensate for when it wouldn’t work well on its own. The new version is less dependent on knowledge of the entities moving through it and works very well, but it took me way longer to write than I would have liked.

Besides creating the necessary technology for the game, I’ve never worked on such a large scale before. Programming is not software engineering and hacking is not project management. I didn’t have much experience leading or creating a serious project before this one, and I found myself struggling with choices. What do I call this class? Should this be its own class in the first place? Is this overengineering or good practice? And that’s just the software architecture. There was also the question of project scope. I was behind schedule, and it wasn’t due to feature creep. What was I doing wrong?

Continuing the March Towards Completion

But if I could get the game done by Christmas, I think I’d still be doing well. The October Challenge was just a fun deadline and wasn’t a must-hit, urgent business deadline. According to the work I have identified and my actual rate of work, I thought I had a more accurate project estimate, and Christmas seemed to be a doable deadline. From what I’ve been told, there is a trend of increased sales around Christmas, so it might work out better for me. I pushed forward.

I was making decent progress at first, but the end of the month involved Thanksgiving and moving out of my apartment. To make matters worse, individual game systems weren’t working quite right, so I spent part of the last week finding and fixing bugs for work I thought was finished. I was finally hitting my weekly estimates, but there were also setbacks. Progress was still slower than I would have liked overall.

Unfortunately, near the end of November, I saw my schedule slip even more when I identified a ton more work. When hacking a prototype together, there can be missing menus, level selectors, data permanence, or any number of other aspects of a game. A full game missing these features isn’t a full game, by and large. When I initially planned out the project, I glossed over a lot of these kinds of details. I wanted multiple game modes, but I didn’t plan for them, nor did I figure out how I wanted the player to access them. Suddenly my project ballooned to almost twice its size, with a likely deadline in February or March, which made Stop That Hero! the six month project I wouldn’t have started if I knew.

Burn down towards February

The Future!

It was demoralizing to miss the October Challenge deadline, but this new estimated deadline was frustrating. I initially hoped to make my first sale at the end of October, and now I might not do so until after winter? And that’s assuming anyone is interested in buying it in the first place!

All this time, my savings account has been slowly reducing in size, and it will continue to do so. I’m well aware that I don’t make money producing a game. I can only make money selling a game. I could shelve Stop That Hero! temporarily while I work on something smaller, but I fear I’ll simply end up in the same situation writ small. That is, a smaller game still requires a lot of technology and infrastructure that I don’t currently have. Plus, I don’t like the idea of dropping a project midway and starting a new one. I’m tired of unfinished projects on my résumé.

I read a lot of things that get me second-guessing my choices. Is Stop That Hero! too complex and hard to make? Should I focus on “evergreen” mechanics, as suggested at Lost Garden? Is TDD inappropriate for getting games finished quickly, or is it necessary for getting games finished quickly? Am I expecting too much from my first project, or should I take the problems I’ve encountered as a sign? Am I running into the same kind of problems everyone runs into, or do I need to scale down my ambition until I have more experience? Do I need to work on smaller projects to build up my technology and code base, or can I continue building what I need when I need it for this project? And before you ask, yes, I have made a Pong clone, among other simple games, so it isn’t like I was jumping into a very large project without any experience at all. Or, maybe the problem actually is that I don’t have enough of these simple games under my belt.

There’s a lot of uncertainty, and it would be easy to panic or freak out (and I have at certain points!), but it is good to have some perspective. In six months, I’ve done more and learned more than I have in the last five years prior. While I expected to learn a lot during this time, my existing knowledge wasn’t as helpful as I thought it was. I’m taking on roles that I never had experience with before. Before I went full-time indie, I didn’t make decisions that would have a major impact on my business, and it’s an enormous responsibility.

And yet it isn’t a crippling responsibility. It’s exhilarating!

While I have the added burden of figuring out what specifically is important, I get to focus on it as much or as little as I want. While it’s a little scary to think that my decisions can make or break my business, they’re my decisions, and part of the fun of running your own business is in learning how to make better ones. The stakes are high, but at least I’m not settling for less out of a need for security.

Six months ago, I had very little idea that I’d make the progress I have and face the challenges I did. I knew it wouldn’t be a cake walk, but I also knew it wasn’t impossible. If I could change anything, I’d have tried harder to produce results while working part-time. I wish I had more direct experience working closely with other people making games so I didn’t have to figure out nearly as much on my own.

Still, I’m only six months out, and I’m in it for the long haul. In 2015, I hope I’m writing my own five year retrospective with plenty of good news to report.

If you are a veteran game developer, do you have any specific wisdom to share or regrets to warn against? If you are an aspiring game developer, do you have any questions about what the future might hold? Please post them below!

Categories
Game Design Game Development Linux Game Development

Stop That Hero! November Development Summary

I wrote up a October challenge post-mortem at the end of the previous month, and almost an entire month has gone by. I haven’t written much, partly because I went off of my self-imposed schedule to do more game dev work at the expense of writing and reading time.

What progress have I made with Stop That Hero! in the month since?

First, I implemented my own component-based object system. I know, I know. I wrote about the frustrations of trying to implement state of the art game objects and said I would give up, but eventually I found my own way. In trying to proceed with the game’s development and putting the frustration behind me, I found that I was very close to doing the same kind of work anyway. I’ll write more about the details of my implementation in another post.

Even after I had the infrastructure for the object system, I still had to figure out how to use it. In a running game session, I understand that the game’s systems will make use of the object system and components, querying and updating them as needed, but what about initialization? Specifically, how does the hero get created? Should that object and all of its relevant components get created when the level is loaded, when the level is initialized, or as part of the first update to a new game?

Some entities will get created during the course of a game session, such as when the player creates a monster at a tower, but the hero is there from the beginning, and I was having trouble trying to figure out how to treat his creation.

I already have a number of components:

  • Position (current location data)
  • Sprite (the current sprite image to display)
  • Spawn Point (a position where an entity will be initialized when created)
  • Movement (speed and direction data)
  • Targeting (a list of potential target type IDs and the current object ID targeted)
  • Targetable (a target type ID)
  • Pathfinding (a list of traversable terrain IDs and the current path)

With the above components, I can already see the hero moving from a start location (the spawn point) to a target, which is an object made up of only Targetable and Position components. The hero picks the nearest object with a target ID matching the set of IDs he is allowed to target, avoids obstacles such as trees and water, and moves along the path generated by the pathfinding system.

The pathfinding system was surprisingly difficult. A* is such a common algorithm, and there are plenty of code examples around. Essentially, it’s a solved problem, right? The problem was that all of the code examples and most tutorials and pseudocode were node-based, whereas I was looking for something that gave much more focus to the connections. That is, it should be possible to get from one node to another in more than one way. For example, if you have a bridge, you can jump off of it very easily but you wouldn’t be able to get back up unless there was a ladder, and climbing the ladder would cost more than jumping down. Or, if the height is great, climbing down the ladder would be less risky than jumping and potentially hurting yourself.

The book “Artificial Intelligence for Games” has a focus on connections, but the pseudocode was a little difficult to follow. When the pseudocode makes use of whitespace, it’s hard to tell what code block you’re in when the source spans multiple pages. While the book says that there is a working code example on its website, I couldn’t find any code related to the pathfinding chapter. I emailed this error but the website still doesn’t reflect it, and I haven’t heard back from anyone about it.

I thought I had my pathfinding system working since my unit tests passed. Obstacles were avoided, and short paths seemed to finish as expected. It wasn’t until I gave the hero a target about a quarter of the map away that I saw a problem:

Debug Path

The hero’s path is specified by the multiple hero sprites and the black line. The dotted yellow line is what I think a more appropriate path should be if the pathfinding algorithm was working correctly. I found it very odd that the path was complete yet so suboptimal. I eventually realized that part of the problem was a bug in my node sorting, and here’s the relevant line:

lessThan == costSoFar < r.costSoFar

I didn't see the problem for a long time, but I eventually posted the code online. Phil Hassey pointed out that I was testing equality instead of assigning a value. Doh! Sometimes you just need a fresh pair of eyes.

There was also another bug in that line. "Artificial Intelligence for Games" argues that you should be using the costSoFar value to sort nodes in the open list, saying it is the only value that isn't a guess. I didn't quite understand why, but I figured such a thick text book written by experts who have worked on more games than I have would know better than I would. So, here's a lesson: never implement an algorithm without understanding it. Everyone else in the world argues you should use the estimated total cost to sort nodes. After all, you're trying to guess which one will get you to the target node in the fastest way. Sorting by cost so far means that there will be a bunch of nodes, possibly in multiple directions, that can be first. Once I changed the value checked from costSoFar to totalEstimatedCost, my paths were straighter and shorter.

Still, my pathfinding system isn't working quite as I expected. The hero can only walk on grass, but other entities could fly over everything. While they might prefer flatter areas, they should still be able to fly over trees, mountains, and water. I created a hero with the ability to move over all of these different terrain types, and I was disappointed to find that the path didn't change. He was still avoiding them as obstacles.

I realized that part of the problem is how I mapped the world representation to the pathfinding graph. Does the terrain have an absolute cost, or should terrain costs be entity-specific? That is, is a mountain always harder to traverse than grass, or should a mountain troll bias towards mountains while a slime prefer the plains? If every entity had the same kind of movement restrictions, it makes sense to have absolute terrain costs. An obstacle for one will be an obstacle for another. But if some can move through water or fly in the air, does it make sense for terrain to have an absolute cost? If I give each entity weights for terrain types, why not just get rid of the absolute costs entirely since the weights are what ultimately matter? How does a game such as Advance Wars handle it?

Other issues I had to deal with included problems with using floating points versus ints. I was using floats to represent world positions for objects, which is fine, but when I was integrating different aspects of the system together, I found that other data structures were implemented using ints. I was losing all of the precision I needed, and it wasn't until I was printing out text every few lines that I could see the problem. Unit tests didn't catch this issue because separate objects and components worked just fine.

But with pathfinding and targeting working fairly well, Stop That Hero! is much further along. Once I can move an entity to an expected target, the rest of the game will hopefully come together much more quickly. Hopefully.

Categories
Game Development Marketing/Business

Planning an Indie Agile Project

I’ve mentioned story cards, points, iterations, and burn down charts, but I’ve never explained it here on this blog. Unless you’ve done similar Agile project planning, you might not know exactly what I’m talking about. Thanks to Erik Yuzwa and Casey Dunham for asking me to explain my project planning process!

In traditional waterfall development, Big Design Up Front (BDUF) is the rule. BDUF is done on the belief that if you plan every detail early and hand off the design to the development team, the development should be smooth sailing. The reality is that requirements evolve, technical requirements might not be fully understood at first, and not everything can be anticipated. Agile software development practices are an attempt to work within the true nature of development to deliver working software to the customer. Things change, so make sure your methods make it easy to change.

In a project, you have stakeholders and developers. Stakeholders are usually game designers, product managers, project managers, CEOs, customers, or anyone who has input into the direction a project should take. Developers are the ones who put the project together to the satisfaction of the stakeholders. Stakeholders know best about what the project’s priorities are and can determine the value of the finished project and feature set. Developers know best about how long specific tasks might take or how difficult features might be to implement. During the planning phase of an Agile project, the two groups work together to figure out a prioritized feature set and estimated schedule.

I’ll start by warning you now. I’m not an expert. I have very little knowledge and experience with project management and the role of a game producer. What I’ve done is based on my experience as a cube dweller at my last day job. The company was pursuing Agile development methodologies, and I got some training as a developer, and I was able to see how the stakeholders were trained as well. To make it worse, I work alone, so I have to put in extra effort to wear the hats of business owner, project manager, and other stakeholders. Sometimes I took shortcuts, but only because there’s no need to communicate with myself explicitly.

If you’re a fan of Joel on Software, you might find the article on Evidence-based Schedules more helpful. Instead of settling on an arbitrary date, it gives you a confidence distribution curve over a range of ship dates, which gets more accurate as the project progresses.

When you have a specific date as a hard deadline you can’t miss (hahaha), the following explanation of an instance of Agile project planning might help.

Introduction to Paddles of War

Let’s assume you’ve green-lit a project and have picked a date for when you would like to see it finished. I’ll illustrate with a simple example called Paddles of War. It’s based off of a game I tried to implement in college in QBasic. It was inspired by an Atari 2600 game I loved called Warlords.

Paddles Of War is a multiplayer, real-time battle game. Each player controls a paddle, defending a castle made up of walls and the king behind them. A cannon ball is ricocheting around the play area, and each time it hits one of the castle walls, it destroys that part of the wall, eventually exposing the king behind it. If the cannon ball hits the king, the king is killed and the associated player is eliminated from the game. The last player with a surviving king is the winner. If the cannon ball hits the paddle, it is deflected away.

A fairly simple game, it’s like Pong meets Arkanoid with some battle elements thrown in. Let’s say that the deadline for the project is three months from now.

Stock Up On Supplies

First, you’ll need some tools. To start, when you’re in the project planning stages, you’ll need a lot of index cards and something to write with. Sharpie markers are usually suggested, but pens are fine. I also like having different colored index cards to help with visually differentiating between different kinds of cards. I’ll get to specifics later in this article.

During a project, you should be able to look at a wall of index cards and know at a quick glance what is currently being worked upon, what is scheduled for the current iteration, what’s finished, and what’s blocked. I purchased two cork boards and put them side-by-side. Why not one large cork board? Well, it was more expensive and I’m an indie on a budget. Also, with two boards, I could rearrange and separate them at will, so it seemed more flexible. I also have pins to put index cards up on the boards.

And that’s it. All you need to do this kind of Agile project planning is a writing utensil, a bunch of index cards, and a place to post them. I suppose sticky notes might work, but I’d worry that the paper would curl and the glue would stop working. Pins and index cards seem to work great.

You can also make use of a spreadsheet to create a chart to make progress easier to track, and I find such charts really useful for project health checkups. I’ll explain how I use Google Docs for such charts, but you won’t need to worry about it until the project starts.

Identifying the Project Requirements

Now you are in what is known as Iteration Zero. Agile project scheduling is based on iterations, and iterations are an arbitrary unit of time. Usually, a week is good, although some projects will have two or three week iterations.

Iteration Zero is the time to identify the work required for the project and figure out what the implicit and hidden requirements are. Find a room with a large table (or use the floor if your pets will leave you alone long enough), and bring the index cards and writing utensils.

At this time, everyone can create what are called User Stories. See this introduction to user stories for more details, but you can think of it as a high level, basic description of a feature or requirement. Some people argue that only stakeholders can create user stories, but developers might be more familiar with the underlying requirements. If your publisher has standards for what should be in every single game, such as translations to other languages or configuration options, the game designer might not necessarily be aware of their existence, yet the developers still have to expend the effort to get them done.

When creating a user story, you want it to be easy to identify what the story is, which requires a minimum number of words and big writing:

Creating a StoryInitial Stories

As you can see, each story card is very easy to read from a distance, assuming you write them legibly.

In the case of Paddles of War, the game designer might come up with these initial stories:

  • The player can start a new game from the menu.
  • The player can move the paddle with arrow keys.
  • The cannon ball starts moving from center in random direction.
  • The cannon ball can destroy castle walls and kill kings
  • Paddles can deflect the cannon ball.
  • Game ends when there is only one king left.

There will be many, many more, but with just these high-level stories, it’s enough to start thinking about the software needs. A developer might wonder if these stories say everything accurately and poses the question: “Is it possible for there to be more than one cannon ball in play?”

The designer might respond, “Oh, that’s a good idea! Multi-ball might be fun!”

Before the designer creates a new story card about allowing multiple balls in play, the developer points out that with more than one ball, there’s the potential for two kings to be killed simultaneously, which means it is possible that there will be no more kings left. Since the game ends when there is only one king left, what happens when there isn’t one? Are draw games allowed, or should there always be a victor? How does the designer want to handle this situation?

While the programmer can provide input into this story, it’s ultimately the designer’s call if it should be one. The designer is the stakeholder, and he/she is the one who determines the value of features and whether they should exist in the first place.

The programmers might see ricocheting cannon balls and collision responses, and they’ll recognize the need for a physics system. Is there an in-house system available? Do they have to build it themselves? Will they use a third-party solution?

No matter what the answer, the important thing is that questions are being asked. Stakeholders and developers are communicating about what the project will actually be. The producer might have to look into existing solutions, but maybe there isn’t much of a budget for such things. For now, a story can be written related to the creation of a physics system. An implicit requirement is now explicit.

When you’re finished with user story creation, you might have many tens or hundreds of cards, depending on the complexity of the project. For my Ludum Dare 18 version of Stop That Hero!, for instance, I had 31 cards in the end, and I’m sure I remember that some important aspects of the game had no story cards associated, so there could have been more. Since the game was being done in a weekend, I didn’t bother creating the story cards towards the end to reflect to newly identified work. Since I was working on my own, it’s not like I had to stop and communicate my intentions to anyone but myself, so I took a shortcut. When you work with someone else, you’re not going to be able to do the same without repercussions.

Now, by figuring out all of these stories, aren’t we doing the same thing as Big Design Up Front, which means it has all of the rigidity disadvantages as well? No. Agile Development is meant to respond to change, but you can’t respond to change if you don’t know what the change is from. By trying to identify all of the stories that make up the project, you have a good, high-level idea of what the project actually looks like. Also, you save time. The details for any given story can be planned when that story is being worked upon, so lower-level details benefit from a kind of a “Just-in-Time” planning. After all, if the project is likely to change, the stakeholders might decide that a particular story doesn’t need to be implemented at all. By waiting to plan the details until you actually work on it, you aren’t wasting time on making plans that never needed to be carried out.

Estimating Cost

Now that the user stories are finished, it’s time to estimate how much effort will be required for each story. Now, remember, the developers are the only ones who can make estimates with any accuracy. Implementing stories is their domain. Stakeholders can question estimates or ask for explanations, but in the end, if a developer thinks that a story is going to be tricky, the stakeholders have to accept that estimate.

To do estimates, each story card is given a numerical score. This score doesn’t necessarily correlate with a time estimate, although some teams like to think that a number represents the number of hours or days it would take to accomplish anything. The point of the numerical score is to indicate the estimated cost of a story, whether in time or effort. Also, this estimate will be different depending on who is doing the estimation. A veteran game developer is going to create more low scores than a junior developer would. The team of developers must agree on the score for each card.

This is the part that could be incredibly time-consuming, but a nice way to speed it up is to take all of the story cards and throw them into separate collections: easy, medium, and hard. Then for each collection, you can probably quickly separate them into sub-collections of easy, medium, and hard, or maybe just easy and harder, or whatever the developers find appropriate. Boom. You’re done. Now you just have to write down numbers on the cards corresponding to what collection and sub-collection they’re in, and you’re done assigning story points. To illustrate:

Separating the cards into columns by expected relative difficulty from left to right:

Separating the stories

Assigning numbers to the columns:
Categorizing the stories by difficulty00010More categorization

Putting the score on the story cards in the upper right hand corner:

Scoring a story according to its category

The entire project at a glance:

All of the stories in scoring categories

You’ll note that the numbering isn’t sequential. When you’re trying to decide the relative difficulty of a story compared to other stories, what does it mean to be a 5 versus a 4 or 6? If you are measuring difficulty based on estimated number of hours, then sequential numbers make more sense. Using the Fibonacci sequence, it makes it very clear how a story’s estimated cost compares to another’s. You might choose a different sequence entirely.

The last thing the developers need to estimate is how much they think they can do as a team in an iteration. Let’s say that each iteration in this project is one week, which means there are 12 iterations over the course of three months. Now, what’s important to understand is that the estimate is not divided among the development team members. Doing 10 points in an iteration with two developers doesn’t mean each developer does 5 points, and adding a third developer doesn’t necessarily mean you can expect 15 points of work in a week. The estimation is a team effort. It’s not an important distinction when you work alone like I do, but with multiple team members, you can’t treat them as if they are replaceable cogs in a machine.

What the developers usually do is grab a sample iteration from the full collection of cards. They’ll put stories together that sound doable in an iteration, and then they sum the scores on those cards. The total is the estimated iteration velocity. For this example, let’s say the developers think they can do 10 points of work in a week.

Prioritizing Iteration Requirements

Now the developers get out of the way, and the stakeholders get to play. Armed with the collection of story cards, their scores, and the iteration velocity estimate, the stakeholders start putting together iterations according to what they want to see finished first. Again, stakeholders are in charge of the value assessment, so while developers can provide input (“Er, you can’t have the Foo until the BarWidget subsystem is ready, so the BarWidget subsystem needs to be in this iteration if you want the Foo as well.”), the stakeholders get the last word on what story goes into what iteration.

Each iteration has only as many story points as the iteration velocity at most. The developers have already indicated what they think they can do in an iteration, and the stakeholders have to respect the estimate. They can’t expect more work to be done in the same amount of time. Expecting crunch time or assuming that the developers are padding the estimates isn’t sustainable or healthy.

It’s usually at this point that the producer gets heavily involved. If sound assets are going to be ready in a month, for example, then it would be nice if the game was capable of playing sounds within four iterations. Plan those iterations accordingly.

Also, is it all possible? 12 iterations at an iteration velocity of 10 points means that at the end of three months there will be 120 points worth of work possibly finished. According to the example project’s scoring, there are 190 points estimated in the backlog (and you’ll note important things are missing, such as sound and animation work, so there should be more cards, but as this is just an example, I’m not going through all the effort).

Does this mean that the developers need to try to do more per iteration? Should the estimated velocity be changed from 10 to 16?

No! It means that the stakeholders need to make some decisions. Is it more important to hit their ship date, or do they want to have everything in the project plan finished before shipping? Can they be happy with shipping only on desktop computers and not porting to Facebook or mobile platforms? Is multi-ball a must-have feature? In this example, a lot of the estimated hard work was in packaging for builds, but in a real project, there could be all sorts of wishlist items, feature creep, and legitimately important requirements reflected in the story cards. It’s up to the stakeholders to put together the iterations according to their priorities. After all, what those priorities should be is their domain of expertise.

While all of the iterations could be planned up front, the plan can change depending on the progress of individual iterations. It might not be worth the work to plan more than the next iteration or two. I usually have the current iteration planned and the remaining backlog somewhere nearby the cork boards to easily look through if I feel like it.

Development Time

It’s time to get those developers working! During Iterations 1 through 12, the current iteration’s cards can be put in a highly-visible place. An iteration meeting usually ends a previous iteration and kicks off the next one. Stakeholders and developers meet, talk about the previous iteration’s progress, and introduce the next iteration.

First iteration

Above is an example of the first iteration of LD18’s Stop That Hero!. I had colored index cards to label a number of columns, and since I worked alone, I left a few out, but here are the different column label explanations:

  • Approved (not pictured): Place stories under this label when the stakeholders agree that a story is finished. Again, I work alone, so when I say something is finished as a developer, who would disagree?
  • Implemented: When a story is considered finished by the developer, the story goes here and awaits approval from the stakeholder.
  • Assigned: This column is for each story actively being worked upon by the developers.
  • Unassigned: This column is for all stories in the iteration that aren’t approved, implemented, or are actively being worked upon. At the start of an iteration, all of the iteration’s stories go here.
  • Blocked (not pictured): If a developer cannot implement a story, whether due to an unforeseen technical issue or waiting for an external resource, the associated card goes under here. Since I work alone, blocked stories are just stories with requirements or dependencies I haven’t planned for, usually. I just consider it part of the work, so it’s not really blocked if I’m the one doing the unblocking.

While stakeholders determine what stories are in a particular iteration, developers get to choose which story in the iteration to work on at any given time. The developer, or developers if the team makes use of pair-programming, will pick a card from the Unassigned column and move it to the Assigned column. It indicates to stakeholders and other developers that this story is actively being implemented. When a story is finished, the card gets moved to the Implemented column. If the developer finds that there is some obstacle preventing the completion of a story, the card is moved to the Blocked section, and the developer picks an Unassigned story to work on in the meantime.

At a glance, anyone can see the Big Board and know what the iteration looks like. If it’s the beginning of the iteration, it’s not very alarming if no cards are in the Implemented column. If the iteration is almost over and there are still no implemented stories, you know that something is wrong.

In development, sometimes you don’t realize the true nature of a requirement until you start working on it. Maybe a story that made sense in Iteration 0 now seems too vague. Perhaps there are details missing that require a decision from the game designer. Or perhaps a completely new requirement is conceived, and the stakeholders really want it. Whatever it is, requirements change.

What’s nice about using index cards to represent project requirements and user stories is how easy they are to move, create, and destroy. Is there a need for a new user story? Pull out a new index card and write it! Is there a user story that encompasses too much? Split it up by creating multiple stories and ripping up the original card! Is a feature in a later iteration suddenly more important for the big boss to see sooner? Move the cards between iterations!

Creating new stories and working on them aren’t necessarily done in the same iteration. A new story requires the developers to score it, and this work can be done during the iteration meeting. If work wasn’t completed in the previous iteration, the stakeholders can decide if they still want to see it done in the next iteration or if they can push it off to another one. Those iteration meetings act as milestones and opportunities for project assessment.

Within an iteration, it can be useful for the project team to meet for quick stand-up meetings daily. These aren’t hour long meetings. Each member of the team quickly says what they worked on the day before, what they will do today, and whether or not anything is blocking them. Any further discussion can usually be handled outside of this meeting, allowing non-interested parties to get back to work.

Since I work alone, I don’t have daily stand-ups. My cats don’t usually provide much useful input anyway. I do, however, have iteration “meetings” each week, in which I assess the previous iteration’s progress and put together the next iteration. Since I wear all the hats (my cats don’t wear hats), it’s probably more important for me to be conscious of what needs to be said in this meeting. The developer might just want to get back to work, but the producer is going to want to know why progress is slower than expected, and the president might need to decide if the game can be shipped later and still meet the company’s sales goals. Or maybe things are going very well, and the designer wants to know if a new feature can be added. Without multiple people in those roles, there’s less worry about miscommunication, but there’s more concern that an important business role has been forgotten.

Assessing the Health of the Project

For you chart junkies, this is the fun part. You have lots of data here: estimated iteration velocity, the backlog’s total score, the deadline, the number of points completed in each iteration, and the number of points added during an iteration. What can we do with it?

I’ve found that creating a chart to be incredibly useful for at-a-glance project assessments. Here’s an example showing my current project’s first 7 iterations:

7 iterations of project

The blue line tells you the ideal plan. Basically, if I have constant iteration velocity from an estimated total project backlog, I can see when I’ll expect the backlog to hit 0 points. In this example, the expected project completion date is December 8th at a velocity of 10 points per week.

The orange line represents the actual backlog. At the beginning of this project, I had identified 75 points worth of stories. If stories are always being completed, you can expect this line to go down, but if work is getting added, it can go up. In this case, the line went up in the 4th iteration, and since nothing was done in the 5th iteration, it stayed horizontal.

The red line represents the amount of work getting completed, or the actual iteration velocities. Except for the 5th iteration, it has been going down at various slopes. The steeper it is, the more work is getting done, and a horizontal line again indicates that nothing was done.

Some people might argue that the orange line is the only one that matters, and it would be if all you cared about was the project being done. However, from a project management standpoint, the orange and red lines don’t mean much unless you compare it to the blue line. Knowing that there is progress is good, but knowing if the progress is good enough is better. The blue line, again, is the ideal, and if you compare the other lines to it, you can get an idea of how healthy the project is.

The red line can also be compared to the orange line. If no work is being added, the slopes will be the same, but if the orange line is more horizontal than the red line, you know that more work was added to the iteration. If the orange line pulls away from the red line too much, it indicates that requirements weren’t identified up front. If either of those lines ends up extremely high compared to the blue line, you know that the project is not on track to meet its deadline.

For example, early in this project, my estimated velocity was 20 points, and it was frankly a guess.

BurnDown at 20 points per iteration

Ignore the fact that the lines extend to the right for so long since it was based on data that wasn’t filled in yet. Still, right away, in the first iteration, you can see that the red and orange lines were above the blue line. The second iteration wasn’t much better. I only did 7 points of work in the first iteration and 10 points in the second. To make it worse, I was adding more stories to the backlog. It took me a few weeks, but I had to face the facts and realize that I wasn’t working as fast as I thought I would.

So I changed my estimated velocity as well as the initial estimated backlog. and as you can see in the earlier chart, things look healthier. But wait a minute! The project isn’t actually healthy! It’s late! Is this just slight-of-hand?

It would if I was trying to deceive, but what I’m trying to do is get as accurate a picture of the project as I can. The project was going to take longer than I originally anticipated, but by getting more accurate data, I could make better decisions. Do I continue the project with the new deadline? Do I cut features to try to get closer to the original deadline? Do I hire contractors to help me speed up development (keeping in mind Brooks’ Law)? Do I cancel the project outright? I decided to continue the project, and I felt confident about getting the game finished before Christmas.

That is, until I realized that there were various aspects of the project I hadn’t given enough thought to. At the end of iteration 7, I created a number of new stories related to glossed over details. Here’s the latest chart:

Start of 8th iteration

See that spike in the orange line? Yeah, that represents the project nearly doubling in size due to all of the stories I didn’t anticipate originally. Things like a system to let the player choose what level to play in a campaign or a way to save progress. As fundamental as these stories were, I failed to identify them as actual requirements for the project, and so they were never part of the original plan. Even though work is getting done steadily, as the red line demonstrates, the orange line makes it very clear how much trouble the project is in.

Again, it’s way better to have more accurate data than to be happy with flawed data. The project was always in trouble, and now the data reflects this fact. Since I’m an indie without obligations to a sales force or contracts, it’s not as big of a deal to let the deadline slip as it would be if I was working on a multi-million dollar project with sales estimates and stockholders expecting me to meet them. Still, I only have so much in savings, so I’d like to try to get to my first sale sooner rather than later.

The good news is that I expected that spike in the backlog. As I explained in my Stop That Hero! October Challenge post-mortem:

While I knew what tools I would use at a fundamental level, such as which compilers and libraries I would use, I didn’t realize I needed to figure out what technology I needed to create. If I did, I probably would have planned for it in the schedule or I would have pursued a simpler project in the first place.

So I knew there were going to be stories to identify that I missed during my project’s Iteration Zero. I just didn’t expect there to be so much! Hopefully in future projects, I can learn from this experience and try to be a bit more thorough in the technical feasibility assessment. Plus, I’ll have the benefit of this project’s codebase.

Still, the point is that with this kind of Agile planning and this chart, I had an early warning and a rough idea of the project’s health. Without this data, I would have to rely on intuition, and well, let’s just say I don’t have a dartboard.

So how do you create your own chart? I create a spreadsheet with the labels and data indicated below:

Burndown Chart Creation

If you click on that image, it’s probably easier to read. The iteration column is just numbered 0 through whatever. The dates column is straightforward. I put the end date of the iteration in each cell.

Under Burn Plan, I have each cell subtract the Estimated Points Completed Each Iteration from the previous amount. So if the estimate is 10 points and the burn plan’s initial value is 200, then the next cell will have 190, and the one below that will be 180, and so on. This column along with the dates will give you your blue line. How do you pick the initial estimated backlog? You can choose a number based on a target date, or you could try to estimate the size of the finished project. My initial number was based on the original estimated velocity of 20 points and an original target date of October 31st. Since then, I’ve tried to use this column’s data to indicate when I can expect to finish my project if i don’t cut features. I’ve had ranges between November and March based on different starting values and estimated velocities. At the start, I didn’t realize how large of a project this game was going to be, but with my latest data and this blue line, I know when I can expect to finish.

Points Completed and Points Added are manually changed each iteration as you complete and add points. Initially, you’re just adding a massive number of points to represent the start of the project with all of the identified work so far.

The Backlog tracks the currently known work, so each cell takes the previous cell’s value, adds the points added to the iteration, and subtracts the points completed in the iteration. This column gives you the orange line.

The Burn Actual vs Plan column will generally subtract the Points Completed in the iteration from the previous cell’s value. So if the first cell is 75 and 3 points were completed in the first iteration, the next cell down would be 72. For this column, you’d ignore the Points Added column. The Burn Actual vs Plan column gives you the red line.

I wish Google Docs let you set the minimum value of each axis. It’s a little annoying to see negative values when the data stays above 0 (seriously, Google, what’s up with that? According to your support forums, this is a highly requested feature). Of course, applications such as Excel and OpenOffice.org’s Calc wouldn’t have this problem, but I like the flexibility of being able to view my burndown chart and data anywhere.

Conclusion

Hopefully this article has given you insight into how I plan my projects and how you can do something similar for your own projects. By using tools as simple as index cards, you can quickly get an idea of the size and scope of your project. Developers and stakeholders can work together from their strengths to create the plan, and by using a simple spreadsheet, you can track the health of that plan.

Once again, I’m not an expert project manager, so I’m doing what I can and am still learning. For instance, while the orange line gives me a lot of useful info compared to the blue line, I don’t know what the red line means when it’s so much further down the chart and starts to go negative. In a few iterations, this burn down chart representing a revised date of February will have a negative red line:

Burn down towards February

The red line still represents work getting done relative to the backlog, but I wonder if there’s a better way. I’d love to hear any feedback you might have, and feel free to ask questions!

Categories
Game Design Game Development Linux Game Development Personal Development

Stop That Hero! Development Continues

With the Ludum Dare October Challenge over, I am still working on Stop That Hero!. Even though I had said that the Challenge deadline wasn’t important to me, I still had this desire to meet it, and I think I had a lot of competing thoughts in my head since I never made a firm decision to hit the date or ignore it. On the one hand, it’s mentally freeing to not have a deadline breathing down my neck. On the other hand, I don’t want to take forever working on the game.

Project Estimation

My old project schedule estimates were based on a few key pieces of data. I had a deadline I wanted to meet, which was October 31st. I had the number of estimated story points for the entire project, which came out to 75 points total. Going backwards, if I did 20 points of work each week, I’d hit the date with some time to spare. Putting together a sample iteration, I felt 20 points was reasonable at the time.

In the last month, I found that I added new stories each week, so now the project’s total story points have increased to 89 points. I’ve also found that 20 points per iteration was overly optimistic, and it seems 10 points per iteration might be more doable. With this new data, I decided to estimate the project with a different set of data, and you can see the project comparison below.

Burn Plan Comparison

The flat lines to the right are basically projecting into the future based on no work being done, so you can ignore them. The blue line indicates the ideal. In the first case, I was expecting to hit 0 points on October 27th. In the new schedule estimates, I’m likely to be finished by December 8th.

What’s nice about these graphs is how much they can show you in an instant. So long as my actual burn rate and the actual backlog stay under or at the blue line, my project is healthy and progressing nicely. If they cross over to the top of the blue line, something has gone wrong. In the first case, you can see that the project was in trouble from the start. I thought that if I could start hitting 20-point iterations that it wouldn’t be that bad, but I couldn’t do it.

With the new estimates, those weak iterations were actually relatively strong, even though the last week was very poor. I only managed 2 points of work then, and I ended up adding 6. I hit a snag in development, but I am recovering from it. Still, you can see that over the life of the project, I’ve been adding to the backlog, and with the previous week, my backlog matches the estimated backlog at this time. It doesn’t give me much room to add more to the backlog, but it isn’t scary yet. If it is mid-November and my backlog is far on the upper-left side of the blue line, however, then I’ll have to question what’s going wrong.

My main concern is that there will be many more stories added to the backlog, especially since I was surprised to learn how much of the basic technology I needed to build in the last month. Also, I worry about not being able to dedicate all of my time to the project that I normally would. Besides the fact that Thanksgiving and Christmas are coming, I’m also moving at the end of the month. I’m more than certain that my project’s schedule will be negatively impacted, but since I am aware of it now, I can take steps to plan for it.

The Game’s Status

What’s implemented so far? I have a menu system which allows me to select what level I want to load. A level loader will populate a level instance with map data from a PNG file. The level uses that map data on initialization to know where to place towers and treasure chests, as well as what type for each, and it also knows where the hero’s initial spawn point is. The level loader also sets the hero’s starting lives to a hard-coded value.

There’s still a lot left to do, but the biggest thing missing is the concept of an entity.

Near the end of the previous month, I ran into trouble when it came to actually implementing the hero. The large number of added points were partly because I took a vague story for implementing an Entity and broke it down into multiple, specific stories related to various aspects of the creation of an Entity. Now instead of trying to create an entity and all of its behaviors at once (and not knowing when I’m finished or how to start), I will be working on rendering an entity, moving an entity according to its speed and direction, and other very specific tasks that are easy to understand and focus on.

Other major components include pathfinding and player actions. The prototype had a poor-but-workable pathfinding solution. While I was happy with it in terms of a weekend project, I knew it wasn’t as good as it could be, and I learned a bit more about A* implementations since then.

While the main activity for the player involves picking a monster type and deciding which tower to create it at, I’d like to investigate other things the player can do to impact the game. In previous posts I’ve mentioned ideas such as banners that all monsters will gravitate towards or clicking on resources at controlled towers in order to collect them. I’ll hold off until I get the fundamental activities implemented, but I think they could change the feel of the game in a positive way.

Once I have the ability to create entities and some way for them to move, fight, and die, the rest of the game will fall into place relatively easily. Victory and defeat conditions depend on the entities actually doing things, animation requires things to animate, and there are details and balance issues that can only be addressed when I have something to detail and balance in the first place.

Of course, I’ll continue to write about the game’s development. B-) Is there any aspect of the game’s development that you’d like for me to explain in the coming weeks? Let me know by leaving a comment!

Categories
Game Design Game Development Games Marketing/Business Personal Development Post-mortem

Stop That Hero! October Challenge Post-Mortem

October 31st came and went, and Stop That Hero! was not in a position to be sold, even as a beta or alpha project. Partway through the month I realized that even if I was able to finish the project, the work of setting up the payment systems, customer support, and even the website was going to take some time as well. According to my estimates, I’d finish the game sometime between the end of October and the beginning of December. As disappointing as it would be not to finish in time for the October Challenge deadline, I also knew that it was a “fun” deadline as opposed to a hard “must-hit-this date” for my business.

I will continue to work on Stop That Hero! because I believe in the project, but I’d also like to get better at project management. Now that the deadline has passed, I can look back on the month and think critically about how I did. Even though there was no business-related urgency in getting the game finished for the Ludum Dare challenge, I still wanted to do so, and it was demoralizing to realize that the game wasn’t going to be finished in time.

For the unfamiliar reader, Stop That Hero! was originally created for the Ludum Dare 18 Jam. The player was an evil villain in charge of a castle and a number of towers, and a hero character was trying to conquer the castle, liberating towers and collecting treasure chests along the way. The player would create minions at any of the towers, and those minions would try to kill the hero. Kill the hero three times, and you win. Lose the castle, and you lose the game.

For this project, I wanted to make Stop That Hero! a commercial-quality game that required no proprietary dependencies and ran on at least GNU/Linux (my preferred platform) and Windows, with plans for a Mac OS X port and an eye toward mobile devices. I wanted the game to be data-driven instead of hard-coded. I wanted the game to have multiple game modes and levels, and I wanted me and the players to have the ability to create our own custom levels with custom rules. I realized that it was a lot to do for a first release, so my intention was to make the game hard-coded yet easy to change so that it was using external data and scripts. Future updates would involve replacing the hard-coded bits with loadable data.

What Went Right

While it might seem strange to think that anything went right for a project that wasn’t finished, I do believe there were some good things that positively impacted the project.

  1. Planning and Preproduction Time. Even before the October Challenge was announced, I knew I wanted to take Stop That Hero! and make a full game out of it. I spent a few weeks at the end of September looking at every aspect of the game, from resource handling to monster variety to game modes.

    While I think the original LD18 game’s mechanics were marred by a lack of game balance and probably could stand on their own, I wanted to investigate every possibility for making this game the best it could be. I identified major design challenges that I wanted to focus on early on. I also speculated on how much of the game could be data-driven or scriptable. This early planning helped me visualize how I wanted the finished game to look and feel.

  2. A Regular Work Schedule. As an indie game developer, I have no boss imposing a schedule on me. Keeping my job doesn’t require my presence during official office hours anymore. Since I determine my own schedule, I can do whatever I want, whenever I want. It’s not a license to slack off and take vacations every week, of course. My income depends on the output of my efforts.

    The thing is, my time usage wasn’t very productive or balanced, and it hasn’t been for months. If I spent time on game development, I’d find that my writing would slip. If I wrote, I’d find that magazines and books would pile up in my inbox. If I read, I’d realize that I almost missed paying an important bill. Coinciding with the time I started preproduction for this project, I realized that I needed to do something to change my situation. To make my productivity a bit more predictable, I created a regular set of hours for myself. Until I had a game to sell, I wasn’t going to make any money, so production took up the lion’s share of the time I spent in a day. To ensure that there was balance between game development and everything else I wanted to get done, I gave myself regular hours for writing, reading, and organization. I use Google Calendar to setup recurring events. You can see an example of my day below:

    Regular Hours I discovered I wasn’t very good about waking up early enough for the morning stretches part, which is something I want to work on next month, but I tried to stick to the schedule. If I missed stretches, I wasn’t making it up at the expense of being late for game development. If I was late for game development, I wasn’t going to encroach on writing time. If I did make such allowances, it would destroy the whole point. For the most part I stuck to the schedule, which meant I was doing about 4-5 hours of game development per day, an hour of writing per day, an hour of business or game development reading per day, and an hour of organization per day. While part of me wondered if I needed more time dedicated to game development, the balance allowed me the time I wanted to learn, share, and prevent things from slipping through the cracks. While I might tweak the hours going forward, I definitely prefer this self-imposed, organized, and regular schedule over letting each day’s activities be determined by whim.

  3. Agile Scheduling As Early Warning System. Once again, I’m pleased with the knowledge I learned from using nothing more than a couple of cork boards, some index cards, and pins. Before the project started in earnest, I created an estimate of the work I needed to do as well as an estimate of how much I thought I could do per week. As the weeks passed, I realized how poorly I was doing in terms of keeping with the schedule.

    I wrote about it in Agile Alert: Slow Project Progress as well as Balancing Current and Future Needs, but the point was that without using story cards and a burndown chart, I wouldn’t have any idea when this project would be finished or what I could do to improve my situation. It allowed me to make project decisions earlier rather than later as well as weighing the advantages and disadvantages of delivering the finished project later.

What Went Wrong

  1. Not Planning Time For Art and Sound Work. The Jam version of the game features all art and sound created by me. I’m not that great of an artist, and I’m no sound designer. If this game is going to be polished, I was going to need to hire someone else to do the work. Of course, until I needed the higher quality assets, I could use my current art/sound assets as placeholders.

    The thing is, I never really had a plan for how I was going to go about finding contractors to provide the replacements. For a project that was originally expected to be sold by the end of the month, I should have had a plan in place for getting all of the final polish in. It would have been hard to ask for finished art when the game itself was nowhere near playable, so it isn’t a total negative, but I could have started a search for artists and composers. At the very least, I could have looked into pre-made art and sound packages. Otherwise, I would be spending a lot of time learning how to create half-way decent art and settling for lame sound effects and no music.

  2. Underestimating the Complexity of the Software Architecture Hacking a game together in a weekend is relatively easy because the code is prototype-quality. It’s meant to be used for a few days, and you don’t need to worry about maintenance or future updates. The future is mere minutes later, and then it is over. For the October Challenge, I wasn’t interested in a single sale. I was interested in the health of my business. When there is one sale, I expect more to come later, and so I wanted to make high-quality software that is easy to provide support for.

    Unfortunately, I didn’t realize until late in the month how little experience I have with creating a full-fledged project from scratch. When all of the code is in a single, monolithic file with almost no external data driving it, it takes no work to determine what data structures should live where. When you’re working on software with flexibility and maintenance in mind, it’s a completely different mindset. Since I didn’t have much in the way of reusable code that was of the quality I desired, I was spending a lot more time working on infrastructure and scaffolding than I expected. I could write an individual piece of code well enough, but I had very little experience with knowing what individual pieces of code I needed to write in the first place.

    Also, with unit testing, the code that “works” would only work in tests, whereas the actual game still needed a number of other parts of the project finished before I could see anything that looked like progress on the screen. It’s good to see the green bar as often as I do, but it’s frustrating that the actual game doesn’t do anything more than it did the week before. I now understand what the stakeholders felt like at my last day job whenever I would say “Yes, I’m making great progress. No, there’s nothing new for you to see yet.” Sometimes you just need to throw something, anything, up on the screen every once in awhile.

  3. Not Being Decisive About What Game I Was Making. Since I wanted the game to be data-driven and scriptable, I thought that the major design work would take place with malleable data rather than rigid code. I wanted multiple game modes, and I had an idea of what each one might include. I thought that there could be single level instances as well as campaigns of levels that tie together somehow. I wanted victory and defeat conditions to be scriptable, but I also wanted some core mechanics to be as well. For instance, while the basic game might provide all of the towers up front for the player with no way to retake a tower that the hero has liberated, a different level configuration could require the player to conquer independent towers first and provide the ability to retake them if they are liberated.

    The problem with the game designer’s “I want it all” approach is that it put a lot of pressure on the programmer to make the software incredibly flexible. Since the designer and the programmer positions are both filled by me, it meant that I was asking a lot of myself. I knew better than to make a game engine that could be any genre, any game, but I didn’t realize that making a Stop That Hero! engine that essentially allowed for endless variety of game modes and mechanics wasn’t any less difficult. While the previous sentence sounds like it should have been self-evident, I didn’t have 20/20 hindsight to help me write it back when this project started. It seemed to be so simple. So long as the game was driven by data and scripts, I could make any mode I wanted.

    At the beginning of the project, I had supposedly made a decision to implement a particular game mode as part of the version 1.0 of the game, but I didn’t want to give up on the flexibility to do any of the others I had thought of. If I really wanted to hit the end of the month deadline, I probably could have pared down the feature requirements list. Flexibility can be retroactively coded in after 1.0 was released. Instead, I gave myself the impossible task of getting everything done and hoping it could be done in time without regard to how long it would take. It’s no wonder the schedule slipped.

  4. Getting Into a Developer Funk. Towards the end of the month, I hit a point where I could not make forward progress no matter how much I wanted to do so. I was second-guessing myself, partly because I probably felt overwhelmed with the architecture work, and partly because I made the mistake of doing research and development on the state of the art for component-based game objects. Basically, I wanted a component-based game object system since it would help me in my quest for a flexible and data-driven game, but I learned a number of competing ideas, and I found that any new code I wanted to write had all of these new mental filters in the way. Data-driven Programming vs Object-oriented Programming, game objects vs game entities, encapsulation vs getting things done, etc. It was a lot to take in, and I had difficulty getting all of the new information to settle down in my head.

    When I finally abandoned my attempt at the component-based system, I still couldn’t make progress on a less flexible entity system. How hard can this be? I did a working version in the original Jam version of the game, right? Well, once again, I wasn’t throwing all variables and data structures in the same class anymore. I couldn’t make decisions because I was paralyzed with the fear that I would make a poor one.

    I experienced a smaller version of this when I was getting into unit testing for the first time. For instance, I’m not used to the need for as much Dependency Injection as I did on test-driven work, and I was losing confidence that I was doing software development “right”. Early in a project, you might think of one reference to an interface that an object needs, so you provide that reference in the constructor of the object. Weeks later, and you might have 4, 5, or 6 such references as parameters, and suddenly you’re faced with the need for another one. At this point, it starts to feel wrong, especially since it can hard to keep it all straight in my head. Since I was working alone, I didn’t feel I had anyone to discuss it with, so I would have to move forward reluctantly. Eventually, the fear that I was doing something wrong paralyzed me.

    I did eventually get out of my funk and started making forward progress again, but it was only after a long phone conversation with a more software architecture-knowledgeable friend. Thanks, Larry! When you think you’re lost, sometimes all you need is some guidance and advice.

What I Learned

  1. How Much Technology I Needed and Didn’t Have. If I didn’t care about making my game available for GNU/Linux or avoiding proprietary solutions, I could probably have used technology such as GameMaker, Unity, or Flash to make a game. They offer plenty of game development-specific support, either directly or through libraries. Instead, I had to do a lot of work myself. While libSDL provided a number of basic hardware abstraction services, I still needed to write a lot more game-specific code.

    Again, I understood I wasn’t writing an end-all, be-all game engine, but I still lacked a repertoire of code to help me make the game. A lot of my time was spent laying down the basic infrastructure to allow me to work on the game. It’s odd since I can easily hack together a working game in a weekend, but when the project’s seriousness demands more, I found that I lacked the basics. While I knew what tools I would use at a fundamental level, such as which compilers and libraries I would use, I didn’t realize I needed to figure out what technology I needed to create. If I did, I probably would have planned for it in the schedule or I would have pursued a simpler project in the first place. For instance, while I knew I needed AI pathfinding, it didn’t occur to me that I’d need something more sophisticated to track all of the objects in my game than a bunch of independent collections of data.

  2. How Much I Still Need to Learn Between software architecture and the basics of game engine requirements, I hit a number of stumbling blocks that forced me to pull books off of shelves and search online for answers. I would have thought I knew enough about game development to make a game, but I had underestimated how much more work there was to take an otherwise working game that was hacked together and writing the code in a way that made it easier to debug, fix, and change.

    Working with others would help us all glean knowledge from each other, but as an indie, I’m going to need to interact with game developers in more than a social way. Also, I need to get better at project estimations. I was too optimistic this time around.

  3. How Difficult It Is To Talk About Game Development When It Is Not a Hack Fest. Most of the people I talked to on IRC were helpful when it came to particular aspects of what I was doing, but they almost all seemed to perceive that I was hampering my efforts with the use of unit tests and the desire for high code quality. “Just finish the game” is easy to say when you’re working on an LD48 competition entry for fun, but when your business depends partly on the ability to provide customer support without introducing bugs and problems, it’s not just fun and games anymore.

    Selling a copy would have been nice at the end of the month, but I also want the ability to sell more copies later. Selling a hard-to-support game isn’t a good way to improve my ability to stay an indie long term. The October Challenge wasn’t an end in itself for me. I saw it as a kick in the pants to get me focused on moving my business forward. By and large, it worked. I have a project that is still moving forward even if it is at a slower rate than I would like. Still, it was difficult at times to talk about game development as a business-related endeavor since not everyone had the same long-term goals.

As I said, I am continuing this project even though the October Challenge is over. Using the project data so far and assuming I continue to work at the same rate, I can expect to finish the game by December. It’s still just an estimate, but it is a much better informed one than the one I made at the beginning of the project. While it is disappointing that I couldn’t finish this project in the month, I am pleased with some things. My schedule helped me make consistent progress, and I have a much better understanding of the game’s design questions since I spent so much time thinking about them before the month started. Still, while I had done a simple technical feasibility assessment, I needed to do a deeper study to realize all of the things I needed for this project. Basically, as much as I tried to plan ahead, there were some things that just weren’t on my radar. I know better now. Besides having done a lot of work for this project that can be reused, future projects should benefit from pursuing a better understanding of their technology requirements.

Categories
Game Development Games Marketing/Business Personal Development

Results of the Ludum Dare October Challenge

November begins, and that means the Ludum Dare October Challenge is over. Creating a game and selling a single copy was the goal, and you can see the results of the 2010 October Challenge.

At the time of this writing, there were 13 19 20 entries submitted. Some of the games are still awaiting their first bit of revenue, but others have sold their first copies as soon as release day!

Congratulations to everyone who has risen to the challenge!

Categories
Game Development Geek / Technical

State of the Art Game Objects

Years ago, I wrote about Component-based Game Design, in which I talked about the advantages of breaking down your game objects into components. Inspiration came from a number of places, including:

My Experience

Over four years ago, I even managed to implement a simple test program as part of my application for my last day job, and at the time I thought it was easy and fun to do. The hardest part was setting up all of the basic infrastructure to support registering components.

In four years, however, I never wrote code that resembled that test program.

Why not? Because it turned out that it wasn’t all that easy or fun, and I didn’t like the idea of making a full game with it because even a small test program was a bit painful to build up. My implementation of a board game was heavily based on Hannah’s concepts of States and Actions, so it might be a bit more complex than what is typically considered the state of the art. Actually, it’s probably more accurate to say that the implementation was based on my understanding of Hannah’s article, so I probably did things terribly wrong and made it more painful than it had to be.

Each Action typically interacted with multiple States, and so there was a lot of dynamic_cast calls. Practically speaking, adding a new State and its associated Action meant a lot more work than I would have liked. I might as well have stuck with the monolithic game object, and in the years following my original post on the topic, I pretty much did. Most of my projects were small in scope and had very specific designs that didn’t change much, and the code base was manageable enough that it wasn’t a problem when the designs did change.

The Motivation

With Stop That Hero!, I wanted the flexibility to change the design of the game as it was being developed. That isn’t to say that I wanted the ability to make a first-person shooter halfway through the project, but I did want the option of experimenting with new monster types, different player actions, and objectives for a level. I want to be able to change the design of the game without requiring me to change the code drastically. I also wanted the ability to drive the game through the data, which would allow me to create custom scenarios and interesting game experiences, and it would allow players to create their own mods.

I already understood the basic concept of component-based game objects. Instead of monolithic, inheritance-based objects that are hard to change, objects should be identifiers with the components that make up an object being tied to that object identifier. If the design changes, the impact on the project might simply be the assigning or removing of components. For instance, I could have enemies that walk on land or fly in the air. I could introduce a new amphibious enemy by assigning it the ability to walk on land and create a new component related to swimming in water. The code involved is minimal and low-impact on the rest of the project.

What I didn’t understand was how to go about implementing a component-based game object system that wasn’t cumbersome and annoying to use. In my experience, having ready-made components was great for game design, but creating the components and the system to use them was a pain.

The Research

And so, once again, I find myself looking into component-based game design. I found quite a few more resources over the span of a few days as well as some that I have read in the last few years. I’ll quickly list them in case you’re interested in pursuing this topic yourself:

Terrance Cohen’s presentation led me to discover that Insomniac Games has a public-facing research and development page, which led me to his presentation Three Big Lies: Typical Design Failures in Game Programming, which introduced me to the concept of data-oriented design.

And from there, I realized I needed to clarify what it was that I was looking for.

I wanted to learn how to do data-driven, component-based game development in a relatively simple way. What I realized was that I was looking for three different things that had little to do with each other.

One, I wanted my game to be data-driven, which isn’t all that hard. So long as the game is pulling in data from somewhere and acting on that data, it’s data-driven. It’s possible to have the inheritance-based hierarchy of game objects and still run the game based on external data, and it’s possible to use that external data for component-based systems.

Two, I wanted my game design to be easy to change. A component-based system is superior to the inheritance-based one in this regard. With an inheritance-based system, any design change might impact the carefully-planned hierarchy. It can quickly be hard to manage, and changes become more and more painful. Components are easier to change. Add them or remove them, and an object’s behavior changes, and it works on the fly as well.

Three, I wanted to figure out how to write the code for such a system without the complexity I dealt with last time. Seriously, dynamic_cast everywhere a component needed to talk to another component made the creation of new components quite painful. There had to be a new way.

Data-driven games are much more powerful with a component-based system, but it’s outside of the scope of what I want to focus on here. What I was most interested in was the answer to the question “What is the best way for me to implement a game object in my game?”, and frankly, it wasn’t enough to know I wanted components aggregated together. I wanted to know how.

Which brings me back to data-oriented design. According to DOD, the only purpose of code is to transform data. That’s it. Traditionally, programming was focused on algorithms and code, modeling the problem in terms of classes and objects. The problem is that the models tend to add more complexity to the original problem of modifying data.

Now, data-oriented design isn’t the same thing as data-driven design. The former is about programming, while the latter is about game design. See Noel Llopis’ Data-Oriented Design (Or Why You Might Be Shooting Yourself in The Foot With OOP):

OOP is so ingrained in the current game development culture that it’s hard to think beyond objects when thinking about a game. After all, we’ve been creating classes representing vehicles, players, and state machines for many years. What are the alternatives? Procedural programming? Functional languages? Exotic programming languages?

Data-oriented design is a different way to approach program design that addresses all these problems. Procedural programming focuses on procedure calls as its main element, and OOP deals primarily with objects. Notice that the main focus of both approaches is code: plain procedures (or functions) in one case, and grouped code associated with some internal state in the other. Data-oriented design shifts the perspective of programming from objects to the data itself: The type of the data, how it is laid out in memory, and how it will be read and processed in the game.

One thing that wasn’t clear to me while doing all this research is that data-oriented design is not terribly compatible with object-oriented programming, and since most of us game developers know OOP as THE way to program, it’s difficult to see it any other way.

The thing is, it isn’t a normally a problem. OOP can still get you to a correct implementation, especially when performance isn’t your primary concern. The code will run the way it is expected. One of the major advantages touted by all of the data-oriented design articles I found was efficiency. As an indie game developer who doesn’t work on games that push the processor or memory requirements of my customers’ machines, I’m not usually worried about cache thrashing or performance issues. I’m not concerned about throughput on PS3 Cell processors or processing shaders quickly on the GPU. I’m not one of those people who thinks that processor speed is fast enough and memory is large enough for whatever horrible implementation I can come up with, but at the same time, I am not using the Crysis engine and gigabytes of data for my games. I don’t currently make games that take advantage of parallel processing and I most definitely wasn’t going to worry about the cost of calling virtual functions, so initially data-oriented design wasn’t very appealing.

But why I kept pursuing information on it was that it was supposed to be great for unit testing and modularity. Since I’m a big fan of unit tests, being able to write them more easily and with less dependencies would be a huge win. Being able to write simpler code would be another huge win because it can help in the creation of components.

So bottom line: data-oriented design looks like a fantastic way to help me develop a game object system. The code will be simpler and easier to test, and I get the extra benefits of having more efficient code! Nice!

Well, at least at a high level. I still need to figure out what it all means when I don’t have the benefit of an existing company’s proprietary engine. I figured that I needed to explore this data-oriented design thing a bit more.

EDIT: Here’s a talk by Andrew Kelley with practical ways to implement data-oriented design: Andrew Kelley – Practical DOD

The first three examples helped me understand how the actual code might be laid out, but it was that last one that really made me understand where OOP is causing problems. It focuses mainly on performance problems related to caching, but the idea of performing a bunch of unrelated actions on a single object at a time versus doing one action for lots of objects at once was really made clear, especially after seeing images 12 and 30-32.

The Frustration

Unless you’re one of the mainstream game developers who have used or implemented a component-based system as part of your job, it seems getting started is the hard part. Game development forums have a number of threads in which people are convinced of the benefits but don’t know how to get a system built.

The article in Game Programming Gems 5 by Bjarne Rene has sample code on the book’s CD, and the good news is that it is a complete solution, but it seems that the complexity of inter-component communication can be a problem. Plus, is it still relevant? It seems as if game developers have moved away from components that perform actions, at least according to what I’ve read.

I haven’t had a chance to look at Game Programming Gems 6, but apparently there is an article on game objects there as well, although it sounds like there is no example code so I’m not sure how hard it would be to follow. The blog T=Machine argues that there is a difference between Entity Systems and component-based systems. Fine, but your entity system is still aggregating components, so regardless of the differences, I need to know how to create a component system.

It seems that anytime there is code in any article or presentation, it’s incomplete or hard to follow. The article might say that you should use IDs and not create an actual object class, and yet the example code has a class. It might show a class deriving from some base that was never introduced or create a function signature without an explanation for why it is there. I almost wish the articles would unit test their way through their sample code just so I could follow along with the author’s intent. Also, it seems that there is no shortage of article series on the subject that never get finished. Some examples are MMO-specific, some are concerned about performance, and none seem straightforward. One article will suggest doing something that another says you shouldn’t do.

And so I felt like pulling my hair out when I sat down to try to implement my own system. At a high, conceptual level, it makes sense to me that an object is nothing but an ID, and it’s the components aggregated together that make up a game object. I understand that I should be able to create an object by creating components, associating them with the object ID, and adding those components to some manager. What was difficult was implementation, and part of the difficulty was about ownership of the data.

I had written an entity manager with a couple of components, only to throw it away after becoming frustrated with how limited it was. I apologize if you’ve read this far and were hoping for more insight into a component-based system. It was too much for me at this time, and I had to stop if I wanted to make progress on my game.

Ultimately, it seems that the component-based system isn’t going to happen, but I need to figure out how to make progress on the game itself. Somehow, in learning a lot more about components, entity systems, and data-oriented design, I feel frustrated and incompetent. Every time I want to write code, I have a dozen different alarms going off in my head warning me that what I want to do isn’t what this author suggests or is against what that author says. My existing code, which I was happy with before, is now feeling too constricting. Whenever I try to make progress, I feel like I have game developer’s block. I can’t see the next step, and even when I think I have, I don’t know how to start. It’s a bizarre feeling.

This post came off more whiny than I would have liked, but I’m not blaming anyone or feeling entitled. I’m just frustrated, and I’m trying to figure out why.

Categories
Game Design Game Development Geek / Technical

Stop That Hero! Sprite Rendering Questions

In the previous post, I reported that levels could be loaded and rendered. So why isn’t it drawing the towers and chests? The short answer is that I didn’t get to them yet, but in all seriousness, it took a little thinking before I could start.

In the original implementation, almost everything was done in a single file of code. The code to draw a tower was:

pHardwareLayer->renderSprite(towerSpriteName, m_towerLocations.at(towerIndex).first * TILE_WIDTH + WORLD_X_START, m_towerLocations.at(towerIndex).second * TILE_HEIGHT + WORLD_Y_START);

TILE_WIDTH and TILE_HEIGHT were each 16, since each tile was 16×16. WORLD_X_START was 0 since it started drawing from the left side of the screen, and WORLD_Y_START was 87 since the UI was drawn at the top.

So depending on which tower I was drawing, I would get the x and y world map offsets, then multiply them by the tile dimensions, and offset by the top left corner of where the world was being rendered.

Why can’t I do the same thing now? Because I didn’t want to hack out everything in one file. A tower is no longer represented by data strewn across different data structures in the game code. A tower is now its own class. A Tower class has these members:

Point m_position;
std::string m_sprite;
int m_type;
int m_status;

There are more variables associated with monster creation and ownership status, but these are the variables relevant to this post.

The Problem

To draw a Tower, I could use the sprite specified by the name in m_sprite and the coordinates in m_position. The problem is that m_position isn’t screen coordinates. It’s map coordinates.

No problem. I’ll change m_position so that it specifies the screen coordinates.

Except m_position is being used in pathfinding, and it is important that it represents a specific tile in the world.

No problem. I’ll just multiply m_position by the tile dimensions, just like in the original implementation.

Er, but, why should the Tower know anything about the tile dimensions? It should only know about towers. Maybe it knows how large it is in terms of tiles, but why should it know how large a tile is? It doesn’t need to, except when it renders a sprite.

No problem. I’ll provide a second Point variable called m_spritePosition which represents its screen coordinates.

That would probably work for stationary towers, but what happens when I need to render moving entities such as Slimes? Unless the on-screen position is mathematically tied to the entity’s position, I can see those two numbers diverging. I could update both pieces of data each time I update one, but what a pain that would be!

The Solution

Create a Sprite class to encapsulate all of it, and let the Sprite class worry about where to render.

Since towers are now encapsulated in their own class, it makes sense that the way I render them (and almost everything else in the game!) should be encapsulated somewhere. The Tower class no longer has its data members polluted with a bunch of members related to sprite drawing, and it doesn’t need to worry about what to do with that data, making its interface and internals a bit cleaner. Also, Sprite classes can be reused for other objects, such as monsters and treasure chests, in a standard way.

To handle the rendering of images, I created a SpriteImage class with the following members and commented explanation:

Point m_position; // The sprite's position
std::string m_imageName; // Name of the sprite in the sprite collection which stores this particular image.
Rectangle m_imageRect; // What rectangular area in that sprite that holds this particular image
IViewPort * m_viewPort; // Explanation to follow.

At first, this solution doesn’t seem to solve the major problem identified above. It looks like the last problem in that the tower’s position and the tower sprite’s position are stored in two different areas.

The trick is that a Sprite defaults to a 1 to 1 mapping between its position and the screen coordinates, but it’s possible to scale it between arbitrary mappings, too! The secret is in m_viewPort.

If a SpriteImage is given a view port, it will scale its position based on what the view port says the scale should be.

How is this useful? Imagine having an 800×600 screen resolution, and you wanted to render a UI button near the bottom right corner. You could make a SpriteImage of a button at position (700, 500), and it would probably work fine.

But then what if you change the screen resolution to 400×300? It’s possible that you’ll port your game to a mobile device with such a resolution. The button would render off of the viewable screen. You’d have to change the button location manually in order to see it at the bottom right corner again. This goes for every image in the game. It could be tedious and error-prone.

Alternatively, you could use a view port that knows the screen resolution is 800×600, and it could be configured to scale based on a percentage. Now, instead of placing a button at (700, 500), you’d set its position at (87.5%, 83.3%). Then, if the screen resolution changes, you simply change the view port, and any sprites associated with it would know the correct scale to use! It’s very powerful and easy to move elements of the screen by horizontal and vertical percentages.

That’s great for rendering sprites anywhere on the screen, but what about my example above? How does a Tower draw on an arbitrarily-sized and arbitrarily-positioned area of the screen, and how does it know where to do so if its position is based on tile position?

As I said, the view port can do arbitrary mappings. In my case, if the world is made up of 50 tiles x 33 tiles, and the area to render everything is 800×528, and it is offset from the top of the screen by (0,87), how would a sprite use this information? Offsetting is easy so I’ll address it first. Wherever a sprite ends up wanting to render itself after scaling, the view port will tell it to move down the screen 87 pixels. As I said before, I use this offset to give room for the UI at the top.

Scaling is almost exactly as it was at the top of the screen. Mapping 50 tiles to 800 pixels requires multiplying by 16, which is the size of each tile. Similarly, 33 maps to 528 with a factor of 16. So if a Tower is set at (50, 33), its going to render at the bottom of the viewable area, whereas a Tower at (25, 0) would be centered at the top just under the UI. Below is a quick example of how I load level data from tiny PNGs.

Level Data To World Map Rendering

If you click on the image above, you should be able to get a better idea. The level is described in the small PNG that consists of almost all green pixels and a single white pixel in the middle. When this level data gets loaded, what you see on the screen is a lot of grass tiles and a single tower where the white pixel corresponds. While the PNG is 50×33 pixels, the tower renders in the correct location on the 800×528 view port, even though the tower’s location is in terms of the 50×33 level.

And does it work for moving objects? Absolutely! Let’s say I have a Slime monster located at (2, 3) on the world map, which corresponds to (32, 48) on the screen. When a slime moves to the right, I can’t simply change its position to (3, 3). It would jump the entire width of a tile to get there! Slimes are slow. So why not move it in fractional increments? The scaling still works. A slime moved to (2.1, 3) would correspond with the sprite rendering at (33, 48), which is one pixel over. Technically, it would render at (33.6, 48), but fractional pixels don’t make sense, so for purposes of rendering, we can truncate or round it to the nearest integer.

Again, this view port mapping allows me to do spatial logic at an arbitrary level and not worry about the screen resolution. The only thing I would have to worry about is loading a set of sprites that make sense at lower and higher resolutions. Otherwise, sprites would either overlap or have space in between them. This functionality could also be used to render minimaps and allow zooming and panning.

I like this implementation because the sprites don’t need to have any special logic about what they represent. They just need to know what scale and offsets they’re being rendered at. The object that owns the towers knows where it wants them to go, so it can be in charge of the view port. Tower positions can still be used in pathfinding, and the sprites can still render correctly. The only tricky part might be knowing when I’m loading a sprite at the default scale of the screen resolution and when I’m loading one based on a view port’s scale. To render an image centered at the far right of an 800×600 screen, a sprite at (700, 300) makes sense, but it wouldn’t work if the scale settings assume that positions will be specified in percentages. It would be rendered far off to the right by 700 screen lengths! To specify it in percentages using pixels, (700/800, 300/600) would work.

Also, I’m really happy to have a higher-level sprite class. How did I survive so long without one?