crogine: cross-platform mobile oriented game framework

After I wrapped up DoodleBob at the beginning of the year, I wanted to find a project which would push me to learn something new. A few people pointed out to me that Bob would be a great little time waster if it were available on mobile devices. Unfortunately xygine, as it is SFML based, won't run on anything outside of desktop systems. As great as I think SFML is its mobile support, to put it bluntly, is a bit pants. So, then, a chance to not only learn mobile development but some SDL2 too! Thus, the concept of crogine (the CROss-platform enGINE) was born.

In previous posts I've commented on some of the development issues when creating crogine (and the games which are powered by it), including an explanation of how I set up Android building in Visual Studio. Here, then, I shall only summarise the overall structure of crogine.

The Framework
Most importantly I wanted to make sure I used what I had learned when writing xygine and improve on it where I could. The base App class and state stack mechanism remain more or less unchanged, as does the Event and Message systems. Starting a new project using the framework should not only be relatively quick and easy, but also familiar, and what I had with xygine worked well. I also wanted to make sure the interfaces to the core classes were familiar too, so it's possible to see a strong SFML influence on the class names and members therein. It meant reinventing many of the OpenGL classes such as textures and shaders, but the learning and insight proved highly valuable.
    xygine's biggest fault, in my opinion, was the poorly designed ECS, which, at the time, was heavily influenced by the use of Unity. It was pretty inflexible, required a lot of boiler plate every time a new component was created and, er, didn't really have any systems as such. This is the biggest change in crogine (and what crogine has taught me will, undoubtedly, find its way back into xygine) where, thanks to some research and invaluable suggestions by people over at #sfml, the ECS is completely new, and takes a cleaner, data oriented approach. Now components are more or less pure data, small structs where possible, with accessors in classes only where I feel it makes sense. Processing the components is moved out into corresponding systems, which not only makes for much neater code, but far better data locality, in turn providing much better performance, essential on mobile platforms.
     Splitting the systems from the components also means that the ECS is far more modular, systems such as the 3D renderer can be easily implemented more than once, for example a GLES2 renderer for mobile, and an OpenGL 4.x renderer for more powerful desktop systems. Either one of these can be instantiated at runtime with absolutely no change to any of the required components, meaning that a single game in development can target multiple systems while still taking advantage of specific hardware. Audio systems can be swapped in and out too, favouring either OpenAL or SDL_mixer - and, with an open interface, custom audio renderers could be written should the need arise.

    I have introduced the concept of 'directors', classes which sit within a scene, but only observe it through events and messages. The directors can, when needed, then send commands to select groups of entities through the Command system. Following a data-driven approach, crogine loads assets such as particle systems, sprites and models via external configuration files. This allows definitions for materials, textures and meshes to be easily updated in a text editor, without having to recompile any software.

Multi Dimensional
Writing a framework from the ground up was also the perfect opportunity to properly develop complimentary 2D and 3D rendering systems. In xygine I created a 3D rendering system which sat on top of SFML in a wobbly kind of way - so much so that due to compatibilty issues with MacOS the 3D renderer only ran on Windows and linux. Here, in crogine, the Scene class has been written in such a way that simply replacing the projection of the active camera switches the output between 2D and 3D. Multiple scenes can run alongside each other happily, so a single scene can be dedicated to the 3D rendering of the game world, while a second scene, using an orthographic projection, renders a HUD and menus over the top. This also brings the full flexibility of the ECS for rich and complex scenes to the UI. xygine's dedicated UI classes are nowhere to be found, as everything is now entity based. This can be used to create some cool effects such as 3D menus, and HUDs which interact directly with the game world. With all this in mind it is likely that future revisions of xygine will drop 3D in favour of returning to its 'xy' roots, and leave the 3D game development to crogine.

Nobody, and nothing is perfect. While I'm pleased with much of what I have, particularly mobile performance which, quite frankly, surprised me, the API is a little uneven. When I started I had a pure data oriented ECS in mind, and those early components such as meshes, models and shaders all have very public data members. As development went on I decided I still preferred a more encapsulated interface afforded by OOP, so I tried to blend the two where I could. Components are still very much pure data, but the public interface has tigher control over its access.The latter has worked out OK, but has left some of the earlier code in need of refactoring. crogine is still very much in development in some places too, with incomplete function definitions here and there, and rogue comments which weren't updated with subsequent refactorings, making them occasionaly vague and misleading. The main driving force behind development has been the creation of two games, one of which is (yet another) remake of Threat Level. Because of this the development of crogine is led very much by the needs of the game in its current state. Compared to xygine there is also little documentation outside of the included doxy comments.

Future additions
While crogine is already in good shape the underlying SDL library provides a few more interesting features which I'd like to eventually experiment with. One of those is haptics, force feedback via controllers, and the vibration function on many mobile devices. I'd also like to improve the network support, preliminary connections are provided by enet, but multiplayer games are something I'd really like to develop down the line. As previously mentioned I also want to take what I've learned of ECS development and move it back into xygine via its own development branch. I also plan to fill the crogine wiki with as much documentation as I can... before I forget how it all works ;)
    Plenty to keep me busy then and, I suspect, away from any reasonable blog posting in the near future. To fill some of that gap here's a video of crogine in action, demonstrating the current state of Threat Level:

crogine is open source, as is Threat Level, the sources for which you can find over at github.


Popular Posts