Journal
"Ooh, yes, I've finished all the backend stuff and I can get to work on seriously making the actual game now" is what I've been saying in virtually every entry on this for the last year and a half. But it never really stops - if MMF has one specific weakness it's its modularity, in the way that for the most part event lists are tied to frames, and the result of this if you change something in one game level you need to go and copy and paste it into all your others (not to mention keep track of which one has the most up to date list that you want to synchronize). But this weekend I've been trying to make things easier for myself in that respect.

You really need to plan a game of any decent size from the beginning if you want to finish it within your lifetime, and Crystal Towers 2 has gone through a lot of changes that would have been much easier to cope with if they were in from the start, so I'm performing a great refactoring to speed up the rest of the game and this time really have something I can just add on to. Initially, the game relied on itself for its data - abilities, items that monsters could drop, and so on - with a couple of external plain text rules files for things that I wanted to be able to change easily, like the missions for each individual level. That was fine at first, but as the game began to balloon up beyond all proportions that I ever imagined it to have, I started an Excel spreadsheet detailing all the data in the game as well. And as I realized I kept having to replay the game to keep track of where I expected the player to be in terms of progress at each point, I then wrote a Java solver that used yet another version of the data in the game to tell me the possible "moves" from each position (with a completion of a level or gaining of a new item counting as a "move"). So up until last week, I had to keep four copies of the game's data up to date with each other, with only a slight link between two of them offering any sort of intelligent reuse of information. This is what we in the computer science world call "a nightmare".

It was actually when looking at the external rules files for Civilization II that I realized how stupid my current situation was, and decided that I'd better do something about it. I had previously thought to myself that it would be nice to read all the game data in from the spreadsheet that I was using to stop myself going insane rather than having to copy it all in manually afterwards, but I had dismissed that as being too insecure a way of doing things and I didn't know if MMF's database connection object could read Excel files without Microsoft's additional gubbins installed. But those Civ 2 rules files gave me an alternative idea - I was fairly confident that somebody in the world must have put together a way of reading Excel files from Java, so I could get that copy of the data into my solver fairly easily, and once I'd got that, I could get Java to write out the rules files itself to be read by the game.

So this is roughly the alternative communication between files that I have going on now - everything is connected and sourced from the same place instead of having each part hovering around looking lost. Thanks to a bit of planning ahead when I converted the save files over to a better system, I also have the option of encrypting the data and making it uneditable while still allowing the game to load it (which will be very important for the online scorecard system) - this happens through a separate MMF translation application. The parts of the game that used rules files already have been easy to convert, as all I've had to do is write a translator in Java to gather them from the database and put them in a form that the game can use. There have also been parts that relied directly on data in the game, which were more difficult to convert as I had to come up with ways to externalize them.

For example, one of the biggest problems I had with the old system was the list of items that each enemy could drop. I had initially written it so that each enemy detected when it was about to be destroyed, picked a random number and dropped an item based on a list of hard-coded chances. With the new system, it instead leaves behind a "SynthCreator" object, gives it its name, and allows a global function to take care of the rest. This function performs the dice roll, looks for any entries in the "drop" rules file that match the name it's been given, and creates a dropped item accordingly. The whole process is so much simpler, even if it did take a weekend to convert everything over to using the new and much easier way - all I need to do now when an adversary is destroyed is create one object and start the function. While I was at it I also externalized the damage that different damage types cause to each monster type, the amount they take off your own health when you blunder in to one, and so on.

Changes like these, along with trying to move everything possible into the global event editor (which I was wary of as it was rather unstable in earlier releases of MMF, but it seems to be absolutely fine so far) make the events of each level much simpler to understand and work with, as they just need their own unique events rather than a copy of the ones that are used throughout the game. So this time, I really am confident that it's taking shape.

It helps that the graphics I have from Jay Frudy are fantastic, too. I'll put a video up at some point to save you reading all that.

2008-04-28 15:49:00