1. Lords and Villeins
  2. News

Lords and Villeins News

The Path To Pathfinding In Lords and Villeins

The public beta for the campaign update is soon coming to an end. In fact, we expect it to go live as early as next week! Besides re-designing the tutorial experience into fifteen distinct missions, each focusing on a unique game mechanic, we are adding one more major improvement to the game - overhauled pathfinding system.

It is improving performance dramatically and because we went through quite the journey of solving it over the years, maybe it would be a fun read to share it with you. So let's get into it!

[h2]What is Pathfinding?[/h2]
If you are not sure what pathfinding is, let me first introduce it a little bit. In the world of AI, we typically refer to NPCs or other intelligent creatures - in our case the villagers - as agents. Agents can do a lot of things, but almost all of them involve getting from one place to another in the game world. So pathfinding is just that - mathematically solving the problem of finding a viable path between two points on the map.

In most cases, this is about as complicated as solving a maze with a pen. You start at a starting point and gradually explore all directions until you reach your goal. If you are smart, you prioritize your choices when to take turns by taking guesses. For example, if the goal is on the right end of the maze, it does not make so much sense to explore paths on the left before you explore the path to the right. It could be wrong, but on average, making these kinds of smart guesses will make you faster. So the art of making the right kind of guess is also a big part of pathfinding.

[h2]Common Approach[/h2]
At first, I utilized a very common algorithm known as A*. It is quite simple and sufficient for most games. The main premise is to make a good guess about the next direction, while exploring multiple paths at the same time. As it alternates between each direction, it keeps track of how long the path is so far and a guess about how many steps are left before it can reach the goal from where it currently is. Then in every step, it simply explores the direction that is most likely to be the shortest until either all options are exhausted, or the goal has been reached.

This algorithm is often quite fast, but when paired up against hundreds of villagers each searching multiple paths every frame, sometimes across the whole map (which is not small, especially the experimental ones), it was soon obvious this would not hold on its own.

[h2]Memory To The Rescue[/h2]
The first thing I considered was to have villagers remember things more, so they do not have to calculate the paths over and over again. After all, if the maze did not change, why not just store already calculated paths in the memory and simply ask for it again later? Furthermore, each discovered path works in both directions, so if they are stored, only half of the maze needs to be solved.

This was a nice idea in theory, but the reality was quite different. On larger maps, memory was bloating really fast, reaching several gigabytes of extra storage. And unfortunately, it was not even making anything faster for two main reasons.

First is that our villagers recognize differences in where they are allowed to go. Not every villager sees the same "maze". Some can pass through some doors, some can lockpick them, while others must avoid them completely. So they are relatively unlikely to ever share already calculated paths with another villager. Most paths were never reused, until nearly all path-finding maps were fully solved and already taking gigabytes of data.

The second problem was the fact that our world is very dynamic and constantly changes. Whenever someone builds a wall, any paths that are going through this location must be thrown away. If we destroy a wall, there could be an already stored path that could now reach its goal faster. We can keep it anyway and sacrifice the accuracy for performance, but this can get quite extreme and it is not very practical. And since there is no good way to tell which paths would be affected, in the end, all of them had to be discarded with a single change on the world map.

The third and small issue was that all of the memory would be lost whenever you would reload a save file, so attempts were made to also serialize this data. This however led to extreme loading times and very large save files, so I abandoned it quickly as well.

[h2]Multicore Approach[/h2]
Most CPUs nowadays have multiple cores that can be leveraged to improve performance, but this does not happen automatically so as my next attempt to make things better I went in to write an architecture that can leverage them.

Every agent now registers the paths they need and puts them in a queue. Then every frame, the pathfinding service would create a batch of multiple requests and schedule them for completion. This allowed me to compute multiple paths at the same time each on a different core during a single frame. The downside was that there was now a guaranteed one-frame delay for each request, but it was a small price for the gains in performance.

Having a queue of requests also allowed me to prevent spikes by limiting how many paths get computed every frame. This eliminated nearly all performance spikes unless a rare very long path would have to be calculated. On the other hand, if a lot of agents requested paths at the same time, they would now have to wait several frames before their request was completed and it introduced a new problem - villagers periodically stopping and standing while waiting for the pathfinders' response.

This was especially apparent every time a wall was built or destroyed. All villagers had to stop their movement, request a new path, and then wait for several frames to get them. This made any large maps with hundreds of villagers frustrating to play (though they were not exactly playable before either).

