Bi-Weekly Update – 7/21/2019 Jul 21 - Sev
Welcome back to your regularly scheduled bi-weekly Installation 01 Update. Now you may have noticed something a little different about this week's update… that's right, it's actually on time! Oh right, and I'm writing it now, your "friendly" neighborhood Sev. I like to think it's because Bean finally realized my full potential, but in reality it's because nobody else wanted to do it. Anyways I'm not going to dwell on it too much, let's instead talk about the things that the lovely Installation 01 team has been up to.
This week I bring you a wonderful message from the one and only Brogrammer, a look at the fuel pump for one of our upcoming maps, and a little something at the end to brighten up your day. So sit back, relax, take a pause from planning the area 51 raid with the bois, and let's get into it.
Can You Boost Me?
To those loyal fans that aren’t in our Discord, what are you doing? Get in there already. To the loyal fans that ARE in our Discord that have Nitro I'm sure you’ve heard by now, because we’re a couple months late, you can now boost a server. So if you do have Nitro and haven't boosted a server yet please consider boosting the Installation 01 server so we can have one of those snazzy looking banners and more emotes of Bean’s face, because who doesn’t want that?
A Programmer's Guide to the Projectile Component System
For those of you always asking about and wanting more out of these updates, boy do I have some news for you. Unfortunately we can't always show some of our beautifully handcrafted armors or give you that piece of gameplay footage that's just enticing enough. Luckily what we can do is talk to the one and only Kendall about what it is that he does (which is almost just as good in a very subjective way). So he took the liberty, or rather we told him, to describe a little bit of what it is he's been doing for Installation 01. So instead of me blabbering on here I'll just let the man himself who actually knows what he's talking about explain...
Hello! You may have seen me before or may not have. Either way, I am GingerKendall! Usually referred to as, Kendall. A simple tag away on discord! I joined the team as a 3D artist and transitioned over to a programmer - more specifically a Brogrammer. I have been with the project for over two years now and have learned a whole lot along the way. There is a tremendous amount of talent across the entire team and I really enjoy working with everyone. However, now I get to write another little piece of the update.
What started as a testing ground for my own projects quickly expanded to something much larger. Installation 01 now uses my Projectile Component System which leverages Unity’s DOTS which allows for highly optimized and multithreaded code. The less resources allocated to projectiles means resources can be allocated somewhere else. Everything is still a work-in-progress, of course.
The ultimate goal of this ongoing endeavour is to create a system that is modular, requires minimal maintenance, performant while simultaneously being easy for designers to use. This includes creating iconic projectiles such as the needler shards, plasma pistol bolt, and even the extra-ordinary sniper rounds in less than a minute. However, it also should allow for quick prototyping of new projectile types.
How It Started
This all started in my own project where I was experimenting with Unity’s new Data Oriented Tech Stack (DOTS) and Data-Oriented-Design (DOD). It first began as just a ”make whatever I feel like” way before trying to make this projectile system but it quickly got out of hand and expanded scope. I was seeing massive performance gains on the first pass for everything. It was a really cool boost to see.
The expansion started as adding a series of components to test out the performance and DOD’s programming paradigm. I created thousands of entities with component in a scene and just let the systems take over. Not long after it became projectiles and eventually explosions.
One of the first system tests, was “this could look cool if I add thousands and they always look at my cursor.”
Then I said, “What if they shot projectiles where ever they were looking?” I, of course, then had to make an initial pass on projectiles.
The next step was, what if projectiles followed the cursor’s position?
As the images describe, the helmets look at a specific target and now the projectiles do as well. This is simply done by attaching a “Tracking” component to any entity. When done to a projectile - suddenly it turns into something very similar to the needler shards.
And that is when it became interesting to the I01 team as we have never had needler projectiles before. Then it grew to a bunch of different components that are still being added! I want this to be usable across any project - currently it is used in two, i01 and one of my own.
I want this to be a package for easy implementation across any project. Want to see the public trello with future components and systems? Well here it is! https://trello.com/b/FguxaMwc/wdibprojectiles
Due to principles of DOD and the purposeful restraints of Unity’s DOTS, it forces the user (programmer who is writing code) to do it in a very specific way. These restraints allow Unity’s underlying framework to do the heavy lifting when it comes to multi-threading to avoid issues such as race conditions, deadlocks, and other nasty situations. That comes in the form of Unity’s Jobs System. However, there is another key component to making it all come together and be performant, Unity’s Burst compiler.
The Burst Compiler takes these Jobs and hyper-optimizes (compiles) the code at the assembly level. This vastly increases performance just by adding the [BurstCompile] attribute to the job. Of course, it has its restraints such as not being able to use managed memory, only certain types, and some other caveats. However, the performance gain is huge compared to any of the restrictions. It works so nicely with the Entity-Component-System (ECS) paradigm.
ECS… The basic breakdown is that there is an E for entity which is an object with an ID. The entity has data on it called Components. The C means components… Components is just more data, they do not actually contain any logic themselves, just variables and stuff. Example: the projectiles have components for damage, movement speed, and much more! These components are reusable though, so the damage or movement speed can be used on any entity. Just attach them! But they won’t do anything, they are just data. We need something to manipulate the data… its time for the ‘S’!.
S for systems in ECS are where the behavioral aspects of the game are defined. The actual logic. Let’s say we have an entity with a movement component and speed component. The system gathers all the entities with at least these two components and it does this calculation to move the entity: (forward direction * speed * deltaTime). All those entities now move forward if those two components are associated with our entity, keep in mind that it can have any other components too but our MovementSystem only cares about these two specific components.
Add a “Tracking” component and now it automatically makes the entity face a target in a different system - which doesn’t care about the movement system. But when the two systems do their own logic, it combines to this effect. The needler following effect.
That should be good enough for now, I recommend looking into Unity’s DOTS if you find the time and are interested!
The implementation actually looks pretty simple from the editor. We have all our projectiles, explosions, and weapons data located in very specific places which designers can directly read, create, or delete. I had to make quite a few underlying changes to how we actually handled our saved projectile data but from the designers perspective it changed very little. Instead of “CanHeadshot”, “CanExplode”, and booleans with if checks, it simply became adding components you want to a list. It allows designers to simply pick their components, set their values and thats all. On the surface.
Under the surface, the projectile and explosives work the same way. You take this data from the designers and in realtime create a corresponding archetype. Then it is passed to an appropriate factory which creates the new entity with all the correct components and data. That sounds simple and straightforward. As it should.
However, that is just creating the entity and its components. Which is all data, and data is not useful without context. Systems create context. An example is the HitSystem and MovementSystem. The HitSystem takes all entities with at least the “Translation” (position) and “PreviousTranslation” (position last frame) components and does a raycast between the PreviousTranslation and the current Translation to see if we hit anything. If this entity does not have the components that the MovementSystem requires to move entities… The raycast will always be in the same spot because those two translations would always be the same. By simply adding the required components to the entity for both systems, it just works.
Behavior is exclusive to systems, but components aren’t exclusive to one system.
Adding the actual tracer round was done after our recent stream. Super simple but vital.
By writing separate systems for almost every component, it removes the issues of large classes and makes it much easier to debug what a specific system is supposed to do. It allows for defining singular behavior per component using a system. This behaviors when combined can create interesting gameplay. There is a lot planned. Example time though!
Now when they are combined:
These projectiles have a few different components: Explosive, MultiHit, ProjectileCount. They are separate systems all acting alone but combine to make something awesome. And it takes the designer 30 seconds to make! Plus, they are tweakable in runtime so it has super quick iteration time.
Add some cool visuals from Greg and boom!
I do want to say while it is cool to make things that are fun, they need to be performant. Get ready to hear that word a few more times, might as well cache it.
Performance is a huge thing in any video game. Some components have a bigger impact than others. The most impactful components are multi-hit and explosion component. They both require looking for multiple hits per frame rather than a single hit. Batching these hits is the best way to get more performance but it decreases code readability while increasing code complexity. But that is expected, lets dive into the components and why they are more performance intensive.
The Multi-hit component is needed for weapons like the sniper. It needs to have the ability to hit and pierce multiple players in a single frame. While not super expensive, it still has a larger impact than regular projectiles. However, explosions do something different.
Explosions have multiple steps. First step, gather all objects within the radius it can hit. It needs to gather every object, players or physics objects. Second step, it needs to filter out the objects that were gathered. It needs to raycast to each object and make sure there is not something in the way, such as a wall in between the object and the epicenter. Step three, is to process the final hits. This means applying damage and/or physics impulses to the objects. These steps each add complexity and performance hits. However, further optimizations have yielded good results.
In editor, which has lots of overhead, I was running at 33.33 ms (30 FPS for bk’s) with 36,000 projectiles on screen. My specs are GTX 1060 and i5-6500. I should do some proper testing in a build but this gets my point across nicely. I can’t think of any situation where there are over a 1,000 projectiles on screen at once. That doesn’t mean optimizing isn’t important, it is always.
The more performant the Projectile-Component- System (PCS) is, the more allocation of resources other game systems (rendering, network, etc) can use. This could range from visuals to other cool heavy computational systems. Either way, the less the PCS uses resources - the better!
If you have made it this far or just looked at all the pictures - thanks! I appreciate you taking time out of your day to read this. If you have more questions, feel free to ping me in the Installation 01 public discord. Maybe if you want to see a gif of something, let me know. Maybe even suggest some new projectile components!
Also make sure to leave some feedback about what you think about this type of content in updates. Deeper dives into what goes on behind the scenes. We have a lot of talented people on the team that can write about what they do. We are constantly learning and evolving our art and codebase. Want to see something specific to development? Make sure to mention it in the #i01_discussion chat on Discord!
Well that was a lot of technical speak. I hope you guys understood and absorbed all this knowledge that Kendall just bestowed upon you, so maybe you too can become a game developer one day. Afterall, it’s not everyday you get to hear from the Brogrammer himself.
Fuel For the Fire
Hey, remember that sneak peek at the map "Goliath" we gave you back in the update from October 21, 2018? Well I don't blame you because it was just a cluster of shapes missing their textures arranged into map form, however now thanks to the wonderful work of our 3d artist TheoryBox and texture artist Jibrail, we can have a cluster of shapes missing their textures arranged in a map form with a fuel pump on it.
Of course keeping it true to the Halo style, our vehicles won't be guzzling gas like those tanks that totally 100% weren't there in Tiananmen Square in 1989, so you won't be able to pull over and actually interact with said pump. What you can do though is admire the beautiful machine from the window as you commit vehicular manslaughter. Additionally you can admire it from close up while committing regular manslaughter, just watch the blood, don't want it getting dirty.
I’m a fan of the way the hose looks while coiled up, the weathered look on the metal is a nice touch as well. So when you finally are able to get your hands on the game Soon™, as you load into Goliath, and you see this beautiful mechanism in the corner of your eye just take a moment to appreciate the work that went into it.
Sharing Is Caring
Do you ever just lay in your bed at night and think “Huh, I really haven’t done anything for my community lately and all my good karma is running out”? And do you also just happen to have a very specific skill set that can be used in the world of game development? Well then you’ve come to the right place, we’re currently looking for new members to apply to our development team.
Just click that button below, and apply for the position that fits you best.
It seems as though Bean has left for another adventure, this time with a mysterious companion in the back. Of course no matter where Bean goes, the glorious beams of light will land upon him like a beacon of hope increasing his already great complexion even more. Well wherever he’s going I just hope he doesn't take all the Sun with him, we need that to sustain a healthy ecosystem.
That’s all we have for you this week. I’m hoping you enjoyed the first update written by yours truly. If you didn’t that’s unfortunate, but you should be used to disappointment at this stage. You can send me a well written complaint letter by carrier pigeon if you really feel the need, and I'll make sure to get back to you in 3-4 business years.