I'm fond of the idea of unit testing but I'm having trouble applying it to game programming. Games are highly stateful and often the code doesn't break itself into distinct units. In my experience, most functions mutate state rather than returning values.
Consider a simple action like playerJump(height)
. I'd love to have a test suite that checks a large variety of cases to make sure that jumping always works as expected. However this function will likely return no value and have the side effect of, player.velocity.y = -height
and checkCollisions(player)
. I can't think of a clear unit test to build around this.
Is unit testing just not viable in highly stateful applications like games? Are the advantages of unit testing so great that it would be worth programming games functionally?
Update:
Games from Within has a series of in depth articles about using Test Driven Development in games. I highly recommend them to anybody interested in this subject. Here is the first article:
http://gamesfromwithin.com/stepping-through-the-looking-glass-test-driven-game-development-part-1
Benefits of Unit testingIt forces you to separate your different features in testable classes. It also simplifies the re-usability of the code in future projects. – New code does not break existing code: less stress and risk when updating existing feature or adding new ones.
Unit tests are also especially useful when it comes to refactoring or re-writing a piece a code. If you have good unit tests coverage, you can refactor with confidence. Without unit tests, it is often hard to ensure the you didn't break anything.
All the unit tests are suddenly rendered useless. Some test code may be reused but all in all the entire test suite has to be rewritten. This means that unit tests increase maintenance liabilities because they are less resilient against code changes. Coupling between modules and their tests is introduced!
Often the code doesn't break itself into distinct units.
That's just poor design. The code doesn't break itself into anything. You, the designer, have to impose a structure on the code so that you can demonstrate that it actually works.
However, this function will likely return no value...
So?
...and have the side effect of, player.velocity.y = -height
and checkCollisions(player)
.
Then test for that.
I can't think of a clear unit test to build around this.
Why not? You just gave an excellent specification for the results of the function.
You might need a few mock objects to replace the full-blown Player with a simplified MockPlayer that's easier to test with.
But your specification of behavior was perfect. Just test for the things you described.
Unit tests can be useful for a lot of the low level libraries you may use with game code but I seriously doubt it is of much use for the higher level stuff. Games are usually simulations and rely on massive amounts of shared state which can't meaningfully be mocked up and tested in isolation. Often functions in games do not return any sort of value that you can instantly check but instead set a process in motion which should complete at some point in the future. Testing such behaviour is worthwhile but requires a significantly different approach to the unit test idea of testing pieces of code in isolation.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With