Just so you know, this is not a tutorial series! I am writing this series mainly to give you a behind the scenes look at the process of making a game in Unity, and to document the development of this project.
Since the last progress update, I added a cannon model, drastically decreased CPU usage, and upgraded to BepuPhysics v2, which recently came out of beta. I had to put off cannon functionality to implement the faster physics library, but that’s next on the list now.
I started off today by trying to find a way to have my water receive shadows. Annoyingly, after some research, I found out that there’s some difficulties that arise when trying to make transparent objects cast and receive shadows. I did read that apparently it’s relatively easy to have them do one or the other, just not both. Since I don’t need the ocean to cast shadows, that’s not an issue, but so far I haven’t found a way of making it work.
Today I created models for cannons and cannonballs. This took quite a bit longer than I would have liked, but I’m satisfied with the result.
Today I added GPU instancing support with per-object colors. This will improve rendering efficiency, and it also makes the project files much cleaner. Essentially, I’m now able to have very few materials (at the moment I only have three) while still having as much color variation as I want between objects.
Since this allows me to individually modify object colors, it also lays the groundwork for ship customization in the future.
Today I moved the per object coloration code into one script. Now all the ship’s color settings are in one place, making it much easier to modify. Afterwards, I continued looking for an answer to my water shader problem. As I mentioned on Monday, transparent objects have a hard time receiving shadows. Since shaders are already a bit of a dark spot on the internet (in terms of resources available), it’s really difficult to make progress.
Eventually I did figure out a way of making it work on my test shader, but it only works 100% properly in the scene view. In the game view, the water plane just disappears—unless I switch the camera’s rendering mode to deferred, at which point the plane is visible, but it flickers.
I’ll have to re-implement support for deferred rendering in my shader in hopes that that solves the flickering.
When I turned on my computer this afternoon, I found out that I had apparently forgotten to upload the progress I made at school yesterday to Unity Collab. That means I’ll be limited in what I can work on this weekend without causing file merge conflicts.
I decided to try and get shadows on my water (again), but I’ve come to the conclusion that it isn’t possible. At least not without giving up transparency. Casting shadows onto the water also seems to interfere with the nice foam effect I’ve got around its edges. I’ll probably have to find some sort of workaround to fake the transparency.
As it was Easter Sunday today, I decided to take a week off from writing blog posts. With the little bit of time I did have to work on the game, I starting building a component system. It’ll be similar to Unity’s but likely more specific to the needs of what I’m working on. I could probably get away without one, but one of my goals for this project is to keep my code as clean, readable, and reusable as possible, and a component system will help to do that.
I spent most of today working on the component system, and I managed to get the core structure in place. However it still needs a bit of work before I can thoroughly test it and integrate it with my existing code.
Today I did some light testing with the component system and fixed a few minor issues.
Afterwards, I took a look at the server’s CPU usage. It’s been at about 50% (with no players connected) for pretty much as long as I’ve been working on this project, but I never bothered to investigate. The strangest part is that the usage doesn’t appear to change when players connect. This suggests that a console application doing nothing but running a basic physics simulation uses half of my processing power—which is totally absurd.
Luckily, I got some pointers on discord (thanks Dave!) about what might be causing the issue. It turns out that the way I was running my game loop is an absolute disaster. Instead of sleeping the thread in between ticks, I was letting it sit there without anything to do. Although it would only ever “idle” for 0.033 seconds at a time, this behavior apparently destroys performance. After modifying the code to make the thread sleep until the next tick, CPU usage is down to below 1% (with no players connected).
Today I fixed a few collider issues while integrating my component system with my existing code. I also found out that BepuPhysics v2 came out of beta a few days ago. I’ve decided to upgrade from v1 before I get any more invested, so I may not get around to making cannons functional until next week.
Today I finally finished swapping physics libraries. It took a lot longer than I had hoped, due to the fact that BepuPhysics v2 is a complete rewrite of v1 (meaning almost everything is set up differently). I still have a few issues to sort out, and I need to test it properly to make sure it works as intended, but the bulk of the integration is done now.
I’ll start off the coming two weeks by making sure all the physics stuff works properly. After that I intend to finally make cannons functional. Assuming I manage to accomplish that relatively quickly, I’ll look into ladders and probably make a lot of miscellaneous changes and additions.