[Experienced tool developer Cyril Marlin outlines a method used to build an automated testing system for Wizarbox's SoBlonde, a Wii adventure game -- which reduced bugs, increased polish, and is flexible enough to be adapted to other genres.]
A game solver can find a way to play an adventure game to the end, giving help to testers, as you can see in this video, testing SoBlonde for the Wii.
In game development, one task that is time consuming is testing. There are many documents and tools covering unit tests, however here we'll cover higher-level tests and their problems.
Testing is a highly repetitive task, and many use cases should be checked. Each modification has a risk of breaking the game: engine, high level logic, or resources are each a potential source of problems. Furthermore, the diversity of situations adds an additional problem, since each change should be tested in every situation. This can add up to a lot of time.
It is imperative to test as soon as possible, and as completely as possible, because the later a bug is detected, the bigger an effect it will have on the game. Indeed, once checked into the game's source control system, the bug will be start to be mixed with other developers' changes.
If so, when discovered, it will take longer to find and fix, as its resolution may conflict with the work of others. Finally, the larger teams needed for big projects increases the number of concurrent bugs in a project.
This can sometimes be solved by specific testers during the whole project, but the repeatability of the task has serious implications on the team. Bad habits can slip in, such as only running a single path to complete the game, and/or skipping some parts. In these situations, testing may not find bugs that exist, but the cost of testing remains the same. Worse, testers can have a hard time paying attention, thanks to the fact that the task is too simple or repetitive.
However, as I have already said, continuous tests are necessary, because without them, the source control system is likely to become corrupted and impact other developers.
Sometimes we can use a hard-coded test script, which contains all the actions to perform. But this method is far from ideal, as it will often have problems:
As a solution, we automated some aspects of game testing, including:
The objective was to save time during development by removing the costs of creating and maintaining test scripts. Additionally, because testing has been performed throughout development, more potential bugs will have been found prior to entering QA.
The creation of a solver is closely linked to the data representation and logic operation of the game engine. We will describe below the scripting language that was developed to meet the production needs of the game SoBlonde: Back to the Island. It is a very simple script language, based on a set of C macros: The script associates, for each scene event, a list of actions to perform, with an
And for every action in the list:
The script system listens for events generated by the user or the game, and executes the associated action list. We can conditionally run of a sub-list of actions with conditions based on scripting variables declared globally. The fact that there is a global registry of variables is of importance, as we will see later. Here is an example:
// shell has not been captured and bernie is on left
PlayAnimation(ID_ACTOR_SUNNY, ANIMATION_SUNNY_SHRUG, false, false);
PlayAnimation(ID_ACTOR_SUNNY, ANIMATION_SUNNY_IDLE, true, false);
Parallel execution (as seen in the game) is out of our scope. We associate the "Activate" event on the entity BERNIE's to actions with condition BG01_PICK_BERNIE equal to 1.
The scripts are integrated in the game as modules: one for each scene (a scrolling screen) for easier editing. Being written in C, they are always available in memory. The entities, however, are not saved; their parameters (position, visible, interactive, etc.) are defined in the scene initialization stage. All variables are globals, so a game state is simply the script variables plus the content of the inventory.
The end result is very simple, and allowed rapid development of the game.