Dust of Restful Death

The main story quest in Daggerfall Unity is cracking along lately. The more problems I solve, the faster I can pass new quests. This has created a cumulative effect where things are snowballing towards the finish line. Today, I feel I’ve reached an important milestone with the main quest passing up to “The Dust of Restful Death”, only a few short steps from the end.

In this quest, the player briefly soothes the tormented bones of King Lysandus to learn why he requires vengeance. From a technical front, this is not only the result of a long chain of earlier quests, but required some new interaction between the world and quest system, and is the first quest to play an in-game cinematic.

There are bound to be problems and bugs to fix as the full story quest rolls out to testers, but for now let’s just enjoy this one quest where Lysandus has his big moment.

Vengeance Build 81

New builds are now available on the Live Builds page, bringing us up to build #81 across all platforms. A lot has happened over the last month, with steady contributions from long-time Daggerfall Unity developers Lypyl, Allofich, TheLacus, and Nystul. I would also like everyone to welcome on board new developer Hazelnut, who has built many valuable updates over the last month.

I’ll post a more complete list of updates towards the end of this post, but want to start with the big visual stuff that’s changed since last update.

 

Main Quest

The complete main story quest is now offered when starting a new level 1 character. Please keep in mind this is still under construction, so you are likely to reach a point where you cannot continue and may need to start fresh later (or use a console cheat). It could be another few months before all main quests are in a passing state, but I felt it was important to start offering to new players.

Continue reading

The “Fighters” Update

The Fighters Guild awaits

A whole new cycle of Live Builds is now underway for Daggerfall Unity 0.4. Here are some of the new features you’ll find in the latest “Fighters” update.

 

Quest System

The quest system is now open! Visit any Fighters Guild and speak to the usual quest giver to receive a random guild quest. Be sure to bring your strongest character, because quests span everything the Fighters Guild has on offer, from rats to liches.

Mordane Yeomham has work for you

 

While still incomplete, the quest system in Daggerfall Unity manages to kick things up a notch over classic:

  • No more binary QBN/QRC files and command line compilers! Quest scripts can be created with a simple text editor like Notepad and are based on Donald Tipton’s TEMPLATE v1.11 scripting language, the de facto standard for creating Daggerfall quests. If you’ve written Daggerfall quests before, you already have the skills needed to write quests in Daggerfall Unity.
  • Quests scripts are JIT (just in time) compiled by Daggerfall Unity. This means you can write new quest scripts and test them while the game is running.
  • Daggerfall’s classic quests have already been migrated to the new scripting language and many quests are perfectly playable in Daggerfall Unity now.
  • New features! Daggerfall Unity is already extending the capabilities of the quest system beyond what’s possible in classic, such as using location exteriors in quests. It’s even possible to write new quest actions in C# and extend quest system through mods.
  • The Quest Debugger lets you see what your quest is doing at any time by displaying the internal Task states and Timers, and helping you find buildings quickly. This debugger will continue to grow in power as the quest system develops. Note: Quest Debugger is always enabled in “Fighters” update. A toggle will be added once quest system passes tests.

 

Real Skills

Be prepared! Daggerfall Unity now has real combat formulas, including weapon and armour checks, dodging, critical strike, and more. If you take on a vastly more powerful enemy, you might not land a single blow.

How do you like me now?

 

Skill and level progression are now working. Your character will grow in power by playing the game and be able to level up at last. Skills like dodging and critical strike will be checked during combat, and skills like medical are checked during rest. Daggerfall’s level-up formula is applied on travel and rest, and you’ll go up in level once your skills have been raised enough.

Practice makes perfect

 

You can now set your interaction mode using F1-F4 (default keys). Use Info mode to find an NPC or building name, and use Steal mode to try your luck at picking locks. This even checks your Lockpicking skill against the lock using Daggerfall’s lockpick formula.

Maybe a more direct approach is needed

 

New UI Windows

The exterior automap will help you navigate around town locations. Named buildings are marked automatically for now, and the Quest Debugger will direct you to quest buildings until the discovery and “talk” systems are implemented. Like the dungeon automap, you can zoom, pan, and rotate the map. It’s great dragging the map around with left mouse button rather than using arrow keys.

Now, where was I?

 

The keybind interface will help you bind keys just like in Daggerfall.

No more editing text files

 

Wandering NPCs

Mobile NPCs now wander the streets during daylight hours across all climates in Illiac Bay. Meet Nords, Redguard, and Bretons in your travels.

Excuse me, do you know where I can sell all this orc blood?

 

The “talk” system has not yet been implemented in Daggerfall Unity, so you can’t yet speak to these wandering people to ask for directions, rumours, and so on. This will be coming sometime in 0.5 update cycle.

 

