Looking at my engine I didn't want to have to start pulling things apart just to be able to unit test them. And unfortunately if you don't plan for TDD from the start a lot of the times this ends up happening as you try and figure out how to effectively test things. With that in mind I looked to new features that I wanted to add to my engine that I could test from the ground up.
The only major new addition that I had planned for my engine in the short term was a resource manager. Up to this point I've been dealing with so few textures and sounds in my game that I didn't really need one. But to keep things clean and tight when developing a game with the engine I figured it would be a good thing to have.
So yesterday I set about creating a resource manager just for textures to start off. The interesting thing about unit testing anything is that if you're testing a module that creates it's own data, in this case creating and loading a texture, it can be a bitch to setup without testing the rest of your engine at the same time. Say I wanted to test that the manager can successfully load a valid texture. At first glance to test this I need to have a valid texture and setup my D3D device so I can actually load it. This would end up taking forever which is the opposite of what you want with unit tests.
The solution to this problem is with mock objects. Objects that look like a texture but have all the methods stubbed out in a way to simulate the real thing. Sounds straight forward but it's an amazingly confusing thing when you have a module creating these things from the inside. That means design changes to the actual module just to enable testing.
In this case the solution was to create a class factory for textures. The resource manager uses the factory to get new texture objects and you just need to have the factory pass real objects when the game is running and mock objects when you're doing your unit testing. Just another compile flag to add to the list.
So in the end I had a bunch of extra work that I did both on the design side and the coding side to enable proper unit testing. Needless to say I was a bit annoyed and all of a sudden not so sure it was worth the effort. That was until I started writing the class and testing it as I went along.
Now I've never claimed to be the best coder in the world, but I'm not the worst either. With that said my unit tests caught over a dozen bugs in my code. I would have found them once I integrated them into my game but in that setting it would have been a lot harder to debug. Especially in a multi-threaded world where everything and anything is going on at the same time it's nice to be able to isolate your components easily. Even better than that, the unit tests found a couple crashing bugs. Anyone who's every tried to debug stuff using DX on a single monitor knows how much of a pain it can be.
Needless to say I am now 110% sold on TDD and anything new that I add to my engine I will be writing unit tests for. Eventually I'd like to go back and tackle the rest of the engine that's already implemented but completing my current project is more of a proirity than making sure my old code is unit tested.