All posts by Patrick

I'm a game developer who's been in the business since 1993. I'm currently a Lead Designer at Hidden Path Entertainment.

So Many Datafiles

Yes, Technical Debt is still rearing its ugly head.  One of the things that any procedurally-generated Roguelike has is a ton of different files that hold profiles that define how to generate cities, landscapes and enemy encounters.  And tables, so many randomized tables!

sceneinspectorDuring the 7DRL I found an expedient solution that worked for the challenge and a fair amount of time afterwards.  I baked data right into each Unity scene that I saved out, imagining that I could just make a scene for each type of scenario or terrain profile I wanted.  I could bake in components that had all the predefined information I needed and just load them as needed.  I could even drag-n-drop the appropriate prefabs for everything I wanted to spawn.  How simple.  Sure, it nagged at me that it wasn’t super extensible, but scenes were cheap to make and I was interested in how far it could get me.

Wellll, it turned out it was pretty far, but eventually it started to haunt me.  The more scenes there were, the harder they all were to maintain, even if all the common information was kept in Unity prefabs.  Oh god, the prefabs…  they are great sometimes, but they also can puke all over themselves if I moved files around or a metafile got invalidated somehow.  Also, any time I wanted to choose something randomly, it felt like I was writing new code to deal with it each time.

I also used the serializer for a number of structures, but there was always a desire to have more flexibility when reading data.

Anyway, I knew I needed to up my datafile game.  My friend Jim’s amazing RL Dungeonmans has something like 500+ datafiles holding anything from name generation to encounters to tile definitions, with weighted randomization tables and tables that reference other tables.  How slick!  He spent many years refining his data methods and he encouraged us to reuse his approach in our own games.

So last weekend I finally bit the bullet and built a datafile system around some of the same concepts and in the end my format is virtually the same as Dmans.  This way I can build a sector with a pretty flexible format:

defThing sector_basic
{
 class adSectorData
 scene Overworld

 biome Desert
 nametable sector_name_chart
 treasuretable sector_treasure_table

 music mus_desperado

 basic_city_table 1d2
 sector_outpost_chart 2d4
 sector_town_chart 2+1d3
}

And these tables have some handy reference capabilities (recursing through each table referenced) and weighting for randomized results:

defTable "sector_name_chart"
{
 #t1 "sector_place_types"
 #t2 "place_nouns"
 #t3 "sector_adjectives"

 "The [t1] of [t2]" 10
 "The [t3] [t1]" 10
 "The [t1] of [t3] [t2]" 10
}