More Mods

All the mods that were previously integrated with Daggerfall Unity now have standalone updated versions from their creators. Available mods are on the Released Mods page of the forums. Please let the creator know if you encounter a problem with their mod.

You can now create art replacement mods for Daggerfall Unity. Check out the new Modding pages for more details on how to replace textures, sprites, models, sounds, and movies. A few great-looking art mods are already in the works, such as the Terrain Flats art mod by jman0war. He is hand-painting all new terrain art and it looks amazing.

 

And in case you didn’t know already, Daggerfall Unity has a runtime C# compiler, mod packager, and mod loader. This has been available for a while, but not a lot of people seem to know about it yet. Check out this page on the forums for more information on creating a Hello World styled mod in C# for Daggerfall Unity. You could even make a mod that adds custom actions to the quest system!

 

Get Involved

You can find the latest builds on the Live Builds page as usual.

For conversations, please use the following forum thread for all talk and bug reports for now. More information will be found in that thread to help you run quests.

 

Credits

I have the following people to thank for their contributions to the above features, in no particular order:

Allofich – For tirelessly working on skills, formulas, level ups, and researching classic save format. Some of the real gameplay features in this release would not have been ready without his efforts.

TheLacus – For creating the asset swap capabilities, documenting everything, and supporting people in their efforts to mod Daggerfall Unity.

Nystul – For the incredible automap user interfaces and mods he creates.

Lypyl – For the runtime C# compiler, mod packager, and mod loader. Also for his help with reverse engineering building data during early stages of the quest system.

JustinS – For his perfect keybind interface.

And thank you to everyone else who has contributed smaller fixes and patches on GitHub: muderbeard, midopa, electrorobobody, and more. Daggerfall Unity has only come so far thanks to the ingenuity and generosity of contributors. The combination of open source and a brilliant community will take this project a long way in the future.

Cheers!

Town Populations

I’ve had my head in the quest system for several months and really needed a short break. I also happened to need a solution for spawning enemies outdoors in cities (for example, the ghosts and wraiths in Daggerfall at night) and noted there was a good amount of overlap between spawning enemies and NPCs in town environments because they all need to avoid placement inside building geometry. And whatever solution I use for placement could probably be used for navigation as well. I had scheduled wandering NPCs for 0.5 cycle, but decided to make an early start on this while solving town placement and navigation. And what better way to test this solution than to actually watch NPCs walk around?

The first problem I had was how to find an appropriate placement position. My initial idea was to use the foliage placement array in exterior data. This formed a nice grid over each block, but it also marched over water and under buildings. That would not be suitable. I considered just dropping in mobiles and using a combination of rays and colliders to refine their position until they found open space, but that approach seemed way too messy and inefficient.

That’s when I had a eureka moment thinking about how perfectly automap image data lined up with the game world. Take the below screenshot as an example. In game, I’m standing outside the Odd Blades looking at the entrance door. On the automap, once unit conversions are done, I’m in exactly the same place.

 

So Daggerfall’s automap perfectly skins building footprints. This should mean I can take the inverse of automap data to work out which parts of the environment are open. I quickly prototype by placing white cubes on open environment and avoiding the building footprints. Take a look at the results.

 

This is beyond perfect. The automap doesn’t just contain data for building footprints, but for flat placement and decorative geometry as well. I have a strong suspicion Daggerfall also uses the automap data in this manner, it’s just too precise and detailed to be a coincidence.

With a solution in mind, I now have to execute the idea. I create a new class called CityNavigation which is added to the location GameObject at scene layout time by StreamingWorld. This constructs a navigation grid at the same time location and automap data is read so only a small amount of additional processing is done per location. With the inverse of automap blocked out, we get the following:

This is good – the white areas can be used for placement and navigation, but it’s not perfect. It also needs to account for tilemap under location. We can’t place NPCs on water tiles, and they should try to avoid those tiles when walking around. Rather than just block out unwalkable tiles, I take this one step further and allocate each tile a specific weight, where a higher weight means the tile is more favourable. Here’s the final navgrid where black areas are “no-go” and brighter areas are preferred over darker areas. You can probably see right away this creates a strong preference for the road network:

 

What you can’t see in the above image is that each weight occupies the upper 4 bits of a single byte. The lower 4 bits are reserved for a flag system, giving me up to 4 bits to control NPC behaviours. This will be important later in this article.

