Something that has always been scary (well, it’ still is) before launching Vizati is tech support.
No matter how much you tested your game, it’s bound to have bugs. Also what I’ve realized is that I don’t spend enough time testing the game, oh and you too, yes YOU (I’m assuming you’re a developer of course).
The past year I gather around a few friends who never played it to test the game for 2 days. 6 people played it the first day, 4 played it on the second day. We gathered around all complaints and issues and addressed them. After that there was more play-testing but not as aggressive. There were 3 or 4 persons testing it regularly.
The problem was always that the game was running on a more or less safe environment, there are tons and tons of different PC configurations out there. Installations problem, bad drivers, some other software running causing conflicts, all this can happen.
The PC version most problematic issue was getting everything installed properly. .NET framework installation would sometimes fail and silently quit and for all purposes the game was supposed to run.
It never happened to any of our testers, but as soon as the game went out it happened.
I accidentally bumped into a thread while searching for Vizati reviews and found a client complaining that he just bought the game, It wouldn’t even start and that the developers didn’t even care.
I was shocked…what? I checked my inbox, both my personal and Different Pixel inbox. Nothing, I sent a email for myself from an external account to test it since we are running our pop server on a rented one. It worked. I decided to register an account on that forum and contact the player.
After a few email exchanges we figured out what it was and I created a thread on our own forum.
The reason he said the developers wouldn’t care is cause he wrongly assumed we wouldn’t based on past experiences with other games. This is a very problematic issue, having around a client telling that you just care about selling is bad if you are just starting. There’s not much you can do with people who don’t even try and make contact.
This version is perfect, there isn’t a single bug and I dare someone to point one….
lol actually the Xbox360 version never went for sale, still waiting for that XBLIG on Portugal
That’s the main issue with the iPhone port, I never gotten a single email.
I know a small percentage had some issues, it’s inevitable, but they rather place a 1 star rating and a “Don’t work” comment and move along. With all the updates some eventually place another comment like “It’s working now”. But I’m still in the dark, what is working that wasn’t before? Is it something I fix intentionally or accidentally?
Although the iPhone is a more controlled environment you can still have issues. You have 4 generations of iPhone, 4 generations of iPod Touch and iPad. Different memories, different CPU speeds. Also some have OpenGL 1 others OpenGL2. Also some run on an ARM6 others on ARM7, the processor type is transparent for the developer but if you know what you are using you can optimize floating point calculations a bunch.
I tested the game on an iPod Touch 2G, had a couple of testers playing on iPhone and half-way through I found out that game was almost unplayable on a 1st Gen iPhone. I solve that optimizing the engine.
This proves that without those external testers I would have placed the game for sell just like that without even knowing there was a problem. My iPod Touch is one of the slowest so I assumed it was ok. Don’t assume anything.
The WP7 port has this one bug that has been haunting me and I can’t reproduce it. Basically the tutorial font get’s all twisted but only when viewing the tutorial. Someone reported it to me and I wasn’t able to reproduce it on the emulator. After I got a real device I can’t make it happen, No one has given feedback about that on Vizati ratings at the WP7 Marketplace. Rita also has another WP7 device it it works great too.
A couple weeks ago I was invited to present the game at a conference, they had the game installed on one of the other speakers phone and it was working. Suddenly during the presentation to the audience it happened, I quickly skipped the tutorial and the game continued normally. So this one is still out there. Other than that I had 2 persons complaining that the game would crash after starting but a soft reset did the trick.
Around a week ago we’ve released Vizati for Mac on the App Store. This raises a bunch of more potential problems, some Macs have PPC, others Intel Processors. Also I never, ever coded anything for Mac, it’s always scary… even more since I don’t have a couple of macs laying around to test, I have to rely on remote testers.
I haven’t gotten many emails, most are suggestions or so and so far the worst bug report I got was the game not running in fullscreen, only in Window Mode, which I assume is the game wrongly calculating the screen max resolution. When toggling to fullscreen I’m querying the screen current size and using it so there may be some issues there. Must address that.
A BIG mistake I did with the Mac version was forgetting to activate the File Logger. Stupid stupid stupid. I did that to help me track where the issues may be and I totally forgot to activate it on the final build 🙁
Word of advice: When pushing a new patched version make sure you didn’t introduced a new bug.
… a lot….
Very interesting post. I’m still busy working for university, but I intend to break into indie game development next year, and this post serves as a warning of many problems I’m bound to run into.
Actually I’ve been trying to ask you something unrelated, but did not know where to post (and haven’t seen you on msn for a while), so I’ll leave it here. I’m working on my 2D game engine and trying to make it a bit more feature complete, and was wondering if you could briefly enumerate all features that you found were useful for your engine and might have not been obvious at first sight?
I also noticed you had a resource manager for XNA on your engine. I must ask, what’s its purpose considering that XNA has its own ContentManager, and what went into its design?
Yeah my new year resolution was to use MSN and Facebook less 😛
Don’t worry I didn’t blocked you or anything like that 🙂
I usually check my twitter feed everyday @DJ_Link
As for the questions I’ll try to keep it short:
– Reference Management (keeping track of what’s alive or not)
– Animations Pump – Helpful for pausing all at once
– Content Manager
There are more but most of them are more obvious.
As for the Content Manager I made a wrapper around it so I could easily port my code to other platforms. My Conten tManager to some level is path independent. I had a couple of image source path to it, them when asking for an image, I only have to ask by name, makes easier to manage.
Example. Source image is at “Content/files/images/image.jpg”
I add this path to my ContentManager like
When requesting image.jpg I only need the name. This is useful when you change a bunch of stuff from a folder to another, you just need to change the path on the content manger, not change a bunch of code lines everywhere you placed “Content/files/images/”.
Also I use it to load custom stuff of mine, like sound, spritesheets, animations sheets, map levels etc
Another things is that you can unload just one asset from the XNA content Manager, just everything, so I use my own to manage a couple of XNA Content Managers.
Hope this was helpful…
Thank you for your reply, it was very helpful, but could you elaborate some more on the concept of “animation pump”? I googled it but couldn’t figure out exactly what you meant, and coincidently I was just about to pour some work on my animation part of the engine and would like some more information as it might prove useful.
I’ll describe my current architecture a bit, to serve as a comparison and to organize my thoughts. I have a layered display list and a special display object called AnimatedDisplayObject. The display list automatically calls draw and update on the display object, and each display object has basic transform information embedded.
An animated display object can hold multiple animations, indexed by a string Dictionary.
– SwitchAnimation(string name) changes the current animation to another one permanently.
– PlayAnimation(string name) plays the chosen animation once, then returns to the previous animation.
Each animation can be configured with parameters such as:
– Loop direction (forward, reverse, random)
– Loop count (once, n times, forever)
– Callback for animation finished
Each frame can be a single sprite, sprite from spritesheet, or a complex sprite skeletal hierarchy composed of other sprites:
– Callback for each frame
– Duration (in frames)
Yep that seems about right.
I called it an animation pump and it’s basically an Animation Manager, pretty much what you have.
Don’t make animations depend of frame-rate but on elapsed time since last frame.
You’ll may have issues if you change the FPS down the road and are using it as reference
🙂 Yeah I know.
When I mentioned that each animation has a framerate, I don’t mean the game’s framerate, but rather another independent framerate that is calculated around the elapsed game time. This means for instance that I can have my animations running at 12 frames per second regardless of whether my game is running at 40 or 60 fps.
Then, each animation frame has a duration that is specified in “frames”, but these refer to the framerate of the parent’s animation timeline, not normal game frames.
But when you say an “animation manager” it makes me wonder something. In my case, each animated game entity IS an animation manager, i.e. it has frames and knows how and when to advance them (which it does on its Update method).
But since you mentioned having an animation manager, it makes it seem as if there’s a global, central manager that is responsible for controlling the animations of every entity (and each entity merely holds the data). Is this what you meant?I wonder if there would be any advantage in doing that, i.e. exposing an interface for animation on my entities, and register them on a global animation component that “pumps” each of them, rather than having each entity know how to animate itself. Which one did you adopt?
On my system each entity knows how to animate itself. But the animation manager tells them when to update and how much time has elapsed.
So my animation manager calls every single updatable instance a function called Animate and passes the elapsed time:
float elapsed = ///grab elapsed time since last update in seconds
for(int i = 0 ….
That’s what I thought somehow but it left me wondering if there’s really a need (or advantage) to separate Animate from Update? Currently I’m doing animation on each entity’s Update method, and the display list takes care of calling Update on each of them.
I can’t really picture a scenario where I’d want to stop all animations while still keeping my entities being updated, but if I ever needed that it would be as simple as adding a static boolean “AnimationsEnabled” to my animation class and branch on it inside the Update method (or add it on a per-entity basis).
Once again I don’t use the generic XNA Update. My Animate() replaced that.
Each entity just needs a Draw and a Update/Animate function. Inside you will do all update related stuff. Like updating positions or the sprite animation. There’s no real need to separate those. Doing it isn’t wrong of course, it’s just another way to tackle the same problem.
I am a portuguese programmer too 😀
So i have one big question about xbox 360 you can´t sell our games on indie market?
P.S:Uma continuação de um bom trabalho e desejo.te muita sorte um abraço.
Yes unfortunately the xbox360 indie game market is is closed for portuguese devs.I’ve know some Microsoft staff and they don’t know when that’s going to happen. If that’s even going to happen.
But you can sell on the WP7 market.