Despite this, performance gains were still very significant. I also converted the code to use native data structures in order to utilize Burst compiler. To cover how it works would be rather complex so let's just say it made each iteration of the pathfinding run a lot faster on the CPU. And this is where we were until now.

[h2]Hierarchical Pathfinding[/h2]
Pathfinding is now becoming pretty fast but it still has two major downsides - very long paths still take forever to compute, and any time something changes anywhere on the map, all agents must request a new path. It was clear that hierarchical pathfinding would be necessary to solve this.

This one is more difficult to explain, but in essence, it works by separating the map into individual clusters - rectangles of a uniform size. What we want is that any change inside of this rectangle will only affect the rectangle they are part of, and its direct neighbors. If we can somehow do that, not only we can now store some paths in the memory without having to constantly throw them away, but perhaps we can also leverage this to make very long paths to be calculated much faster.

To do this, we will search on the border of each cluster, and create a connection with its neighbor when we can see that an agent could cross the border there. We can also merge some of them to reduce their amount (with some limitations that I will omit here for the sake of simplicity). Then we will calculate a path between all connections inside of the cluster to get something like this:



Now each time a world changes, we only need to repeat this process for the cluster that contains this change. It also turns out that solving just the connections between these entrance points and connecting them in a chain will be very close to the most optimal path for any combination of points on the map. So our pathfinding almost magically becomes a lot more simple.

Because we know which points can reach other points and how long is the path that connects them, we just need to connect the dots on the way to our destination and search for some final bits around the starting point and the destination. If this is too complex to understand, think of it as an abstract orientation map. Instead of having to look directly under your feet with every step, there are direction signs all around you and you just need to blindly follow them.

On a large map of 192x192, traditional A* had to solve sometimes up to 40 000 nodes to conclude its search. On a map of this size, we would create on average between 1000 to 1500 crossings. This makes the maze that we need to solve about 5-10% of its original size. So this abstract map pre-computes about 90% of the complexity of the pathfinding that is shared between all possible paths, leaving the final 10% to figure out some details specific to each combination of the starting and destination points.

This makes even very long paths solved blazingly fast for only a small amount of added memory and a tiny loss in accuracy. And because searching individual paths is so much faster, it does not really make sense to store any of them anymore, since the cost of managing this storage would likely outweigh the benefits of it. What makes sense to do here, is for each agent that follows a path, to also remember which clusters it will go through, and have them request a new path only if these clusters get modified before they reach the final destination. Occasionally they might take a longer path when a shorter path just opened up for them, but these scenarios should be very rare and we can avoid the awkward occasional village-wide halting of movement.

Every path can also be re-traced and smoothed out for only a small extra performance cost to make the final path nearly exactly the same as any high-cost low-level A* algorithm would find. In the end, I decided to make this step optional so players can toggle this in settings if their CPU can handle the workload.

[h2]What is the Catch?[/h2]
Of course, all optimization has its tradeoffs. In this case, building a wall needs to rebuild the cluster immediately, which in rare cases can lead to a performance spike, if the cluster is particularly complex. We are also taking up a bit more memory than before to do this. Searching the path in this abstract map is also very difficult to do natively so the benefits of Burst have been somewhat reduced. Loading times were also extended by up to 10 seconds on very large maps as this abstract map needs to be solved before the game begins. Multiple cores are still leveraged and they make updating a cluster a lot faster, but they do not have a lot of impact on individual searches.

I hope you enjoyed this rather technical read! I would like to open up about the complexity of our game, to shed more light about the challenges we face when optimizing it. What we do is not typical for indie games and it is not always easy to see as much of that work happens under the hood.

If you did enjoy this article, let me know in the comments and tell me if you would like to see more of them! There is a lot of interesting stuff to cover, so I would be happy to share them with you. In the meantime, come hang out with the community on our Discord, and celebrate the Strategy Fest with us!

Michal
Honestly Games

Update 1.3.20 Has Found Its Way To The Public Beta

We greet you, Lords and Ladies,

The time has come to update Lords and Villeins once again! This time, we focused on fixing as many annoying bugs as possible, along with improving some QoL features and balancing the game in general. For now, this update can be found in the Public Beta version where you can test it and if there are no issues, we will push it to the main build soon. You can find the whole change log below the article.

If you're still not a part of the Public Beta and you wish to be, entering it is incredibly easy! All you have to do is right click on the game in your Steam library, select Properties, Betas and find the "artisanbeta" branch. If you encounter any bugs or have any feedback to share, we would love to hear from you! Share them here on Steam forums, or come join our dedicated Discord server.

