Sunday, 30 January 2011

One weird aspect of my career as a programmer is that I never worked under someone with more experience. I started Ronimo Games right out of school and was the only programmer, and thus directly the lead. Since I did my internship as a 3Dartist, this means I never saw how other companies handle their programming. The result is that all of the coding style decisions at Ronimo are just based on my own opinion, and I may be missing some important things that I simply never thought about.

Interestingly, we have been hiring some programmers in the past year, growing the team from just me to five full-time programmers next March. Although the two programmers who have already been working with us for the past year (Ted and Maarten) are former interns of mine, it turned out that as soon as we hired them as real employees, they actually had Opinions. Which is great, because not just blindly doing what I come up with greatly helps against tunnel visions!

One important thing I learned that way recently, is that resetting and reusing objects is error prone, and that a structural change can avoid this.

Let me explain this through an example. In Ronimo's Secret New Game (tm), the player can control a character that when killed, will respawn after a while. My method for doing this, was to hide the character on death, and then reset him when he is respawned, and make him visible again so that the player can continue playing with him.

The problem with this is, that it is easy for the programmer to forget some elements when hiding and resetting. The character consists of many graphical elements, and since they are in very different categories (like healthbar, shadow, character, special effects, etc.), it is not feasible to put all of them in a single list. So when programming the hiding, I need to think of all these elements. The same kind of issue occurs when resetting: many aspects need to be reset (like combo counters, cooldowns on actions, poison time remaining, etc.), and again I need to think of all of them when resetting.

Adding new features is even worse: I always need to remember to add them to the hiding function and to the resetting function. Forgetting one of them results in a bug. Not hiding something is an easy bug to spot, but not resetting something is a lot more difficult to notice, since many effects may usually time out before the respawn timer is over. So it is easy to overlook that sometimes a cooldown may not have expired yet when the player respawns.

This may seem like a subtle and irrelevant issue, but it is very easy to accidentally introduce bugs here when developing a game with more then one programmer, since not everyone may know about these details. So I had been struggling with this for a while, without being able to think of a good solution.

Recenlty, my colleague Maarten came up with a really simple fix: why not completely delete the character on death, and re-create him on respawn? Now we don't need to hide or reset anything. Win!

It turns out that this simple principle actually applies to a lot of things. For example, in Swords & Soldiers, we create all the menus when the game starts, and then just hide them all, except for the one that is currently in view. But why not simply delete them entirely?

Kind of strange that I hadn't thought of this myself, really!

Experienced C++ programmers may counter this argument by saying that dynamic memory allocation costs performance, so resetting is more efficient. This is probably true in most cases. However, I consider design that prohibits bugs to be a lot more important than performance. Current console hardware is very fast and we are not trying to make the next Killzone or Uncharted here.

Anyway, this could also be implemented using placement new (which constructs objects on a piece of memory that you allocated before, instead of requesting new memory). Finally, we have a really fast custom memory manager at Ronimo, so small allocations (up to 256 bytes) are very fast anyway.

Although I didn't think of this re-creation trick myself, it very much fits the coding style at Ronimo: we always try to find structures that make it as difficult as possible to accidentally introduce bugs. Destroying and re-creating objects instead of resetting and reusing them is a great example of this philosophy! Although this example is no super-complex science, I think that one of the most important skills for any programmer is to constantly look at your own code for these kinds of small improvements.

Saturday, 22 January 2011

