Unity Ashteroids – Ash Game Framework in Unity

Unity Ashteroids – Ash Game Framework in Unity

I decided to take a break from the game development today to scratch an itch I had had for a while.

Its no secret that im a fan of Entity-Component systems having used various flavours of them for years. My particular favourite however is found in Richard Lord’s Ash Framework. I have used it on numerous projects including my 3-game prototype challenge.

Ash Framework however is written for the Flash platform. Though there are ports for other platforms, no one has yet done one for Unity. It gets talked about on the Ash mailing list every now and then but often dismissed as either impossible or pointless as Unity already has an Entity framework built into it.

Well after a recent discussion I decided I wanted to have a go at it anyway. It turns out its actually not that hard to implement.

Starting off with David Arno’s .Net port of Ash I wrote two small classes that wrap the Ash Engine and Ash Entity.

Ash Entity is the key piece to the puzzle. You add it as a component to your game object:

screenshot_003

It then checks to see which Unity components have been added or removed each frame and updates the Ash Entity reference. Its simple but it works! It even includes the default Unity Components so that means you don’t need a base “AshComponent”.

The AshEngine serves as the root of the hierarchy. So long as you place entities below it they will be able to find the engine. This makes it really easy and convenient to create scenes at design time and have them work when you hit play:

screenshot_005

From that simple foundation I decided to have a go at porting the entire of Richard’s Asteroids example over to Unity. I was surprised at how little issues I ran into. You can give it a play here:

http://mikecann.co.uk/projects/UnityAshteroids/UnityAshteroids.html
Use arrow keys to move and space to shoot.

It all works surprisingly well. The code is really clean and very simmilar to the original.

The only changes I needed to make from the .Net port was to change some “internals” to “public” and changed the type of the update variable from double to float as Unity uses floats for everything not doubles.

Instead of manually defining the components in “EntityCreator” I use Unity’s prefab system which makes it really nice and easy to edit properties in the inspector in the editor:

screenshot_004

Then load them the usual Unity way using Resources.Load().

Systems are just pure code and added to the Engine as usual:

public class Asteroids : AshGame
{
	private EntityCreator creator;
	private GameConfig config;

	void Awake()
	{
		creator = new EntityCreator(this);
		config = new GameConfig();

		var size = Camera.main.ScreenToWorldPoint(new Vector2(Screen.width, Screen.height));
		config.Bounds = new Bounds(Vector3.zero, new Vector3(size.x*2, size.y*2));

		Engine.AddSystem(new WaitForStartSystem(creator), SystemPriorities.PreUpdate);
		Engine.AddSystem(new GameManagerSystem(creator, config), SystemPriorities.PreUpdate);
		Engine.AddSystem(new MotionControlSystem(), SystemPriorities.Update);
		Engine.AddSystem(new GunControlSystem(creator), SystemPriorities.Update);
		Engine.AddSystem(new BulletAgeSystem(creator), SystemPriorities.Update);
		Engine.AddSystem(new DeathThroesSystem(creator), SystemPriorities.Update);
		Engine.AddSystem(new MovementSystem(config), SystemPriorities.Move);
		Engine.AddSystem(new CollisionSystem(creator), SystemPriorities.ResolveCollisions);
		Engine.AddSystem(new HudSystem(), SystemPriorities.Animate);
		Engine.AddSystem(new AudioSystem(), SystemPriorities.Render);   
		
		creator.CreateWaitForClick();
		creator.CreateGame();
	}
}  

The changes to the Asteroids code in general are minimal. I use Unity’s components wherever possible, so things like Position and Movement become Transform and Rigidbody2D. Rendering is taken care of by Unity so I didn’t need any RenderingSystem or Display component.

The code is available on GitHub for your perusal: https://github.com/mikecann/UnityAshteroids

I was actually surprised I was able to get this all working without any problems. There are improvements that could be made:

Performance of AshEntity