Now that I have a nice procedurally generated map of any exterior location, the next problem is converting between all the different coordinate systems. If you’ve ever tried to make a big world in Unity, you’ll know that precision problems kick in after a few thousand scene units or so from origin (position 0,0,0 in world). This manifests itself through jittery movement and shadows, imprecise feeling of control, and issues with physics system. The game map in Daggerfall rocks in over 819,000 x 409,000 scene units, way beyond what Unity can handle with fine floating-point precision. I overcame this challenge very early on by using a fixed point coordinate system for the world (Daggerfall units) and normal floating point units for the scene (Unity units). The world is built around the player in chunks close to origin, and when player runs too far in one direction, the whole world is brought back towards origin. To the player it feels like they are running continuously through a huge open world, when in fact the world is being constructed around them one chunk at a time. The player never moves more than 1000 units from origin in the X-Z plane.

What does all of this have to do with the navgrid above? Well, now I have yet another coordinate system to glue together. I have not only the Daggerfall units and Unity units, but the X,Y position inside the navgrid array where any virtual mobile objects have to move around. So the next thing I do is write some helpers in CityNavigation to convert from navgrids to world space, world space to scene space, and back again, and so on. This chewed up a solid chunk of Sunday to get working properly, and there’s still a few precision issues due to the large differences in scale. Something to refine down the track.

With all the math out of the way, I can now start placing mobile NPCs into the world. One problem though, I hadn’t written any code to render wandering NPCs yet. So I started with these guys just to confirm the navgrid through scene conversions were working. Sometimes in game development, you have to bust out some programmer art to get the job done.

 

With placement working, next came the process of building the mobile NPC billboard properly – including that stop-and-stare thing they do when you get too close to them.

Town NPC Billboards

With rendering done, I can start moving them around the navgrid using a simple motor. They will generally follow roads when encountered (because roads have a higher weight), but there’s enough randomness to let them change directions and wander around elsewhere on the grid.

And do you remember me mentioning the navgrid can store flags in the lower 4 bits? The first flag I created is an “occupied” bit that lets a mobile claim a navgrid tile before walking into it. This prevents two or more NPCs trying to occupy the same tile at a time. The next clip shows the mobile movement, path following, and dynamic avoidance of each other. I’ve cranked up the spawn count and movement speeds because it helps me observe the behaviour (and it’s kind of fun to watch).

Mobile Pathing and Dynamic Avoidance

Despite everything accomplished, I still have more to do. The next step is working out which races are placed in which towns. I put my travelling boots on and tracked around classic Daggerfall’s world until I found which races appeared in which climate zones. I built this into the helper which returns climate data for texture swaps, etc. and now the correct NPC races (either Redguard, Nord, or Breton) will appear across the game world.

 

The final step was to build a PopulationManager class. This code handles spawning/despawning of NPCs around player as you move through town environments so the location feels populated. After a bit of experimentation, I used a population index per 16 RMB blocks so that small towns feel like they have a smaller overall population than large cities. One of my challenges here is the draw distances in Daggerfall Unity are huge compared to classic Daggerfall. While classic can place NPCs safely in the fog out of sight, in Daggerfall Unity you can see two full city sizes distant across the map. This means that hiding pop-in and pop-out of NPCs is a little trickier. For now, I mitigate this by trying to only show or hide NPCs when player is not looking directly at them (as Daggerfall does) and only allow them to pop-in when a certain distance from player.

There’s still a few bugs to iron out. You can still catch them pop-in nearby if you happen to look in the right direction at the right time, and they sometimes glide slightly in the wrong direction on spawn due to precision issues as they align to the grid. And of course you can’t talk to them yet, because the “talk” system won’t be introduced until 0.5 sometime. But overall, the feeling of crowds is quite satisfactory and Daggerfall-ish, and it’s wonderful to finally see these sprite people bustling around cities.

I hope you enjoyed reading about some of the work that goes into creating even a small feature like this one. If you’d like to read more, I try to post regular micro-updates to my Twitter feed @gav_clayton.

 

Closing The Loop On Quests

For the first time yesterday, I was able to run a full quest in Daggerfall Unity from start to finish, and I’m very happy to say that a sizeable chunk of the quest system is now implemented. Following is another quick visual diary on what I’ve been working on lately. Where possible, I’ll share some information on what the quest system is doing in the background. There’s also a new video at the end.

 

Guild Quests

I have partially implemented guild quests with their usual service providers. Visit the quest-giver NPC in any Fighters or Mages Guild across Illiac Bay to receive a quest from a curated pool that is “mostly working” in Daggerfall Unity. This system helps me set the scope for testers, and introduce new quests over time as more of the quest system is built. Let’s take a look at this in action by following a quest from start to finish.

 