(Due to moving to a new city (Utrecht), I didn't have the time to gather balancing data for Swords & Soldiers for the post I promised last week. So that topic will be for another time!)

A little while ago I was asked to judge a couple of student game projects from the Utrecht School of the Arts. Seeing a glimpse of the group dynamics that happen within these projects is mightily interesting!

The main thing I saw in that group, was that they had no idea what the game designer's role should be. I think the things that went wrong in their team, are nice examples of how I think a game designer should function. Of course, there are many ways in which a game development team can function, but this is how I personally see it.

"I tried pitching my concepts to the rest of the team, but they didn't want to build them. Could you teach me how to communicate my ideas better?" - the game designer

No. This is entirely the wrong way of thinking. In a team of creative people, the game designer does not have to be the one to come up with the basic concepts. This should be a group process. Through brainstorming and things like that, ideas should come up that the entire team likes. Anyone can have good ideas, not just the game designer.

Many game design students seem to think that coming up with ideas is the main job of the game designer. It is not. The idea is just 1% of the development process and the game designer is not better at this than the other people in the team.

"For the control scheme I researched how other games did this, implemented it, and tweaked the settings to make it feel good. I worked so hard, are you not impressed?" - the programmer

No. This programmer worked hard, but on the wrong things. To do their job, game designers need tools from the programmer. So the programmer should implement the control scheme, but he should not be the one to tweak and experiment with it. The main role of the programmer is to empower the rest of the team to do their job. Keep that in mind at all times! Make settings files, or something like that, and let the game designer do his job!

"We divided such tasks, so I was in charge of the playtesting sessions." - the 3D artist

Why split these tasks? In small teams, it is often difficult enough anyway to constantly keep the game designer busy, since he is probably often waiting for new features from the programmer. Creating questionnaires and analysing playtests is definitely something the game designer should be doing!

"The level was finished way too late, because no one was in charge of level design." - the team

Euhm, what? You have a game designer in your team, why is he not automatically in charge of the level design? I know that in large teams, game designers and level designers have separate roles, but in smaller team, I think they should usually be one and the same person. It is quite rare for a small game concept to require enough game design work to keep a game designer occupied full-time during the entire project. Since level design is all about gameplay anyway, the game designer is a natural fit to also be a level designer.

Also, I can think of dozens of games where there is hardly any role for the game designer at all if he would not do level design as well. Just think of the old Mario games. Almost all design hours there would be in the level design, hardly anything in the game design!

"I'm a game designer, I cannot create things myself." - the game designer

Learn some tools, RIGHT NOW! It sucks to always have to wait for a programmer who also needs to do other things. There are tons of tools that are fit for a game designer to create small prototypes. Create mods in the Starcraft II or the Unreal III editor, or create little playable thingies in Gamemaker or Virtools. Also, take scissors, paper and dice and create paper prototypes. Learn to make stuff!

"Then what does a game designer do?" - the game designer's mother

Let me give some examples:

tweak values (like walking speed, jumping height, health, etc.)

design levels and puzzles

design tutorials

organise and analyse playtests

balancing

research existing (similar) games

Finally, I'm going to end this blogpost with a nice little blunt remark of my own:

Thursday, 13 January 2011

We are growing our team a bit further and are looking for yet another programmer at Ronimo, to write platform-specific code for the Xbox 360 and Playstation 3! This time someone with good knowledge of C++ and a couple of years of programming experience (though not necessarily in the games industry). Click here for more info! ^-^

I guess anyone who has ever played a strategy game, has an idea of how complex balancing the powers of three very different factions is. However, while we were developing Swords & Soldiers, I learned that there are several other forms of balance, and an RTS needs to achieve them all at once.

The balancing was done by my colleagues Olivier, Jasper, Fabian and Tom and I learned a lot of this from them. Especially Olivier is a hardcore Starcraft player and he brought in a lot of knowledge of what he had learned by following Blizzard's patches and articles on the topic over the years.

So, let's have a look at some of the many forms of balance in an RTS!

1. Faction balance

This is the standard balance that most people mean when they talk about balancing an RTS. Swords & Soldiers has three very different factions: the Vikings, Aztecs and Chinese each have different units and spells and even collect mana for their magic in different ways. The factions may be very different, but if you are a good player, then you should be able to win with each of them. So who wins is decided by your skill, not by which faction you play.

2. Beginner balance

While standard balancing looks at the situation for good players, it is also interesting to look at beginners. How difficult is it to play with a faction at all? In Swords & Soldiers, we deliberately chose to not make the game balanced for beginners. The Vikings are our easiest faction to understand the basic strategies, while the Chinese are a lot more difficult to play with. We wanted to add variation and spice to the game by making the factions different in complexity of the core strategies.

Interestingly, becoming really good is most difficult with the Vikings. Although their basic strategies are easy to understand, their pro strategies are probably the most complex, requiring more skills and units to be combined.

3. Balance between tactics

Each faction should have many different useful tactics, and most of the time, several viable options should be there for the user to choose from. If a faction is only strong with one specific tactic, then you always play that and the game gets boring. Also, the opponent will know exactly what to expect. So there is not just the balance between factions, but also the balance inside a single faction, where all units and many tactics should be of use.

4. Balance on different maps

When the game is balanced on one map, the balance might be broken on another. For example, in Swords & Soldiers, the Chinese need towers to get mana, so a large map with lots of room to build and defend towers makes them stronger. To reduce the complexity of balancing, we balanced for one particular map (the first medium map) and added the other maps for flavour and variation. In online multiplayer, we only allow for 4 of the 9 skirmish maps, because we think the balance is best on those 4 maps.

5. Early game balance versus late game balance

At the start of a match, you don't have a lot of upgrades yet and your choices are limited. The balance at this point is totally different from late in the game, when both players have upgraded all their spells and units. A balance where one faction is stronger early and the other late is not good: if the early rushes are over, you will already know who is probably going to win. That's pretty boring. On the other hand: having some variation in how fast you can rush does add variation between the factions, so making this completely equal might make the game boring as well!

6. The amount of fun in the balance

This type of balancing is really difficult to measure, but quite easy to feel: some tactics are just lame. Spamming a single unit all the time is really boring, so that better not be a good tactic! The following Viking tactic is an example of how things should be: a very strong combo the Vikings can do is to build Frosthammer units (who do area of effect damage and stun), then freeze a large group of enemies with Snowstorm, and then ram the Frosthammers into the frozen enemies with Rage. Doing this requires skill, speed and knowledge, and is pretty strong, so the player will probably feel great doing this!

7. The amount of luck in the balance

A Chinese player can start out with melee units or ranged units. At one point we had a balance in which, depending on the opponent's opening move, this would mean a certain win or a certain loose. This is balanced: you have a 50% chance that the enemy happens to choose the opening move that lets you win. However, this is based purely on luck and thus requires no skill at all. So even though the faction balance was good at this point, this balance was broken!

A little bit of luck is a good thing to have in a game, though. Players who loose a match tend to feel a lot worse if they know it is entirely their fault. If there is also a little bit of luck involved, then they can blame their bad luck and feel less bad about their skills. Taken to its extreme, luck is why a game like Mario Kart (which features tons of luck through the upgrades) is so enjoyable for beginners: it still lets them win once in a while against better players.

Complexinat0ring!

As you can see, balance has many faces. The biggest problem with it, is that even the smallest change might affect all of the types of balance at the same time, plus it probably affects several match-ups of factions as well. Even for a small change, it is practically impossible to predict what effects it will have on the whole. Therefore, it is incredibly difficult to get the balance right for all of these aspects at the same time.

In terms of balancing, Ronimo's Secret New Game is a lot more complex than Swords & Soldiers, so I am really curious to see how well we can pull it off there!

Since balance is such an interesting and complex topic, next week I am going to talk about some of the pitfals of analysing it, both for developers, and for players and reviewers.

Saturday, 8 January 2011

Last week I explained how we ended up with Halo 2-style behaviour trees in Swords & Soldiers, but I didn't really dive into how they actually work. So now let's have a closer look at how we worked with them.

The small AI above gives a nice example of how our AIs work. The first thing to note here, is that behaviour trees are based on priorities. It is assumed that the AI will always want to perform the top-most action and will not look any further if that action can be executed. In this case, the action at the top is shooting lightning at a Necromancer (useAbility). Necromancers create lots of skeletons, so killing them first is usually a good idea.

To make this priority system work, the action at the top must have strong requirements, for otherwise the actions below it will never be executed. In this example, this is indeed the case: lightning is only used if an enemy Necromancer is actually near, and if you have enough mana to shoot lightning.

Since the AI must also mine gold, the action below that is building workers (createUnit). In Swords & Soldiers, players cannot have more than 10 workers, so as long as the AI has less then 10 workers (unitCount), and it has enough gold (goldAmount), it will build one worker every ten seconds (timeSinceLastUnit).

Finally, whenever not shooting lightning or building workers, this AI will just pump out as many Berserkers as possible (createUnit, at the bottom).

Now the fun of this system is that these behaviour trees are quite simple to work with, so you don't need a programmer to make them. You do need a designer who is good a logical thinking, but that is something I think every designer worth his salt should be good at in the first place.

The key to make keep these trees manageable, is to have enough blocks to work with, and to hide all complexities inside these blocks. A simple example is the unitNear block. The C++ code for this block looks for all the enemy Necromancers in the level and calculates the distance to each of them, to see whether there is a Necromancer near. The complexities of finding the Necromancers and such are hidden in a C++ class, and the designer doesn't have to know anything about that.

In Swords & Soldiers, I think we did not do this very well, though: our skirmish AI is incredibly large and complex. By having more and smarter conditions and actions to work with, I think our designers could have made some trees in half the size.

An interesting side-effect of these trees, is that they are also excellent for story scripting. Swords & Soldiers often triggers little cut-scenes with dialogues and such in the middle of a level. Deciding when the trigger those, can easily be done inside the behaviour tree, since the behaviour tree already has all these actions and conditions.

Initially, I was strongly against this idea, because I wanted to keep the AI clean and not mix it with cut-scenes. I thought this would get too messy and unclear. However, our designers convinced me to do it that way anyway. In retrospect they were completely right: it is very simple to trigger and play cutscenes with this system.

Finally, let's have a short look at a big change we made to the behaviour tree system for Ronimo's Secret New Game. While working on Swords & Soldiers, we struggled with how to make an AI do several things at once. It makes sense for an AI to build units while also casting spells at the same time. Because of the priority system, doing this kind of thing gets very messy. The priority system really only works if you always want to do exactly one thing at a time.

Working around this made the AIs pretty unreadable at some points, so for Ronimo's Secret New Game, we removed the priority system altogether. Instead, we now simply have a big if-else tree. It still has conditions and actions and looks very similar, but the AI does not stop when it has found an action it can execute. This is a lot more readable and also made it easier to add else-structures. In Swords & Soldiers, we essentially only had if-then structures, while we now also have if-then-else structures.

Let me conclude by saying that we are incredibly happy with our behaviour tree system and our own editor for it, and we will keep using this for several games to come.

In the end, this also means that the actual behaviour of our AIs is scripted by our game designers. For Swords & Soldiers this was mainly Jasper, but also a lot of it by Fabian and Tom. For me as a programmer, it is great to see how designers can make all kinds of awesome things with the tools we provide. Our designers constantly surprise me with how much more they can do with those tools than I myself considered even possible! So the real credit for the great AIs in Swords & Soldiers of course goes to our designers! ^-^