It's also worth mentioning that Lords and Villeins is a part of the currently running Strategy Fest, meaning it's discounted by 50% - that's a hell of a bargain, isn't it? And to spice things up even more, if you get the game along with the whole bundle that includes the official Lords and Villeins Soundtrack, the discount will apply there as well, that means you will save even more money!

https://store.steampowered.com/bundle/28876/Lords_and_Bards_bundle/


[h3]Change Log:[/h3]

Bugfixes:
  • Fixed missing arrow icon in animation of resource transactions
  • Fixed Paper Mill continuing animation after it finished processing paper
  • Fixed incorrect length of task execution for collection and storing of resources
  • Fixed some storages not being displayed in the storages category (silo, weapon rack etc.)
  • Fixed bug causing caravans attempting to see a theatre play (they are not meant to)
  • Fixed average beauty value of a villa being incorrectly evaluated
  • Fixed visiting noble family prioritizing dining in the Inn over eating meals from the warehouse
  • Fixed visiting noble family being required full attendance on Sunday Service. Only appointed bishop and existing Chapel is meant to be required.
  • Fixed changed family size when starting a new game not being reflected
  • Fixed game modules being always reset to no game modules selected after restart
  • Fixed issue with Royalty not improving relationship if the deliveries exceed their target over 100%
  • Fixed soldiers attempting to wear Tools
  • Fixed grid pattern being modifiable during removal mode
  • Fixed gathering intelligence task in the campaign not updating the label on progress
  • Fixed a bug preventing clergy from generating demand for paper
  • Updated Scenario 4 starting map, where Butter family now has appropriate amount of beds
  • Fixed input field in the accounting report screen reacting to numbers being pressed in modifying the game speed
  • Increased threshold on maximum length of path searched - this should solve a lot of inaccessible structure problems
  • Fixed bug causing visiting nobles to register poor meal flags incorrectly
  • Fixed storage capacity not being displayed on all storages in the hover menu
  • Fixed villagers taking and dropping money to purchase meal at the inn when it is not allowed to serve locals
  • Fixed Tutorial Tips toggle in the settings always getting set to true after restart


QOL and Balancing:
  • Families in the population book are now grouped by profession
  • Daily deterioration of noble relationship reduced by 50%
  • Removed sand from produced resources of the Furnace zone
  • Increased inventory capacity of Chest to 200Kg (increased from 50kg)
  • Increased inventory capacity of Bar to 50Kg (increased from 15 Kg)
  • Hunters now hunt for up to 6 corpses in the knackery (increased from 3)
  • Visiting nobles arrive with only 2 excellent meals
  • Gem Ore has now 15% probability to be mined (increased from 5%)
  • Rabbits now yield 1 hide and 10 meat (increased from 0 hide and 5 meat)
  • Sheep now generate 6 wool each harvest (increased from 2)
  • Swapped priorities of producing paper and leather on individual steps to maximize producing the resource (paper, leather) instead of the consumption of material (rag, hide)
  • "Anyone can build" category in the construction queue is now disabled if a higher construction tier is selected (it would never display any blueprints).
  • When clicking on a button to display full production queue on a blueprint it now correctly initializes the accounting report to display the queue that contains the blueprint (select correct family, category and tier)
  • The sex need is no longer displayed in intelligence reports if deprived and it no longer impacts happinness or mood. This is because in many cases villagers struggle with this need simply because they do not yet found a partner and the player has no control over them doing so, which only leads to confusion.
  • Farmers will now only start harvesting if a certain amount of crops are fully grown. This is evaluated once a day per zone, and the limit is reduced if the amount of planted crops in the zone is lower than the limit. This further optimizes farmers to harvest and plant crops more efficiently.
  • New game module added that allows you to limit the amount of people attending the Sunday Mass without penalty.

Update 1.3.17 Has Just Arrived To The Public Beta!

Greetings, Lords and Ladies,

We have some really good news for you! The previously announced free Campaign update is now ready to enter Public Beta! We will keep it there for a few days just to make sure everything is how it should be and later release it on the main "branch".

This patch focuses on redesigning the tutorial experience into a more in-depth and approachable campaign. We have prepared fifteen distinct scenarios, each focused on one major game mechanic of Lords and Villeins which can now be introduced in bigger detail, with video tutorials, tips and challenges along the way. As you progress through the campaign, you will unlock more features until finally reaching the full complexity of the sandbox mode.

While new players are the focus of this patch, we also wanted to bring something for our existing players to play through the campaign. So for each campaign map we are adding a unique scenario with special permanent buffs that alter the gameplay in a thematic way. As you progress through the campaign, you unlock these buffs into the sandbox mode, where you can play with any combination of them as you like!

