Word Duelist iPhone Post Mortem

Published March 01, 2011
Advertisement
Foreward
Just a quick word before I get into the post mortem proper: Word Duelist for the iPhone shipped about 12 hours ago. I'm writing this while it's still very fresh in my mind - but I'm also writing it at 2:30 AM, so my mind is perhaps not its greatest.

You can get the full version on iTunes here and the lite version here.

Prologue
Word Duelist traces its routes back to my days as a grad student at West Virginia University. The Experimental Gameplay Project, spearheaded by Carnegie Melon, staged a competition requiring participants to design and then implement a game utilizing a DDR dance pad. I was playing a lot of Wario Ware at the time, and I had just recently watched Volcano High, so I thought fusing the two might be a good idea; the original "Duelist" game had players wandering around a university challenging students to telekinetic duels, where each duel was a series of small minigames involving the dance pad.

The game was actually pretty unfortunate. The graphics were abysmal - poorly edited pictures of people run through some Gimp filters. The DDR pad was super sensitive and didn't play nicely at all with the minigames I had. I didn't do so well in the competition that time around.

Fast forward a few years. Emergent Game Technologies had recently had a major layoff, impacting me in an unfortunate way, and I found myself with time. I decided to spend that time making XBLIG games. My first game was See the Light, a niche puzzle game that maybe 8 people played. The XBLIG version was admittedly an eye sore (a problem I would correct in the mobile versions), but that's neither here nor there. I wanted to move onto something fairly small, and this Duelist idea came back around.

I really don't know where I got it into my head that I could take the concept and adapt it to word games, but it was an idea that latched on and I ran with it. Word Duelist was born. I finished the XBLIG version just as I was starting my job with Spark Plug Games. I then had a bit of a hiatus from indie games while I worked there.

My job at Spark Plug requires me to do a lot of iOS development. I was interested in seeing how the market was, and I was settling into a routine that allowed some measure of indie development. I decided to take my two XBLIG games and move them over - first See the Light and then Word Duelist. - for two reason: to experiment with the market and to build up a C++/Objective-C codebase for more intricate games.

Word Duelist shipped earlier today. I honestly can't tell you how it's doing commercially - whether it's a "success" or not is still to be determined. I can, however, talk about the development.

What Went Right
(1) Data-Driven UI
During my XBLIG days, I vastly underestimated how much work a good UI requires even for a small puzzle game. There are the simple things like laying out widgets, and there are the more intricate things like animations and transitions. When I was doing it all by code, the amount of code quickly added up, and it was a cluttered mess.

One of my first priorities with the new codebase was to never let that happen again. I invested a good amount of time creating a solid data-driven UI system (which I outlined in this post), and it was a huge boon to development. Especially in a game like Word Duelist which has a huge amount of UI.

(2) Scoping
It's amazingly hard to develop a good game in spare time. I juggle a full time job, a social life, a lady-friend, a handful of other hobbies, and finally my game development. On a peaceful week I can work anywhere from 1-3 hours a night with added time on the weekends. It comes out to between 15 & 30 hours a week, generally around 20. That's not a lot of time.

I've made the mistake of over-scoping before; I'm probably doing it right now with another project. But Word Duelist was just the right size - the hard bits had been worked out for the XBLIG version and a good chunk of code had been written for See the Light. The art was 90% finished, with some extra bits needed to make it mobile friendly.

There was still work involved - the UI required migration to the new system, there were new features (Game Center achievements, a Quick Battle mode), and there were some iOS hurdles. Total, I think development took around 2 months, which sounds about right for a game of this size.

(3) Experience

I've been working pretty much exclusively with iOS for the past year (with some Android and XBLIG mixed in for flavor). Had I jumped into this project without having shipped a couple iPhone games already, there would've been headaches.

Objective-C has a bit of a learning curve of its own... much like any of the C-based languages. Quirks of the iTunes review guidelines - like not using private APIs that forums seem so fond of, properly handling memory issues, or handling device rotation - are things I'd seen. I knew how to properly work with Game Center and the quick paths to saving data.

In short, there were no real gotcha's from a tech perspective.

(4) End Cycles
I'm a fan of sticking to end cycles. Alpha, beta, RC. My development up to that point isn't as structured, but the path from feature complete to getting the game released is well defined.

This involved a lot of testing, and a lot of ranting when the later tests failed. Better I rant than have my game fail review, though. I went through 3 RC candidates before the game finally shipped, and had I tried shipping any sooner I wouldn't have actually released by now.

As an indie, it's easy to try & ditch end cycles or underestimate how much time they'll take. Every time I've tried that, though, it was a huge mistake; I'm glad I followed through with Word Duelist.

(5) Screen-Based State Management
My codebase has a somewhat intricate state management system involving processes and how they interact when responding to messages. I've made the mistake before of going crazy with that system, making virtually every task its own process that handles its own execution and then continues.

Word Duelist was a bit more relaxed. Basically every distinct "screen" had its own logic that handled things happening in that screen - input messages, for instance. Screens were broken up fairly well so that nothing became monolithic (no "Game" screens). The code was easy to trace, modular, and just logically made sense.