If you have  a sharp eye for Daggerfall quests, or have ever written one yourself, you’ll notice a lot is happening in the screenshots above:

  • Quest-giver NPC is identified by faction ID and the guild service window shows “Get Quest” as it should for that NPC.
  • The quest offer process is in place for you to accept or refuse job offered.
  • Many text macros are expanded automatically – such as random monster name, target location, player’s race, current region, and so on.
  • Reward is being randomly generated based on quest script.
  • Travel time is calculated from world using same logic as travel map, ensuring player has enough time to travel there, find the item, and return back.
  • The quest log information is generated and stored in the journal with current date, return location, quest-giver NPC, target monster, and how long you have to complete quest.
  • The quest-giver (Mordyval Moorhart) has also been tagged as the Questor NPC for this job. The quest system will keep track of your clicks on this person to know when you’ve returned with the wrappings.

If you travel to the named dungeon and explore it thoroughly, you will eventually find the mummy who is the target of this quest. If you don’t want to search you can use the ‘tele2qspawn’ and ‘tele2qitem’ console commands to teleport directly to the target spawn or item markers in dungeon. However you find it, kill the mummy and the target quest item is placed in its inventory for you to loot along with other randomly generated treasure.

Here are some of the things the quest system is doing under the hood in the above screenshots:

  • Tracking when player visits target dungeon and injecting the mummy into world.
  • Capturing script events like “injured foe” and “killed foe”. In this particular the quest, the mummy wrappings are placed on the monster when you injure it.
  • Tracking quest items, setting their background green, and displaying scripted text after picking up the mummy wrappings.

Now it’s time to return to Mordyval Moorhart for our reward.

In this step, the following stuff happens in the background:

  • Quest script detects you have clicked on the Questor NPC with the target item.
  • The QuestCompleted text is shown for a successful outing.
  • A loot container opens with your agreed-upon reward.

In classic Daggerfall, if you accidentally close the loot window without getting your reward that item is lost. I’ve made a small change where the reward is placed into a dropped loot container at your feet if you forget to collect it. This at least gives you a second chance to pickup your loot.

 

With all of the above working, this closes the loop on the quest process for a whole bunch of quests. It’s not just mummy wrappings, a lot of quests involving item hunts and killing monsters all operate inside this same framework. Where things fall down right now is with some of the special script actions that add flavour and complexity to quests. These remaining quest actions and conditions will be built out over time until quest system is at 100%.

 

Escort Quests

Sometimes a quest will ask you to take an NPC somewhere, such as rescuing the below person from a giant slain as part of a Fighters Guild quest. It seems the giant had been keeping this person for a snack.

A lot is happening in the above side-quest:

  • The quest script selects at random from a victim NPC, a map reward, or no map and no victim. In this case, the victim NPC was selected.
  • The random NPC Lysausa Gaerwing and her home town of Crosswold Borough are generated, giving her a bit of a backstory.
  • According the quest log, she wants to be delivered to Lord Mordoryan’s Wares, a shop in Oxville. Note the %g2 pronoun macro isn’t working yet. This is on my todo list.
  • When accepting the escort, a portrait (which usually does not resemble NPC flat in world) is added to your HUD to show this person is journeying with you.
  • The quest system tracks when player enters target building, displays the scripted popup, and removes NPC from your HUD.

 

Artifacts

A smaller task than above, but still necessary for the quest system is the ability to spawn artifact items. These special items are created by merging two sets of template data together to form one very powerful item with a larger than usual number of enchantments. While magic system isn’t in the game yet, certain groundwork still needs to be implemented. Because I’m looking at spells and effects in the update chain immediately after quests, now is a good time to start thinking about this stuff. Artifacts are still at a very early stage, and I might not return to them for a while.

The character above is holding Chrysamere from a quest script intended only to test these items can be generated by quest system. A big thanks to all the people who sent me their saves so I could test artifact import and creation. I still have some bugs to fix, but I’ve made a good start on this.

 

Conclusion

The quest system is doing great. It’s still a ways from being finished, but all the hard problems have been solved and now I’m just building out support for remaining actions and conditions, and fixing bugs along the way. The next items on my list are multi-spawn foes (e.g. kill 6 rats in a house) and more work on text support (like the %g family of pronoun macros). There’s bound to be a few more articles to go before I can call quests complete.

If all goes well, I should have the first real test build with the quest system in current state available in 2-3 weeks. This will have the Fighters and Mages Guild quest system in place for testers to run through available quests and help me find bugs. You’ll also be able to use ‘startquest’ console command to launch whatever quest you wish, even quests you write yourself, but things might not work properly if you go too far off grid for now. I’ll post more about the test build once it’s ready, including any limitations in the build at the time.

Thank you for reading! If you would rather watch quests in action, following is a pure gameplay video of Daggerfall Unity, except I’m using the console cheats to teleport to objectives in dungeons for the sake of brevity.

For more frequent updates on Daggerfall Unity, follow me on Twitter @gav_clayton.