AshEntity is the core to the whole thing and unfortunately it probably isn’t the most performant. For each entity in the game it checks every frame to see if any components were added or removed. It doesn’t do this in the best possible way so there is definitely room to improve this.

Sugar

There is plenty of room for syntax sugar thanks to the superior C# language over Actionscript 3. NodeList could be made generic and a generic ListIteratingSystem could be developed and perhaps even a way of eliminating nodes altogether. Also retrieving components from Ash Entity could be made simpler by removing the need to pass in the type param when calling Entity.Get<>().

Finite State Machines

As the .Net port does not include Richard’s FSM code I worked around the problem by destroying and creating new prefabs. This works quite well as it allows you to use the inspector to visually design the prefabs however a nice addition would be some editor tools and code for FSMs in Unity.

Unit Tests

I copied over the .Net tests from David’s port and got them running in unity using Unity Test tools without any problems however my Ash Unity code isn’t tested. There isn’t much of it but it probably should be covered.

Mr Nibbles 3D – Menus & Obscuring

Mr Nibbles 3D – Menus & Obscuring

While experimenting around with rotating in more than just one axis I ran into an issue. When rotating you can obscure the camera with the level. It would be possible to construct levels such that they can’t be rotate into a position that anything would be obscured but it would severely restrict the number and type of levels I could build.

screenshot_002

The solution to this problem was to shoot a ray (well, several rays) from the player to the camera, if they collide with anything then its obscuring and thus I fade it out. When its no longer obscuring I fade it back in again. It works pretty well as a solution though I will need to see how it actually works out when I build more levels.

I have also been thinking about the menus in the game. I was wonder if there was a way to make the menus more interesting. Then I had the idea, why not make the menus a level? That way I could introduce the basic controls at the same time!

Each section of the menus are navigable by jumping into the portal which loads the next menu section. Obviously this wont work for menus that need sliders and checkboxes like the options screen, in those cases ill just pop up a regular menu. What do you think? Is it a good idea or will it get annoying?

Mr Nibbles 3D – Level Building

As this is a level based puzzle game one of the big requirements for the project will be the ability to quickly build and test levels. In the original Mr Nibbles the levels were all 2D generated from a bitmap image where each pixel represents a single tile in the world. So for example here is level 4:

lev

Representing the levels as a bitmap image meant that Photoshop became my level editor which allowed me to very quickly make changes and test the levels as I made them.

Obviously that scheme wont work for 3D so I started thinking about how to build levels in the editor. If you have used Unity before you will know that in addition to the actual editor they run a website called the Asset Store where users can submit tools and assets that others can use in their project. It was on there that I came across the Tidy Tile Mapper:

It looked exactly what I wanted. So I bought it and started using it to build the first few levels you see in the video at the start of this post. It was while I was using it that I discovered problems in the way it works.

Firstly its slow to use both from a performance perspective and from a usability perspective. There aren’t any hot keys for commonly used things and painting and removing blocks just chugs after a while. I also don’t like the way the tool handles “empty” blocks which are infact real object that clutter up the hierarchy. The block editor also doesn’t seem to handle some rotations. The way it handles layers is awkward and will be a pain for this game that will require many layers or axis’ of movement.

In short I decided I could do better:

Its only a few hours work at this point and doesn’t have all the features of the Tidy Tile Mapper but it has enough for me to get building my levels quickly. It works by having a “working axis” that you can paint blocks to or remove blocks from. All blocks are added as a child of a “blockmap” which efficiently stores the blocks in dictionaries for very fast lookups.

You can alter the “layer” in the working axis using the mousewheel. The on-screen rotation controls allow you to move around the level in 90 degree jumps. This is extremely handy for Mr Nibbles as trying to build the levels while maintaining the current rotation of mr nibbles as the player plays the level in my head was causing headaches!

I plan to iterate and develop it during the project. If its good enough I may release it on the Asset Store so others can benefit from my work on the tool.