Let’s talk AI!


8th May 2020 – Perry

Caverns mode has posed a particular challenge in developing the AI, since from one test to the next, something entirely different happens.

In previous blogs we’ve written about the nuances of the spider AI and goblin warrior AI, but we haven’t talked much about the AI in general.

First of all, what do I mean by AI? In this case, it is the code that controls the behaviour of ally and enemy units, and to a degree the player’s units too. For the player, it simply controls the units priorities (when they’re not being controlled manually). As an example, a miner will work on mining tiles within their allocated instruction zone, unless they’re hungry or tired in which case they will take a break and go for a meal or a rest instead. Ally or enemy AI however must also define where these instructions go, and what buildings to build, and where.


In the campaign, ally AI is mostly scripted, so the map defines what they do and where, and we can be careful not to create scenarios that are confusing for the AI. This is not the case for caverns mode however, which is a randomly generated environment, so anything can and will happen. In this case, the AI must be an agent, that interacts with a world that we can’t predict or ‘hard-code’. Instead of scripting locations to work on, it must decide for itself where the best locations to mine, forage and build are.

Caverns mode has posed a particular challenge in developing the AI, since from one test to the next, something entirely different happens. During playtests, when I discover the AI has gotten stuck or experienced a bug, I can reason easily enough how to fix it, but I can never be sure whether I have or not, since the next time I test it it’s an entirely different scenario.

As an added complication, the environment is (almost) fully destructible, and has class-specific obstructions that prevent access to either resources or enemies. That rules out certain assumptions I can make about whether a unit can reach its target. It might not be able to now, but a few seconds later, maybe it can. To add to this issue, all the entities in the game are determined through properties that can be modified either through scripts or even in-game (the intention is for modded content eventually). This means I can’t assume anything about a particular entity, I can only see what its properties are. All of this together means the AI can get confused in very specific circumstances, and it’s not always clear-cut what those are or how to solve them.

There are still a couple of scenarios that I don’t really know the answer to yet. One such scenario is when there’s an enemy across a river. When an AI agent encounters an enemy, dealing with them takes priority over other work, which makes sense in your usual scenario. However, when there’s an obstruction in the way, like a river, this causes two enemy units to stand by the river’s edge and yell curses at each other all day, instead of working.


Although I can tell the units to ignore an enemy if they can’t reach them, how do I know when to stop ignoring them? Due to the destructible environment, it could be seconds or hours before there’s an accessible path, and it may be an entirely different route to the one that was obstructing them in the first place. My present solution is to simply wait a number of seconds before considering dealing with a particular enemy again. This will take some refinement however, since it’s unclear how many seconds will a) allow the unit to be productive with work, and b) not make the unit exploitable by ignoring an enemy for too long. Only time (and lots of playtesting) will tell if this is an effective solution.

As for new developments in the AI, I will save that for a future blog. I believe the game will see a small update soon (mostly with bug-fixes), so stay tuned for that. Until next time, keep your helmets on and your axes sharp!



2 thoughts on “Let’s talk AI!

  1. This is fascinating. I am sure you have the most interesting department within programming to work. I developed an AI for a game of Yahtzee and that was hard enough! It has a moderate average score compared to humans, getting it higher would take a lot of work.

    I like that the soldiers stand shouting insults at each other instead of doing something more useful, that’s funny!

    I wonder if you can factor-in some environmental variables that help the characters with their decision-making – so, rather than attack an enemy because they are nearby, perhaps each enemy unit can have a perceived threat level and this is what triggers attacks, or not. A river or obstacle could be assessed as being likely to be breached or not, or even that the edge of the river is in a fog of war – therefore, a new potential task will be recorded, that of finding that hidden information, if that becomes more urgent then the character could go and find an answer to it and explore. However, if the enemy’s perceived threat was fairly low, perhaps this task would be a lower priority than working. Alternatively, he might relay that information to another nearby unit or next time a friendly unit passes him “hey, go check out that fog of war to see if the river ends or not”. Knowing nothing about games development, or AI, I assume that this would take up too much processing and create other much more complex issues, but I enjoyed talking through the thoughts you gave me anyway!

    Thanks for sharing the insights into a programmer’s mind!


    • The most challenging part in this is deciphering which fog of war, or tiles of river are relevant. In a sense, AI is blind and can only see one tile at a time. This makes it hard to get a full picture of an environment, and what is obstructing what. It’s certainly doable, but I might have to write some maze-theory functions so I can rule out chunks of the environment efficiently. It’s more work than I can afford right now at any rate.


Leave a Reply

Please log in using one of these methods to post your comment:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

This site uses Akismet to reduce spam. Learn how your comment data is processed.