(6) The Team
This is the obligatory post mortem shout-out to the team I was working with. The artist (Laura Walters) made some charming art for this game. The musician (Michael Taylor) responded to feedback very well and was extremely fast. He also provided a lot of good sound integration ideas that I had never considered but which added a little extra. I will no doubt work with them in the future if given the chance.

What Went Wrong
(1) Memory Management
One of these days I'm going to be able to tell you exactly why I didn't build my codebase with good memory management in mind from the start. Naked new/delete statements shouldn't really get a lot of play in production code, but there they are. All over the place.

Smart pointers are a very noticeable omission. I've had to be very cognizant of what owns what, and it's a headache I'd much rather do without.

This all came to bite me late in development when there was some awkward memory thrashing. In the UI code, I was handling control transfer between windows, and code was trying to return focus to a widget that no longer existed. This manifested in crashes where the debugger would land in some random spot with random memory being thrashed but no clear signs of why it was thrashed. A proper weak reference system would've made that bug a non-issue, but instead it took me the better part of a day (during beta) to track.

(2) No Multiplayer
This is the kind of game that screams multiplayer. If there were more time, I would gladly put in multiplayer, but I'm scared of multiplayer development. Every time I do it, I feel like I've put in a series of inelegant hacks to band-aid my lack of expertise in the area.

The game is actually pretty well architected for multiplayer if I ever decide to add it later (the XBLIG version did support hot-seat multiplayer and a lot of that intrinsic support carried over). I'm familiar with Game Center's multiplayer development. But it will still take some convincing to get me to go down that road.

(3) Poor Time Estimates
I'm criminally bad at estimating how long something will take. I thought I'd have this game finished at the beginning of the month, and that slipped by about 3 weeks. There were various factors involved in that delay - a major deadline at work, various social obligations, etc, - but my plans should have accounted for those inevitabilities.

As a result, some other projects that I would have liked to work on got pushed by the wayside. I had a lovely Valentine's Day game idea that I missed my window for. Maybe next year.

(4) Texture Atlasing
I did a pretty crummy job of managing my texture memory. Items that weren't used anywhere near each other were lumped into the same image, most of the locations were loaded at the same time, and there was still a lot of unused texture space resulting from me manually laying out all the atlases.

Oh, and all the textures were uncompressed.

If you play the game long enough in one sitting, all of the above becomes a noticeable problem in the form of memory consumption issues that result in textures being unloaded and reloaded awkwardly. It's generally edge-case type stuff (basically beating the whole thing a couple times in one sitting), but still not something you want in a shipped product if it can be avoided. Alas, by the time I realized this problem existed, I was just putting the finishing touches on RC2 and didn't want to make the risky changes necessary to try and fix it.

Epilogue
I don't know if Word Duelist will be a success. Its XBLIG performance wasn't anything to write home about, but I think the iPhone is a different market more interested in word games (I hope, anyway). So far it only has a single rating from a person I know, but it's been less than 24 hours.

Regardless, I stand by it. It's definitely one of my better games, and the iPhone port was a worthy successor.

If you haven't already, you really oughtta get it. And rate it. And talk about it.

Just sayin'.
Previous Entry Word Duelist Ships!
0 likes 3 comments

Comments

blewisjr
Just picked up the game. The screenshots actually look very interesting once I give it a solid spin I will definitely give a rating and some input for you.
March 01, 2011 11:42 AM
Aardvajk
With regard to the memory-management issues, my personal view is that when memory management is simple, smart pointers save you some typing and nothing more. When memory management is more complex, they get in the way.

The only time I've used a smart pointer was when writing something (an expression parser I think) that wanted to throw exceptions at random points.

These tools seem like the anathema, but despite a lot of diatribe to the contrary, they don't replace a good, solid understanding of what is actually going on.

IMHO, obviously and I'm probably wrong.
March 01, 2011 05:59 PM
Nairb
Thanks blewisjr!

Aardvajk: I could probably be convinced to agree with those sentiments. I've found that smart pointers can make things a bit more convenient, but in large systems can quickly become hazardous - ie: when certain (usually undocumented) systems hang onto a smart pointer to an object that is manually managed elsewhere.

I think I'm more interested in weak reference support; I've found that I do a lot of pointer comparison ("if msg.StoppedProcess() == mMainMenuProc"), which is incredibly unsafe when memory addresses get regularly reused. In the above example, if I don't remember to set mMainMenuProc to NULL after use, there's a chance that comparison will give me a false positive. Alternatively I could've implemented a UID system.

I also like weak ref's when I'm keeping a bunch of pointers to UI widgets - in the worst case, trying to access a blasted widget will give me a seg fault and a clean stack trace instead of thrashing otherwise valid memory.

Both of the above examples are actual problems I had to deal with. Neither was fun to track down with the debugger. ^^ My system's clean enough where I could probably live without typical smart pointers though.
March 01, 2011 07:50 PM
You must log in to join the conversation.
Don't have a GameDev.net account? Sign up!
Profile
Author
Advertisement
Advertisement