We Have Established Control
Progress is continuing! This update includes some new features, a video about the new escape menu, programmer talk, and a little mood music. Continue Reading
We Have Established Control
Progress is continuing! This update includes some new features, a video about the new escape menu, programmer talk, and a little mood music. Continue Reading
Pick it up Man!
More changes for the Amulets & Armor project. This update I’ve got an interesting video for you. It shows how you can pick up items now in the look mode. Continue Reading
WASD with Mouse
Since my last post, I’ve been working on making the keys work using the WASD keys and the mouse. I wasn’t too sure how this would work out, and honestly, I’ve never done these types of controls in a game, much less in a windowed game. Other than a bout of rea life interruption, the new code was not terribly hard to add. The video attached shows more…
Removing the Curse — One Bad Bug
I cannot help but be pleased by my work today. Although I did not get the new WASD and mouse controls fully working yet, I got side tracked with a bug in the system. Working with the game lately has been a bit of trial and error lately because each time I ran the debug version, I would get an error about every 2 minutes or even sooner when I started casting a large number of spells.
Irritated by the instability of the system, I changed my tactics from adding or changing the code to finding that bug NOW. The little voice in my head was already screaming at me that I was being unprofessional and letting my desire for new shiny features distract me from the mundane and obvious problem before me — that the product was being taken down by a small infestation of memory mangling termites.
Using a magical routine called _CrtCheckMemory() along with my own house rolled MemCheck() commands, I was quickly able to setup a system that searched high and low for the tale tale signs of an unwanted visitor. Nevermind that the frame rate dropped to less than 1 (a screen update every 5-10 seconds), but I was able to setup a test that would cause the bug to show itself. And low and behold, it was in the effects system.
The effects system tracks what effects are on the player. Cast regeneration, and you get a small icon on the side of the screen and your character regenerates. But the effects were not working correctly. Come to find out that the small memory structure allocated for the effect was the WRONG structure. And I when I mean the wrong structure, I mean the wrong structure. Somehow the inventory structure was being used in place of an effect structure (ahh, the one flaw of C — too much power). The proper structure is bigger than the one that was being allocated and writes to the effect were scribbling past the end of allocated memory, thus, corrupting the heap. Since most spells create an effect of some type, this explains why I thought the spells were cursed! They were slowly destroying the memory space.
Now I’m able to play the game again and for long periods of time. Alright, I admit it, I played for about an hour today without a crash. It was nice never seeing a bug … until … I tried to quit and found a new bug. Sigh. The good news is I was able to use the tools developed above to identify what caused the crash, I just have to figure out how to easily recreate it. (It occurs when a blood splatter disappears off the ground at the same moment you complete a level — how’s that for a rare bug!)
My general rule is to find a test case to recreate the bug, verify the bug exists multiple times, fix the bug, and then test that the bug is gone. I hate bugs!
Return of the Avenger
I did a little bit of testing across the different levels and went back to Quest 4: Exiguus and the Undead (sounds like a band name, doesn’t it?). Running around the level, all was going good until I died. Well, I died but I could see no attacker. Holy Toledo, Batman! I introduced a bug that allowed monsters to attack through walls, right? Or maybe some weird problem with the creatures in the floors attacking me, right? No. I just had forgotten to add back in one of the many routines to draw colorized creatures onto the view. In effect, our old orange knight (known as the Avenger, who has been nicely colorized from the standard gray knight into that wonderful Halloween orange) was just not being drawn. And, since I was using a 1st level character, he trounced me in 3 or 4 hits without me seeing whodunit. Not to worry, about 3 lines of C code later and the Avengers are back in action.
A Little Music Please
As I stated in my last post, I’ve been working on the background music. What a surprise this turned into as I had to work the music code differently than the original DOS game. In the old HMI Sound System, I used routines to stream the music in block by block letting the HMI system tell me when to pull in more. This was done for memory reasons as we were targetting 4 Meg/8 Meg computers and the sound tracks were about 6 Megs on average. Flash forward years and I have decided to just load the whole track instead of the piecemeal system. Load times are not even an issue. Unfortunately, I found myself introducing a few dozen bugs. When the sound is turned off, crash. When the sound is set to the lowest volume, crash. When you enter a new level, crash. When you exit a level, crash. Yeah, embarrassing how this bug was owning me considering I had just wrote a sound mixer in an evening and yet this bug is messing with me over and over.
I’m glad to say, I’ve dealt with the problem (take that nasty bug!) and background music is working just fine …. ::prepares to slap computer::
Now music is working just like the full system. You have full control on how loud or soft the music is in the options dialog. And while I was at it, I fixed some other issues with changing the sound effects level (they would pop when you changed their volume). I think we are done there.
Next up WASD Controls! In the old DOS game system, you would go into SETUP.EXE to configure all your custom key strokes. I’m going to look into putting this configuration directly in the game. I wonder if I can make that work for both DOS and Windows. Hmmm … seems simple enough, right? Might give me a good reason to put a menu in there instead of the “Press ESC again to exit the level…” I’m also going to look into creating a Look key that switches between the mouse being active with look/pick item actions or making the mouse control the facing of the player. Yes, this means there needs to be a turn speed and fun stuff of that nature.
This will probably be a big change. But it should bring that feel that players have with current controls into the game. Oh, and if someone doesn’t like the new keyboard layout, it’ll be easy to switch back.
Hold on, am I going to have to do some artwork in Deluxe Paint again?
In Like Flynn
And just like that, sound is now back in the game. I’m pretty pleased with the results. Even though I was wrong about the SDL_mixer library not having a pan/stereo feature (it did, thanks for pointing that out NotPyry), I went ahead and created my own audio mixer. Come to find out, they’re really not that hard to put together and I get the ability to customize it to the game a little bit (volume controls, mixing settings, etc.).
The system now can play 32 simultaneous sounds at 16-bit 44 kHz. Measuring performance shows that on a simple test scene where we get 880 fps, the sound system drops it down to about 800 fps when all 32 sounds are playing (or something close to that — I was just spamming spells as fast as I could). Most levels will have no more than 8 sounds at once standing still and about 12 when the combat is going.
On top of it, stereo/panning is working and I was able to play the game in all its glory. I had no problems with sound distortion or even the “crunchy” sound I’ve had in the past (which surprised me). Maybe that’s because I do the clipping check at the very end of the mathematics and use the full spectrum of the audio system (16-bit 44 kHz instead of just 8-bit 22 kHz).
Overall, I’m very pleased. I even got frequency bending working (this allows a 11 kHz “Ugh!” sound to be changed to a higher or lower frequency version of “Ugh!” at no extra cost).
But I’m not done. I don’t have the background music back in there and need to clean up the code a bit so the DOS and Windows version aren’t intermixed. I don’t expect there to be big changes in the future, but it would be nice to be able to read the code better in the future. For the Windows version I’m going to drop the MIDI and just stick to digital looped music. I’ve got the files and downloads are no longer 19200 baud modems. Background music will only cost 1 more constantly on sound effect in the system.
Bad Spells are Cursed
As I’ve worked on the code I get an occasional heap corruption in the debug version that crashes the game. I was so excited to have sound that I started playing Quest 7 Map 1, and since I forgot how to get the exit to work, I spent a considerable amount of time trying to figure out the puzzle (yeah, I should remember this, but I don’t). Just as I was about to get the last step figured out, crash! Sigh.
But here is the good news, I’m seeing a pattern. There seems to be a link between casting an invalid spell (I didn’t have my list of spells handy) and this heap corruption bug. It’s not a 100% thing, but the more invalid spells you cast, the greater the chance of a heap corruption. There may be more bugs in the system, but this seems to be the first well hidden bug that has a pattern to it.
Sometimes it is nice to see progress being made in the smallest chunks. One of the most exciting parts of working on a 3D game is seeing it improve little by little, even when what you as the programmer is minor to other people. Those small details add up and create a fantastic whole.
Tonight I’ve been spending the evening translating old DOS assembly routines back into C and trying to get the math right for drawing floors and walls. After translating some 70 routines, I have the final first results below:
It is probably no big surprise I didn’t get it right the first time, but this isn’t bad for the coming out the gate. Seems we are missing objects, the textures have a mind of their own as I walk around, and things in the distance seem to pop around. But the sky is right, the textures are in the right place, translucent textures (not shown) are working, and the light shading is working very well. Not bad, not bad.
Frame rate is a little low (303 fps compared to the theoretical limit of over 1400), but I am running debug code with a ton of output appearing on the other screen (also not shown). Oh, and the Windows tools are telling me I’m corrupting memory somewhere … nice.
Moving forward ….
So, some of you may be wondering why I’m doing a Windows port of the game. The reason is mostly selfish — I want it in Windows. Plus, there is more to it I’ll hit list:
So where am I now?
Here’s a couple of screen shots of the current Windows version:
I’m currently scaling the 320×200 into a 640×400 area in a 640×480 window (that’s why there are big black boxes). I’ll probably put in a scale to 640×480 soon, but I just wanted to keep it 1×1 to 2×2 for now.
Current performance numbers on optimized release code shows I’m getting about 1400 fps on the raw UI to SDL drawing code, which is more than enough for the final, but I am running on a quad-core 2.8 GHz machine. NOTE: I have not optimized the windows drawing routine heavily yet.
Oh, before anyone gets excited about a 640×480 view of the world, no, I’m just doing a 320×200 scaled up to 640×480. At this point, I’m still just focusing on getting the system up and keeping it fully DOS compatible.
While I’m waiting on legal paper work, I’ve been doing several things in the last couple of weeks:
Things I’m still looking for or need to do,