As of now, we are releasing the update with only the English localization, but we will be adding other languages before the patch goes live on the main branch, which is when we will also update the wording of any tutorial-related achievements.

HOW TO JOIN THE PUBLIC BETA:

If you're still not a part of the Public Beta and you wish to be, entering it is incredibly easy! All you have to do is right click on the game in your Steam library, select Properties, Betas and find the "artisanbeta" branch. If you encounter any bugs or have any feedback to share, we would love to hear from you! Share them here on Steam forums, or come join our dedicated Discord server.

[h3]What Is Next?[/h3]

While this marks the end of the previously announced three major post-release patches, that we have announced at the end of last year, this is not the end! We continue working on the balancing and performance and we have more amazing things to announce soon, but right now, we are still not ready to bring you more details. So, we will just leave you with a mysterious teaser that we have recently published on our social media and let you speculate!



[h3]Change Log:[/h3]

Brand new campaign mode!
  • Play through 15 new maps, each themed around a core game mechanic of Lords and Villeins
  • Experience a narrative element of a noble house growing their reputation with the royals
  • The campaign is aimed to introduce new players to the game in a more detailed and approachable way
  • Each map introduces a buff that modifies the game behavior. Unlock these buffs for your sandbox games as you complete the campaign.


Other:
  • Added a new Settlement tab in the accounting tab that displays the wealth information
  • When placing trees or soil you can now use the scroll wheel to change the grid pattern
  • Family creation is now a separate step so you do not have to confirm it every time you create a new map
  • Expanded campaign with video tutorials
  • Default socage tax is now 25%
  • Brewing station, Filtering tub and Windmill no longer require a carpenter to be built
  • Added the ability to caravans to pick up trashpiles and keep them in their pocket in the unlikely event of dropping a trashpile
  • Restricted collecting resources the caravans own to only one person per family to reduce the likelihood of dropping a trashpile due to single-frame reservation concurrency issues
  • Added a note to caravan storage and storefront showing which family is assigned to them
  • Added a randomized maximum amount per item limit in the quest deliveries to prevent impossible scenarios (i.e. 600+ bottles requested since value of each bottle is low)
  • Variety of bug fixes


Also, please, note that the new content is currently localized to English only. The full localization process will start after we make sure that the build is in a good to go condition.

Summer Sale Is Here, The Prices Have Never Been Lower!

Hello everyone!

That time of the year is finally here, Summer Sale has arrived on Steam, and with it comes tons of discounts - so don't hesitate and get all the cool games to play when you wish to get cozy at home and hide from the hot weather outside.

Lords and Villeins is a part of the sale too! This time for a 50% lower price. It is a great opportunity to bring over your friends and enjoy this game together. Don't hesitate though - the sale ends on July 13!

To see the whole list of discounted games by Fulqrum Publishing, follow this link and head to "Discounts".

Care to get something extra? Lords and Villeins is also offering the Lords and Bards bundle which comes with the game and its iconic medieval Soundtrack. A perfect opportunity to complete your collection!

https://store.steampowered.com/bundle/28876/Lords_and_Bards_bundle/

The development team is fully focused on finalizing a brand new campaign mode, and we have other exciting things to announce later so stick around! The journey with Lords and Villeins is far from complete.

Patch 1.2.20 Has Just Arrived!

Greetings, Lords and Ladies,

We have a small, but important patch for you! We have fixed the critical issue related to family member duplication, changed some achievement requirements and adjusted a few more things to make the game as pleasant as possible!

Feel free to check the whole Change Log below!

NOTE: Save files from previous version (1.2.18) should remain compatible. However, there was an issue which duplicated nobles that were married during their visit and in case you have encountered this issue, we are unfortunately unable to recover your save file. We apologize for this issue.

  • Fixed critical issue of a noble family member being duplicated when married
  • Removed the "Everyone Is Here!" achievement (have all artisan professions on the map)
  • Changed the condition for "Settle them All" achievement. It now requires accepting a visiting family for each profession once across all games (peasant and artisan included)
  • Reduced requirement for the "There is Nowei" achievement to reach 250 population.
  • Homegrowing pot is no longer affected by underlying soil quality and always maintains 100% growth speed
  • Recruits and servants that were accepted through the council request will no longer trigger council request that asks to relieve them from service
  • Guards will no longer wear jewelry unless it is in their equipment preference set by the player
  • Vandalism will no longer target structures that do not deteriorate (and thus can not be repaired)