defTable "sector_adjectives"
{
 "New" 10
 "Old" 10
 "Dry" 10
 "Frosty" 10
 "Winding" 10
 "Hewn" 10
 "Locked" 10
 "Winding" 10
 "Ancient" 10
     ...

…and bingo, my world generation becomes 10x more flexible and powerful.  I’m dyin’ to get back to the drive-shoot stuff, but this was so worth it.

namegen

Late Night Asset Store Addiction

The Unity Asset Store is a great temptation at all times, cleverly one click from my development environment.  When you’re stuck in the dregs of some less-than-glamorous code snarl, it becomes the devil.  An Asset Store 24-hour sale are basically late-night Ronco TV ads for game developers.  Just 10 bucks for the next 2 days!  30% off!  But hey, this might be just the thing your game needs to be awesome…

Recently I bought a Volumetric Clouds package, hoping that I could get some cool, turbulent cloud cover with shadows over my landscape as the player wanders around.   Looks pretty good, but my poor frame rate just couldn’t handle it, especially at high resolutions.

Clouds

The solution involves a sweet technique of rendering many layers of a noise texture so it piles into a volumetric shape.  It seems to run pretty well for ground scenes looking up at the sky, but for my particular situation it didn’t quite fit.  Maybe I can’t use it for Auto Fire, but it’s a clever enough solution that looks great in a lot of cases, so I don’t feel too bad supporting the creator.

I don’t want to obscure the map features anyway, so just shadows would probably do the trick.  I might be able to do an extremely cheap version of the shadows with some some screen space projection instead…  but there are a hundred other things to do first.

I stumbled on another Unity sale recently that dangled a plugin called Beautify in front of me.  “Add a pro look!  Punch up your colors!  See the detail!”  I couldn’t help but bite, because I’m always wondering what I can do to eliminate the muddiness that I sometimes get with Unity, especially when I shrink assets that are intended to be experienced at realistic sizes.

A good chunk of what Beautify does is apply a sharpen post-process, along with some LUT’s to enhance some coloring.  I must admit there’s an appeal to seeing those shrunken assets appear sharper against the terrain or ground surfaces.  (You’ll probably have to click to see the difference).

Before
Before
After
After

It punches everything up and everything gets a nice feel in comparison.  However, it uses a sharpen filter, so I have to balance its use versus all the work built-in antialiasing does.  So, while it helps eliminate some of the muddy appearance (something I equate with unpolished products), it adds a lot of shimmer and harsh pixels (something I equate with unpolished engines).  In the end I probably just need some lighting help from a real artist. 🙂

Anyway, I can turn down the sharpen or nix it if I want, which is good because I like the results Beautify gives me with color.  It’s also got sweet bonus night vision and thermal views.

Nonetheless, I’m still looking for the right combination of lighting and filters to attain the pro look I’m after.  The quest continues…  and my wallet fears the night.

Overworld Madness

I’ve had some pretty great results so far with generating my terrain and dynamically placing road decals as needed.  The Easy Decal 3D solution ended up being pretty great.  The folk at &u Assets were super-helpful, and with clever use of their baking and decal combine features my roads went from 20 fps to 200 fps.  So, basically solved, and it’s worked out pretty well for putting interesting terrain features when staring down at splat-mapped Unity terrain starts to get tiresome.

I feel pretty good about the look and feel of my overworld, as well as the scale (which was a concern since it’s extremely exaggerated, even though I wanted a gritty feel).  I still have a ways to go before I can finish up my core loop and release a build, but things have leveled up a fair amount.

Overworld Development

I know it’s been a while since I’ve updated, but there hasn’t been a lot going on that’s particularly showable.  My Perforce checkins show that in the past few months I have…

  • AutoHomeChar08132016Used a landscape generation tool called Gaia to generate custom baked landscapes that I can use for specific locales or pre-constructed sections of the overworld.
  • Created a home base area for the player to start in.
  • Project movement grid information on the ground to help navigate some areas.  I’ll still work on making sure that they are clearly traversable.
  • Added charRavennaacters from Fuse in there, using some of the pretty good tools to grab some animations and basic clothing setups.
  • Enlisted the help of my wife Sandra to help get some characters together!  Nice being able to construct characters as easily as you would in a game like Skyrim.  And so far it’s free (knock on wood).
  • I’m still considering how I want to show characters in general.  I liked having them when I had a 2D game because it was easy to see what everybody was, but by going 3D I’m going to have some trouble with parseability.  I’m already scaling things up larger-than-life, but even more might be needed for humans.

AutoQuest08132016

  • Got together some basic quest granting, as well as a main stats screen for players to track the quests they’re on.
  • I also realized that I probably didn’t want a traditional quest system…  I’m not out to make Wasteland 3 or anything.  So, I’ve got the system but I’ll be working on evolving it to work even better with generated content.
  • AutoOverworld08132016Started thinking harder about the overworld experience.  There’s a lot of back and forth that happened here…  very briefly I thought about creating only one overworld zone and generating only content within.  However, performance considerations, as well as the interesting gameplay that can happen in the overworld, I decided to break it into sectors that include both generated and prebuilt areas.
  • Started to move towards the exaggerated scale I want to hit with chunky buildings and roads, but areas on the map with interesting states to deal with.

AutoDecalTest

  • Experimented with a number of ways to put roads on a generated terrain mesh, and so far have settled on Easy Decal 3D, which is a bit quirky but that’s pretty standard with Unity asset bundles.  I think it has a good set of features and make it run performant, if I can just work around some of the funky bits.
  • I’m hoping this approach will work.  It is the most dynamic, and would hold up best for generated terrain, but it’s also eaten a good chunk out of my frame rate and needs optimization.

This is all on top of investigation, data loading/saving, performance, and other things.  Hmm.  So yeah, I guess I was actually pretty busy over July.  Still hoping to get back to working on city combat stuff soon.

Patches and the Depth of Cities

This past week I’ve been polishing a new feature for procedural generation, patches.  This allows me to hand-create a collection of assets (both single-tile and multi-tile) that gets placed down in a singular area by the terrain/city generator.  It can be a solid square or only fill some of the squares within.  I can import any patch by dragging in a group of objects from a sample scene.  The tile system already converts the patches into the tileset currently in use by that map, and mixes in variants as they are available to the tileset.

Autofire_Patch_demoThe patch system has a lot of additional features yet to do.  For example, allowing the definition of patches in a nine-slice style where I can scale them to an arbitrary size with consistent edges.  This would allow me to create arbitrary-sized plazas, but more importantly, I can create a road patch that has signs, lights and various elements on it, that scales according to the length (and width if desired) of the road.

I also want to put in randomized prop points:  object stubs that will randomly place a specific prop in that spot, anything from a trashcan to a stain to an ambient effect.  It also allows me to place variants of an existing entity, such as a destroyed version.  This will be important so that my generated city doesn’t look all pristine the way it does above.

AutoFire_EditorsI didn’t expect to get dragged into city decor so early in AutoFire’s development.  It’s certainly a topic of interest to me, but the push in that direction really came from trying to find props for the game.  My 7DRL city was fine, it was basically a dungeon.  A dungeon can be a twisty maze of passages and hallways don’t necessarily need a specific direction of travel defined.  However, it felt like 90% of modern-day props required placement with some thought…  You can’t just sprinkle in mailboxes, street lights and stop signs via Random.Range(0, size)…  There needs to be established clusters and strips of materials.  I can construct hand-built areas anyway, but to extend everything into procedural town I’m pushing the limit of my limited home-grown tools.

Rolling from all this, I’ve also discovered as my game’s scale gets better established that I’m reaching a point where my single-square building assets are looking weirder and weirder…  I want the cars to be big and bold, and characters in the world to be larger than life also, but right now they are about two stories tall.  I was okay with something more abstract and representational when I was in 2D, but working in 3D makes that scale a bit more important.  Aaaaaand the only way to get my building “walls” closer to the “correct” size is to come up with a system for merging building squares into larger structures.  That will take a whole new post-process that…  I’m going to wait on.

DoomCarI’m quite aware that I’m running the risk of entering a bottomless pit of effort…  Making a city look like a city is hard, and many games make that their only thing, whereas I have
so much more to do.  So, I’m going to finish up this patch functionality and pull back to environments that are a bit easier to generate, such as frontiers, shanty towns, junkyards, and so on.  This way I can push back into mission generation and create some assassination missions and encounters.  This will finally lead me back to the promised land:  the refinement of driving mechanics, combat and its associated UI.

Glad all this is so fun. 🙂

Smoother Sailing

Another slow weekend with not a lot to show yet.  I’ve been digging into my simulation model again and working on some of the halting, awkward motion that both my tactical maps and, surprisingly, my overworld maps have had.  I’ve gotten a few complaints about it, and I couldn’t deny that it was really harming the feeling of speed I wanted to maintain.

A couple weeks ago I revised my input system so the player could queue up movements and move many squares quickly.  However, the player was not able to move that smoothly because the system always gave the rest of the world a chance to move before processing the next player action.  However, this happens even if there is nobody to move (such as when the player is going very fast and executes multiple moves per enemy turn), and even if there were no enemies at all (such as in the overworld)!

This was a useful thing to iron out, and I created a system where the game will stretch out executing any turn based on the longest time given it.  This defaults to 0.2, but with this, the player could execute a full, second-long super attack if he wanted.  Also, if no enemies are on screen, their moves are shorted or eliminated if they are far outside of the player’s awareness.  This gives me a lot more flexibility.

I also have turned into a bit of a Unity Asset Store addict.  I found some great music, vehicle models, terrain textures and even some more dang rocks…  it’s rather shocking how hard it is to find rocks that look good and fit with the rest of your stuff.  Looking forward to the next thing on my list, which is to create “templates”, or groups of objects to use in level generation.  Should be fun!

Auto Fire: Skid Marks

After a couple of evenings over the last couple days, I got skid marks working fairly well.  I had considered it a fluff component, but I also knew in my gut that skid marks could fairly easily show the player where a vehicle came from and whether it is under control or not.

Drawing arbitrary skid marks on the fly!

Generating mesh polygons on the fly in Unity was a new experience, but it wasn’t so bad.  The odd thing is that I spent an unnecessary amount of time trolling the docs and forums for info on supporting quads, and whether I’d have to define things in strips and fans and all that.  Instead Unity just asked for every triangle defined individually, and shared edges were not even an option.  I guess it’s been a long time since I had to deal with individual polygons, and the graphics layer has become just that much more sophisticated.  Does that make me a 90’s Voodoo/TNT relic?

Besides, I’m dealing with maybe 50-100 polygons here, so I’m hardly taxing the system…

Auto Fire: Technical Debt

As I am gainfully employed, my time working on AutoFire is mostly relegated to mornings before work plus weekends.  I don’t have any pretty pictures for you from this past week because I’ve been ripping out the guts of the game, getting it into a smoother-running and more manageable shape.

You wouldn't believe the number of pictures with stick figures holding up the word "debt" there are.
The internet contains precisely 51,245,721 stick figures holding up the word “debt”.

In programming there is a phenomenon commonly referred to as “technical debt”.  In short, it means if you take shortcuts  and the “easy way” for quick results, you usually pay the price down the road.  Those temporary fixes and band-aids that you applied in lieu of carefully planning and documenting your work gets built upon again and again…  Eventually that foundation of toothpicks and dried spit can’t bear the weight, and you realize that your work cannot be maintained.  You throw up your hands and say “This has to be completely redone!” This is the day your technical debt comes due.

In game development technical debt is common…  Early in a project you want to prototype all the gameplay quickly to give everyone a sense of how something works.  You try things, you iterate on an idea to make it better, you try to “fail quickly”…  You do all those things that the best game companies hold up as their credo, which means you have to focus on speed and agility.  Try that crazy new control scheme, add a strategy component to your FPS, see what all the goats look like with hats, or whatever the team comes up with.  This behavior does not encourage proper architecture, and often involves what a programmer calls “a hack”.

BUUUUUT game making also is a business, and there is always pressure to move forward because the last problem is in the rear-view mirror…  This comes from folks like producers and publishers, but isn’t just about the folks in ties and suits:  a lot of people on the team can get antsy if they don’t see new things on a weekly basis, because morale is everything in a creative endeavor.  Programmers get tremendous pressure to move on to the next big issue, and frequently they will warn the powers that be of the technical debt that is being accrued.

Of course, when the day comes that the debt must be paid off, it will involve days and days (sometimes weeks!) of time when nothing changes… in fact, the goal of this cleanup is that everything should work identically as when you started.  It’s very hard for an outsider to understand…  One day long ago I witnessed a manager straight-up ask “But can’t you just hack the entire game?”  No… not if you want something that won’t fall apart when thousands of eyeballs and eager mouse clicks are set upon it.

Nonetheless, “hack the entire game” is precisely what the 7DRL is about…  You need results now and you don’t apologize for it later.  You’ve got 168 hours to get to the finish line and you don’t care if you trample over every “Write Smarter Code” author who ever was.  And I certainly did that.

It's finally time to ditch the last of those 2D pixel art sprites...
Now I finally have time to ditch the last of those 2D pixel art sprites!

For AutoFire my control and world update system was my cross to bear…  I piled my inputs and the control of my entities in Unity’s “Update” system, where each object gets called every frame.  I cobbled together some bullshit traffic-cop system to move things in the right order, except Unity plays it pretty fast and loose…  There isn’t really a great way to guarantee that, say, the function that tells a car where to go would run before the function that actually moves it.  Frankly, I started to not fully understand how the damn thing worked at all.

I knew the debt was coming due…  Players didn’t always feel their commands were registered.  10% of the time the smooth movement of an entity would inexplicably twitch.  The enemy vehicles just spontaneously stopped working.  But I knew fixing it would be a slog, which is why I procrastinated by working on some pretty terrain last weekend instead of doing what I should have been doing.

When you have to rewrite someone else’s code, you can get pretty grumpy about that person.  But when you have to rewrite your own code, you decide that months-ago you was either an idiot or a complete dick.  “What was I thinking?” gets uttered out loud several times, as well as “What the crap is this?” and the classic “How the hell did this ever work?!?”

But a week later and all is well.  The code to control everything is about 25% of its original size.  Everything is carefully managed.  Your input is now queued up and doled out to your vehicle on demand.  Now I can get back to the fun part of making things blow up.