A new bug came to light in Doomdark’s Revenge. I had a report of a crash bug that occurs after 138 days, that’s one hundred, one score, and eighteen days since the Moonprince rode forth into the Icemark.
The problem appeared to be that an AI character’s liege was getting set to himself. This causes a problem in the AI logic for a character choosing to follow their liege. The AI goes something like this…
I want to follow my liege, but my liege is dead, so I need to follow my liege’s liege and this character will become my new liege. The code ripples up the liege tree until it finds someone to follow, or bails and decides to hunt down Luxor instead. When the bug occurs it follows the tree and finds a liege who is dead but they are also their own liege, and thus we get stuck in an infinite loop.
Once I found this as the source of the crash, I needed to work out WHY it occurs.
There are only two places where the liege can change, the aforementioned follow liege routine, and being recruited.
I stuck some debug info on both cases and set the game to run on automatic to see if the issue triggered, and it did.
Here is the scenario…
Anvarorn starts with Fangrorn being his liege. Fangrorn’s liege is Shareth. Fangrorn gets recruited by Anvortheon the Barbarian, and thus his loyalty changes to the barbarians, and his new liege becomes Anvortheon. Anvarorn decides to follow his Liege, who is still Fangrorn. When he gets to the same location as him he notices that they are not the same loyalty and thus tries to recruit him. He succeeds. Thus Fangrorn’s liege becomes Anvarorn. So we now have a circular liege issue. This becomes a problem if Fangrorn dies, because in this instance Anvarorn decides to follow his liege, finds that his liege is dead so takes his liege’s liege as his new liege and therefore becomes his own liege!
I went back and checked the original code, and this issue can happen. The only place you would notice it would be on one of the description screens where it would say, Anvarorn’s liege is Anvarorn – or words to that affect. At worst the character would end up following themselves and end up not moving. This is something that has been mentioned as possibly happening in the current version.
When I implemented the liege tree walk, I did just that, I implemented it as a walk up the tree, and because of the circular issue, a dead lord who is their own liege will create a circular loop if they are someone else’s liege. The original code doesn’t do that, it only takes the next liege up the stack and therefore slowly makes its way up the liege tree over a number of nights. Thus no infinite loop.
This would possibly occur with characters following their foe. If their foe is dead it walks the liege tree of the foe to find the next foe.
I’ve spent some more time looking at the AI for Doomdark’s Revenge, trying to work out why it doesn’t quite appear to be playing like the original. One thing I noticed is that I have completely misunderstood the recruiting logic when it comes to Loyalty and Treachery. I made changes in the last version, but I am going to need to revert them.
The approach algorithm
compare the the attributes of the lords and looking for matches gain +1 for each match.
If the character being approached is not loyal then +1
If the character being approached is treacherous then * 2
if the recruiting character is the liege of the character being approached then +3
If the recruiting character carries a crown of persuasion then +2
If the score is greater than 3 then the approach will succeed.
The basic concept that I have misunderstood is: Loyal characters are less likely to be recruited away form their current liege and un-loyal characters are more likely, therefore the algorithm gets a +1 for none loyal characters. And that treacherous characters are more likely to leave and thus the *2
The next thing I have missed is the lords following the objectives of their lieges.
It works like this.
If the lord has a liege and that liege is following their liege or their foe, then we must follow our liege. Otherwise pick a new objective.
There is a 32% chance that we will pick a new objective. Although that should be 25% because we could pick the objective we already have. That leaves a 68%/75% chance that we continue doing what they were already doing.
The problem for me is the first check. If we use Shareth as an example. She has a 12.5% chance that she will choose to follow either her foe or leader. As she has no leader she reverts to Luxor, which is her foe. So she has a 12.5% chance that she will follow Luxor. All the lords that follow her now have a 100% chance of following Shareth, and this ripples all the way down the stack of lords. Which at the start of the game means that 47 Icelords will disregard what they are doing and follow her.
The mistake I had made is that I had made the following lords take the objectives of their liege when their liege was following their liege or foe. What this means is that when the liege is following their foe the lord follows their own foe. So using Shareth again as the example, when she is following her liege ( Luxor by default ) then all her minions will head to her location, but when she is following her foe ( Luxor ), then all her minions are heading to their foe and not to her location. So as an example, Imgaril the Icelord would be heading to Imgorthand the Fey, who, is likely the the other direction of Shareth.
Hopefully this fix should make the game more like the original, but it bothers me that it is a flawed AI. I ran the game for the first ten days, up until the first battle took place, I ran it on the emulator too to compare notes. Here is what Shareth did over those days.
Search for object
Now Talormane does this
Search for object
Search for object
The reason for the delayed follow on day 4 is because Talormane is following Lorelorn who is following Shareth, but Lorelorn is lower in the processing order than Talormane, and thus Talormane doesn’t know that Lorelorn is going to follow Shareth in that turn.
The final thing that I changed was that there is a 6.25% chance that the change of objective will be DO NOTHING. This is especially important for being in a battle with someone who is not the lords foe, because it means that without this the lord will always leave the battlefield. The mistake I had made was that I persisted the do nothing as an objective, i.e.. The lords objective becomes do nothing. But it shouldn’t, it should stay the same as the previous objective, and this turn that objective is ignored.
Going back to Shareth. If she chose to DO NOTHING then her objective would no longer be follow liege or foe, which means that her followers would be able to perform whichever objective they chose. However, if her previous objective had have been follow liege or foe, then her followers should still be heading towards her when she chooses to do nothing. This would have the affect of allowing them to catch up on her.
After hastily announcing that I will be releasing Doomdark’s Revenge on the 7th I can now confirm that the actual release date will be the Monday 17th Feb.
The main reason for this change is purely logistics. I have to get the website ready to go, PR and Press Packs, Screenshots, Video, submit all versions, and create the store for direct selling.
However, the other reason that I hadn’t taken into account until thinking about submission congestion, is that, during the week of the 17th, it would have been Mike Singleton’s 63rd birthday. So it feels appropriate.
The iOS version is ready to go, and I intend to submit to Apple tonight. Apple usually take 7 days to approve a new submission. If there are any problems, then I would likely miss the 7th. The real area of concern is that from Feb 1st, Apple are insisting that all submissions are done using XCode5 and target iOS7 as the build SDK. In theory this shouldn’t be a problem, however in order to guaranty this, I need to build with the latest version of the Marmalade SDK 7.1.1 and as this version is only BETA at the moment I have slight concerns. I am currently not able to submit to MAC Appstore because of a Marmalade issue, and that affects my confidence in it.
The Android version appears to be ready. The first initial sweep has been done and a few small visual bugs stamped out. The game UI now seems stable across resolutions so I would suspect that supported devices will be the same as with The Lords of Midnight. I don’t foresee any issues moving forward. The turn around time on Google Play is such that I still have plenty of time to fix anything that crops up.
I have done a Blackberry build, and it all seems to be running in the simulator without issue. I need to perform an actual device test but again I don’t foresee any issues. There were some initial problems with the Q10 720×720 resolution but they have been ironed out. BTW: this version will allow the Q10 to rotate and I will include this fix in The Lords of Midnight ASAP.
Samsung and Amazon builds are just packaging. So again, I don’t foresee any issues.
Windows and OSX builds should be good, as this is how I develop. I expect to hand over a master to Fastspring and GoG.com early next week.
The only issue with the OSX version is that it is unlikely to be available in the MAC Appstore for a while. This is due to the aforementioned issue with the Marmalade SDK and OSX Mavericks. If the issue is not fixed soon, and I have a window of opportunity before the 17th ( preferably by the 10th ), I will install an OSX Mountain Lion machine and attempt to build the app. The OSX version will however be available direct or through GoG.com, where I don’t need to release a signed app.
Once the release is out there, I intend to revisit Windows Phone 8 version of both Doomdark’s Revenge and The Lords of Midnight.
One thing that got carried over from the original Midnight Engine was the shading of the landscape depending on the time of day. The original Lords of Midnight, has a different colour for night which is basically that all the white becomes black, but the blue remains the same.
In TME and therefore the remake, I have a tint colour for each time of the day, and the images are tinted toward that colour. That colour is generally a shade of grey and it is used to darken the dawn, brighten up to normal colours around midday, and then dark off fully to night. In reality, this is one area of the remake that I left in that I don’t like. Only because, it doesn’t really look like the original. The night view has a very distinctive look, and as you can see though, the remake doesn’t look the same. It’s fine as things goes, but I would have much rather made it look more like the original.
Doomdark’s Revenge however has a completely different approach. There is a dawn visual, and day visual, and a night visual.
I knew therefore that when I got around to releasing Doomdark’s Revenge, I was going to have to deal with this issue. The tinting method just didn’t cut it. Because I could tint to red, or tint to yellow, but not combine them.
To give you a little background. The colour changing was relatively easy on the ZX Spectrum. Partly because the images were very simple and were constructed, but also because of the way that the spectrum only had two colours in a 8×8 grid – known as the paper and ink. So all the effects were done by just changing the paper and the ink. These colours were not stored with the bitmap either, it was a different memory area. So in fact, what Lords of Midnight does is, clear the screen with paper and ink both white, draw all the pixels to the screen, which you can’t see, and then fills in the paper and ink colours which makes the screen appear.
Now, the choice I made when porting the game was to use full 24bit alpha’d bitmap images. I can discuss the merits, and the whys, and possibly the mistakes, of this decision. But, it’s not been one I can change easily.
The upshot is: changing colours on the fly isn’t easy. It’s much easier with 8bit palletised images. But believe it or not, despite the fact that the terrain images only use two colours, they actually use at least 255 colours in order to get smooth edges, as well as being alpha’d. Changing to palletised images just made it look awful.
Once solution that I knew could work would be to write a custom shader. Shaders are dark voodoo magic that happen on the graphics card. And I’ve never written one in my life. Had Mike been around, he would have knocked one out very quickly. But obviously he wasn’t, and as I was heading toward the original release of The Lords of Midnight, I didn’t have time to look into them.
Now however, I couldn’t ignore it any longer. With the latest update of The Lords of Midnight sat awaiting approval from the platform holders, I turned my attention back to Doomdark’s Revenge, and the next thing to address, was making the dawn landscape look proper. I was going to have to learn to write shaders. And that’s what I spent yesterday doing.
The end result is that I now create all my terrain images as being black and white. These two colours will be replaced by the shader as the image is being drawn to screen. However, I can’t just replace the two colours, I need to make sure that I where the two colours meet they get blended.
If you click on the Mountain fragment you will see a blow up of the image, and see how this would work. Affectively the image can be considered thus; all black, all white, mixed. The mixed part always being where the two meet. So if we consider that we will replace all black (0,0,0) with new colour_a and replace all white (255,255,255) with new colour_b, the other colours will be a shade of grey from (1,1,1) to (254,254,254). What we actually do is use the value of one of the colour components to work out the mix of our two new colours. so 0 is 100% colour_a and 255 is 100% colour_b. A value of 153 for example would be 40% colour_a and 60% colour_b.
Now, it’s not rocket surgery, there’s nothing particularly clever going on here, but for me I had to turn this into a shader, and that was new territory. However, working within the Marmalade SDK and using the OpenGL ES shader reference manual, and a little bit of google… the process turned out a little easier than I expected.
Here is the landscape without the shader active.
But with the shader active, and the two colours adjusted depending on the time of day, we get the following.
And, if we now revisit The Lords of Midnight, we get the resulting night landscape that I always wanted.
Not sure when this will make it back into the current release, probably after Doomdark’s Revenge is released and I’ve been able to fully test the shader across multiple platforms. But it will make it back.
I’ve been working away for the last few weeks, which has meant that my development has had to take into account that it is being done primarily in bars an restaurants. I know many of you are waiting for the latest version of The Lords of Midnight, but although I have spent some time fixing bugs and adding a few new features, I am not in a position to Build a release version. I have to have access to my desktop to do that, and the few days I’ve spent at home with my family, I hope you can understand that spending time in my study on my computer is not the highest order of the day.
After declaring an end to any changes to Lords of Midnight, I spent some time merging the codebases of the different versions that have been branched out over the the year. Namely, Mobile version, Desktop Version, and Doomdark’s Revenge. I now have a unified code base which means that when I release a update for LoM soon, it can be across all formats.
Once the merge was complete I decided to spend some time working on Doomdark’s Revenge. I am hoping to release a test version soon. The night AI will not be activated but you will be able to wander around the map, above and below ground. And generally check out the UI differences between the games etc. This will then give me a good base to slowly turn on AI features and test them thoroughly up to release later this year. For the record that would be in about 12 weeks!
Once area that I have been working on this week, is tunnels. Tunnels are one of the new features that Doomdark’s Revenge implemented. So I have been slowly working my way through the code base, adding in all the little things that need to be there in order for them to work.
It’s a little different with The Midnight Engine, ( which by the way is the underlying code that powers both The Lords of Midnight and Doomdark’s Revenge ), over the original games, in that there is one code base. Doomdark’s Revenge was released as completely new game, and therefore much of what didn’t remain of The Lords of Midnight was just removed and the new code was added. This is a big issue with my codebase, as my original brief for creating The Midnight Engine was to be able to play both games and in theory create a game that mixes the features from both LoM and DDR. So, if we take tunnels as an example, I could just turn tunnels on in LoM, and everything would just work.
Now, let me try and give you an example of why that thought process gives me a nightmare when implementing something like tunnels.
In LoM a map location is split up into [ Terrain, Area, Object, Flags ], in DDR it is just [ Terrain, Flags ] – both area and object are generated. TME uses an expanded format [ Terrain, Variant, Area, Climate, Flags, Object ]. So the generated areas in DDR are stored, as are the objects. ( For the record, objects change every night ). For both, objects are classed as things you find or things you see. So Guidance, Cup of Dreams, Dragons, etc…
Now tunnels are a flag. A location has a tunnel beneath it or it doesn’t. If the terrain is GATE, PIT, PALACE, CITY, then the tunnel is an entrance/exit. If the terrain is PLAINS, FOREST, HILLS, MOUNTAINS, then it is considered a passageway. Now, this is where things start to get messy.
A tunnel location can only have a critter ( dragon, wolf, skulkrin, trolls ), when it is a passageway. And the location directly above ground can only have a critter when there isn’t a passageway below. So affectively you have two locations sharing the same space but only one critter at the location who could be in either of the two locations.
It seems a pretty straight forward thing to think about, but when your code base works on the concept of a single location, suddenly everything changes.
When drawing the landscape, the frontend asks the backend for the information about a given location. It draws the terrain graphics and any critter imagery that is required. The backend has just told the front end that there is a critter at this location. However, now it has to consider if we are above or below ground, and the type of below ground we are on. Based on that information the frontend can decide if that critter is visible or not.
When at a given location the frontend asks the backend for all the lords that are at a given location. But now it has to consider if that lord is above or below ground. The list of these types of checks goes on and I’ve found myself having to work through the engine making sure that I am always using the correct context. More importantly I am trying to make sure that any logic is in the backend and not in the frontend. Therefore the backend now returns the information in the form of, here is the information at the location requested, this critter is above ground and this critter is below ground. It doesn’t matter that there can’t be a critter in both, that is a backend problem not a frontend one.
A similar thing happens with the discovery map. There are flags on a location to say that it has been seen, looked at, or visited. Seen is a distance thing. Two locations away may have been seen, and you know what terrain is there because you can see it on the landscaping view in front of you, but you might not know what it is called. Looked at is for locations directly in front. You know the terrain and the name. Finally, visited is exactly that, you have stood on that piece of ground. But, you might not have stood under that piece of ground. So now we have to introduce the concept of tunnel visited and tunnel looked at. How about, we have walked down a tunnel and got to the end, and we know the tunnel finishes, as opposed to not quite making it to the end, so we have looked at the tunnel location in front, but because we didn’t visit it, we don’t know if the location after that continues as a tunnel, or this is indeed the end of the tunnel.
That one bit flag in DDR ‘tunnel’ suddenly becomes so much more when you are trying to keep a flexible engine. That one bit flag also creates limitations. Two tunnels adjacent to each other must be connected. You can’t run a tunnel under a palace because a palace is always an exit/entrance. This is used to create a one way tunnel in the game.
I have considered removing the bit flag, and replacing it with the concept of layered maps. You would then have a map for all the terrain above ground and then a map for all the terrain below ground. Following that approach would me that the limitations could be removed and it would allow things like different critters above ground than below. Or types of tunnels. But for now, I’ll leave well alone!
Other things have crawled out of the subterranean landscape… For example, two characters at the same location are not actually at the same location when one is above ground and one is below ground. Thus, the newly added grouping functionality suddenly needs to take into account tunnels!
I finally submitted the OSX version of The Lords of Midnight to Apple last night, it’s been a long time coming, a lot longer than I expected. I didn’t start it as early as I expected due to supporting the mobile version until March. Some of it has been because of technical issues, I struggled to get the code, more accurately the resolution code, to work satisfactory. Another part was being burnt out. I hadn’t realised how much getting the Mobile version out, took out of me. I found myself not really interested in developing the desktop version, so I found myself bitting at it and not staying focused. In fact a lot of the code ended up being developed on a Saturday morning while my daughter was diving, like I am now. I have a an hour and a half to kill while she dives, you can only give your full attention for so long, and that was always a good excuse to have my laptop with my and work on LoM.
All being well with the Apple submission process, the game will be available in the Mac App Store for the Summer Solstice. The Windows version needs a little more testing and I need to find a home for it to be distributed. If that all doesn’t happen during the next week in order to hit the same release date, I suspect it will be the week after.I now find myself thinking about the next steps. Jure has already started work on, if not almost finished, the artwork for Doomdark’s Revenge, so there is nothing to hold me back there. I suspect that the actual next steps will be a new build of the mobile version of LoM to include the scaling map, the keyboard controls ( for bluetooth keyboards ), and a few bug fixes that were dealt with during the desktop development. The desktop code is just a different branch of the mobile version, so I just need to roll everything up. Being truthful, I also need to put an advert in the mobile version for the desktop version, it would be nice to pickup at least another 6k unit sales. Continue reading →
I know that I am a little way off this. But as I’ve seen the question raised so many times recently, I thought it better to officially post something.
Lords of Midnight is currently moving through its project life cycle. The Android version should be live tomorrow and I will be focusing on the Desktop versions for Windows and Mac, and any other possible mobile variants like Kindle Fire, and Windows Phone. As well as this I will be adding new features and rolling them out over the coming months. This I see as being an ongoing project. I don’t see any real reason to put an end date on it.
This brings us to Doomdark’s Revenge. Let me say this very clearly, and to be beyond a question of doubt. I WILL be releasing Doomdark’s Revenge. That was always the intention. It is important for me on two levels. Firstly, it’s only right that the tribute to Mike be both games. Secondly, it is important for me to finish this thing I started so long ago; I never did manage to get a Windows release of the The Midnight Engine that included Revenge. So, aside from everything mentioned above, it will be the very next thing I do. I have spoken with Jure and he is completely on board to produce the graphics in the same faithful retro style. See Tarithel sitting pretty in the corner!
The intention is to get Doomdark’s Revenge out before the end of the year. The hope is that it will be much earlier.
The current status is…
Art: We know all the graphics required, and Jure can just work his way through them. All things considered, we know it should take less than 6 weeks for that to happen. That would then free Jure up to get back to his other commitments. Worse case, we can have the game running with original graphics again until his work is finished. But I think I will be bottleneck, not him.
Code: The Midnight Engine, which powers Lords of Midnight now, covers most of Revenge, and the database is all in place. I have once already, to show Mike, run the engine and walked around the Icemark, with all the lords in place etc… The tunnels work. The Mist works. You can recruit characters. What is missing is the Revenge specific enemy AI. The data to drive the AI is in place. So I just need to do a full evaluation of the missing features, and work my way through it.
That is my total commitment for this year. I would like at some stage in the future to address The Citadel, and I need to give consideration for Eye of the Moon. Also, Jure and I have talked about the potential for an updated version of LoM with none-retro graphics etc… And then of course, there is 2014. However, all that will have to wait and be thought about with clear hearts and minds.
But, my commitment to myself, and therefore to you, is to release Doomdark’s Revenge. In the meantime, I hope you are enjoying Lords of Midnight.