Entertaining new video by ZetaPlays covers all the new stuff in 0.4.
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.
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.
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.
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.
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.
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.
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.
The keybind interface will help you bind keys just like in Daggerfall.
Mobile NPCs now wander the streets during daylight hours across all climates in Illiac Bay. Meet Nords, Redguard, and Bretons in your travels.
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.
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!
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.
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.
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.
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).
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.