Developer’s Update #5
It’s been a month since last post, so I guess it’s time for some news on how work is progressing. If I haven’t posted much info lately, it’s because I have been rewriting and refactoring an important part of the codebase, and while that’s very important work for the continuation of the project, there’s not much to show unfortunately. But here’s a quick summary of why this is happening, for those readers who are interested in the more technical problems of game development behind the scenes.
Of course, getting back to programming DarkDale after a few months spent on the One Room Round Robin 2 mod for Legend of Grimrock, I was bound to find incoherencies here and there in the code, and clean things up a bit. But what’s going on is actually a bit more major. It all started when I sat down to consider how to implement saving and loading, or in programming terminology, “serialization”. In the case of DarkDale, it meant not only implementing save and load functions for the player, but also internally, as the game world will be divided in “scenes” that can be modularly constructed and added/removed. A modder for example could build a dark tower “scene”, sort of a self-contained dungeon, and just plug it in on top of the regular campaign. This modular approach will also give great flexibility to the development of the game itself. Not all scenes will be loaded at the same time however, so the engine must be able to instantly save/load scene states, for example when you exit a city scene and move onwards to the wilderness adjacent scene.
Thinking about how to save data meant thinking about how the data is structured. Then, reading a bit more on the subject of data management in Entity-Component-System (ECS) frameworks, I realized… that my implementation was not ideal, and it was Unity3D’s fault.
How? Well, Unity itself has a system which revolves around game objects to which are attached components which add functionality. But these components are not pure data objects, but somehow hybrid structures incorporating data and logic. While there’s not “right” or “wrong” way to things, certain are less flexible than others… I worked on extending the Unity model, taking Unity’s gameObject as the base for the entities that populate the dungeon, and building my components based on the model used by Unity’s components. That let me to many complications trying to bridge the gap between Unity’s system and how I wanted my game architecture designed. For example, Unity’s gameObjects must imperatively have a Transform component. I have lots of cases where I don’t need this for my entities, for example if it’s an item placed in the inventory, or if you’re in the dungeon editor, where a door is just an icon and not a full 3D textured object. Not to mention that Unity’s gameObjects come with a ton of methods and functions and data I don’t need, and which just slowed things down, especially as I procedurally build levels out of Lua files, not with the Unity editor.
So… I sat down and started re-implementing things right. I downloaded the open-source ECS framework Artemis, a lightweight and high-performance system, and adapted it to the game’s needs. All the logic now happens internally with custom objects, and Unity now serves mostly as an engine that takes care of rendering, physics, audio, input, user interface and other hardware-oriented functions. Once I finish rewriting the code, the data, logic and audio/visual parts of the game will be clearly separated and continuing development will be much easier.
Lua is great, but integrating it within a .NET environment is a bit of a voodoo exercise. There are many competing solutions available, many deriving from Luainterface, such as KopiLua, KeraLua, NLua… and then there’s DynamicLua, AluminiumLua, Eluant, Unilua… The list goes on, some are compatible with Unity’s .NET support and some are not, and for the aspiring developer, documentation is scarce, so you’re mostly left to studying it yourself and use trial and error. Happily, decoupling my internal game logic architecture from Unity’s one allowed me to devise a much better integration with Lua, solving a lot of problems that were bugging me. So instead of trying to create a bridge like this: Lua <-> A Unity/Custom ECS hybrid, I now have this: Lua <-> Custom ECS <-> Unity, where it’s much easier to control what scripts have access to and how they control it. So good news, which will make both modding and development cleaner.
All this sounds like Unity is working against me rather than with me, and I may sound as if I disliked it. Well.. nothing is perfect, and every game engine will have problems. Without the infrastucture provided by Unity and the expertise available on its forums and wonderful Asset Store, building a game such as this one would be impossible for an indie developer. So I’m not regretting my choice of platform – you just have to learn how to play around the limitations for each particular project. In maybe a week or two, the whole refactoring will be complete and save/load capabilities will be added. With this done, I hope that the core game architecture will be mostly done, and I’ll be able to move forward with content creation. Meanwhile, I’ll prepare another post about the game world and background lore, so stay tuned!