Subscribe to GameFromScratch on YouTube Support GameFromScratch on Patreon
1. December 2015

 

Paradox the C# based cross platform game engine we featured a few months back, as just announced a major version release and a name change to Xenko.  First about the update:

Xenko

New Features With This Release
Users Can Now Edit Documentation!

We’re so glad to have added this feature that allows users to share information about how to best use Xenko. We know our documentation is not entirely complete yet, so we are really looking forward to hearing and sharing information through the community.

The process for adding to Xenko documentation is real simple. ‘Edit on Github’ in the top right hand corner and you will be able to edit our documentation. If the user-submitted information passes the verification process, we will add it to the documentation.

Edit documentation on GitHub

Automatic Symbols and Source Code Download

Being open source is great, but only if you can find the sources matching the binary version you are using. From now on, Xenko will download the right sources and symbols for an optimal debug and programming experience so you don’t have to worry about doing it yourself.

The process is simple. All you need to do is open Visual Studio options, go to Debugging > General, and check “Enable Source Server Support”:

Enable PDB

 

Next some news on an upcoming December release:

New Animation System

We’ve added a new animation system that allows you to animate any game property throughout the engine. Animating models is great but why limit animation only to the models? With the newest version of the engine, you will be able to animate material color, UI transparency, and generally any property of your game!

Simple, In-Game Profiler

As good as a game engine can get, at some point, you’re always going to be limited by the hardware’s performance. To help with this, we’ve added a built-in profiler so that you will easily be able to identify problems and bottlenecks in your game. Even better, you will be able to turn on the built-in profiler at any point during the process of making your game.

Debug Physics Collision Shapes At Run-Time

Debugging physics is never easy. To streamline this, you will be able to display all the physics collision shapes at any time in your game.

Built-In Scripts

Writing scripts takes time and is not necessarily accessible to everyone. To improve on this, we added some built-in scripts to the engine so that users will be able to do basic operations with ease. Things like animating the camera, displaying physics debug shapes, and adding profiling information can be done in just a few clicks.

 

Finally on the name change:

So, on to the big news! Paradox is officially changing its name to Xenko. We wanted to show our roots a bit more since we are one of the few Japanese-based gaming engines. Xenko was inspired by the Japanese word, Zenko 善光. The Japanese characters signify perfection and light. Sticking with the Xenko theme, we will strive to improve your experience with the Xenko engine (ah, feels good to say the new name).

We know this is a big change, and we truly appreciate your patience as we have been honing in on this transition. Please note that support and download access to any previous Paradox releases will end on December, 25th, 2015.

You can read the full release here.

 

Not sure what I think of the new name, but the old one was certainly confusing.  Whenever I posted Paradox related news in the past there would always be a comment or three expecting that it was Paradox Interactive releasing their game engine.  These transitions can often create a fair bit of pain, especially if they rename at the code level too.

GameDev News


18. November 2015

 

Xamarin, the popular cross platform .NET toolchain just released version4.  From the announcement:

Xamarin Platform – native, cross-platform apps

Xamarin.Forms 2.0

Since releasing Xamarin.Forms last year, we’ve been amazed at how quickly developers have adopted it, accelerating their time-to-market for cross-platform native experiences across iOS, Android, and Windows, all while sharing over 90% of their code.

Since then, we’ve more than doubled the engineering team behind Xamarin.Forms, and made major improvements along the way. Today, Xamarin.Forms 2.0 is faster, more reliable, and more functional than ever before. Highlights include support for pre-compiled screens defined in XAML for faster app loads, preview support for Universal Windows Platform apps, support for iOS 9, Android Material Design, and new gestures like pinch and pull-to-refresh.

Native Xamarin.Forms app displayed on iOS, Android, and Windows Phone devices

Visual Studio and iOS

We’ve rebuilt our support for developing iOS apps in Visual Studio from the ground up, and it’s smoother, easier to set up, and more reliable than ever before. Now you can develop, build, deploy and debug iOS apps entirely from within Visual Studio and communication with the Mac build host is now handled via a secure SSH connection. We now also support multiple concurrent Visual Studio instances, which is especially important if you have multiple iOS projects open at the same time. We think you’re going to love it.

Mono/.NET upgrade

In Xamarin 4, we have incorporated large portions from Microsoft’s open sourced .NET codebase into this release, increasing compatibility, performance, and reliability for all use cases.

Android and iOS Designers

We’ve made big improvements to our iOS and Android designers. The iOS designer can now load and save XIB files in addition to storyboard files, and our Android designer now supports Android Material Design. We have also improved the UI for both designers, and switched to using high-performance native design surfaces, for a smoother, faster editing experience.

Xamarin Test Cloud – automated app testing

We built Xamarin Test Cloud to allow you to easily test your app on more than 2,000 real iOS and Android devices in the cloud. With Xamarin 4, we’re making mobile testing more accessible than ever.

Introducing Xamarin Test Recorder

We’re introducing a new preview tool that makes mobile UI testing dead simple: Xamarin Test Recorder. Initially available for Mac, Xamarin Test Recorder records your interactions on iOS or Android apps, plays them back, and automatically creates test scripts that can immediately be run in Xamarin Test Cloud or imported into mobile test projects in Xamarin Studio and Visual Studio. Xamarin Test Recorder records your actions in our C#-based UITest framework so you can automatically execute them as part of your continuous integration process either locally or in the cloud. Download it now to get started.

Xamarin.UITest 1.0

Xamarin 4 includes the 1.0 release of the Xamarin.UITest C# testing framework, with new capabilities for advanced test scenarios. We’re also very happy to announce that Xamarin.UITest is now free for everyone to use, with no limits on test duration, or the use of local devices and simulators. The powerful combination and ease of use of Xamarin Test Recorder and Xamarin Test Cloud will help you immediately improve your apps.

Xamarin Insights – real-time app monitoring

General Availability

We’re proud to announce that starting today, Xamarin Insights is generally available, with free crash reporting for all Xamarin Platform customers and advanced app monitoring features for power users.

Know the Health of Your App, Know Your Users

App monitoring begins with knowing what problems your users are encountering. Is the app crashing or encountering exceptions or errors? Xamarin Insights provides automatic crash reporting and handles both managed and unmanaged mobile crashes seamlessly. You can also explicitly report errors or warnings to Xamarin Insights and track them through the its dashboard. Xamarin Insights makes it easy to rank your issues by impact, spot patterns in app and device usage, and diagnose the corresponding issues.

Xamarin Insights also helps you understand how your app is being used by tracking and timing step-by-step event data. Analyze which screens are the most popular or which actions take your users the longest. You can even see which events led up to a crash, making it easy to reproduce your issues.

You can add Xamarin Insights to your app with just a few lines of code. In Xamarin Studio, new apps immediately get the benefit of Xamarin Insights with templates that utilize the SDK from the very beginning of a mobile project. And your IDE will automatically upload dSYM files for you so that you get symbolicated stack traces with line numbers.

Visit our docs to get started.

End-to-End for Everyone

We think it’s important that every developer be able to benefit from the full range of what Xamarin 4 can do, which is why we’re excited to announce that as a part of their existing subscription, every active Xamarin subscriber will receive:

  • Crash and error reporting from Xamarin Insights with 30 day data retention and detailed issue reports that include step-by-step pre-crash events and crashed-user identification.
  • 60 Xamarin Test Cloud device minutes per month, with access to every single one of the devices in our growing test lab.
  • Complete access to Xamarin.UITest, including tests of unlimited duration running on simulator or device.
  • A 30-day trial pass to Xamarin University, including access to guest lectures and our introductory courses.
Paid Plans

As your business grows and your apps progress, you can buy paid plans of Xamarin Insights and Xamarin Test Cloud that suit your needs.

For companies who want to ramp up their mobile testing, we’re happy to introduce affordable Xamarin Test Cloud pricing plans starting at $99/month (billed annually). If you want to go further with app monitoring, we also provide scalable Xamarin Insights paid plans.

Xamarin Ultimate

Finally, for companies who want a complete end-to-end solution, we’re introducing a new offering called Xamarin Ultimate, which includes full access to all the features of Xamarin Platform, Test Cloud, Insights, and University for your entire team in a complete package at a great price. If you’re interested in learning more about this, please get in touch with our sales team at [email protected].

 

No news yet on the more indie friendly licensing, which hopefully comes soon.

GameDev News


3. November 2015

 

In today’s Closer Look we are looking at the open source C# based 2D game engine Duality.  The Closer Look series is a combination of review and getting started tutorial that is aimed at helping a developer decide if a game engine is the right choice for them.

 

There is also an HD video version of this guide available here.

 

First I need to start with a confession.  A few people mentioned Duality to me in the past and each time I dismissed it, very quickly.  An open source C# based, non-cross platform Unity-wannabe developed by a single guy?  Yeah right… pass.  These types of projects are a dime a dozen until people quickly realized that developing a product like Unity is actually a hell of a lot harder then they thought, even if they just focused on 2D.

 

Well, let me just start by saying I was wrong… very wrong.  A bit of a spoiler alert, but Duality impressed the hell out of me and I think it will impress the hell out of you.  There is one thing to be aware of right up front from that previous paragraph… “non-cross platform”.  Right up front this is the biggest flaw of Duality so no sense wasting a ton of time if this is a deal breaker.  That said, it’s not the huge problem it used to be as there has been a lot of work underway to make Duality cross platform.  It’s built on top of OpenGL and the entire core as well as all class libraries are now portable class libraries.  In theory this means, aside from the editor which is tied to WinForms, a duality project should be able to run on any modern C# capable platform with OpenGL support.

 

Getting Started

 

Getting started with Duality is easy but may add some complications for integrating with source control, updating or collaborating with others.  The duality download is the engine, and the tools AND your game.  When you spawn a new project in Duality, it downloads and sets up another Duality environment.  You can download the latest version right here. (That’s a direct link by the way).

 

The download is simply a zipped folder.  Extract it somewhere, it’s contents should look something like this:

image

 

Simply double click DualityEditor.exe to get started.  After launching and agreeing to the MIT license, you will be greeted by this window:

image

 

Dont worry, it should only take a few seconds depending on your internet speed.  A full install currently weighs in at around 120mb.  Once done downloading the editor Dualitor should now be loaded:

image

 

I suppose this is a good time to point out that you need to have Visual Studio 2013 or newer installed and with patches applied.

 

The Editor

 

The editor is extremely straight forward, let’s do a quick guided tour of it’s features.  It should be noted, the entire editor can be docked/undocked, hidden or shown as desired, so the layout is completely up to you.

 

Editor View

image

 

You can have multiple instances of the scene view running and you switch between them using the tabs at the top:

image

 

You can also rearrange the views however you wish, such as:

image

 

In addition to the Scene Editor where you compose the entities that make up your scene, there are two other options available in this view:

image

Game View and RigidBody Editor.  The game view is like a running preview of your game, while RigidBody editor is for defining physics shapes, which we will see later on.

 

Scene View

This is your game’s scene graph.  This is where you can select the entitles that make up your scene as well as the components that compose them.  Additionally you can create new entities or add new components here.

image

We will cover this process in a bit more detail later on.

 

Project View

The Project View is essentially the assets that compose your game, things like images, fonts, audio files, etc.

image

New assets can also be created here, using either the right click menu or via drag and drop from Explorer.  We will also cover Project View in more detail later.

 

Advisor View

Advisor view is basically a context sensitive help, like a stationary and in-depth tool tip.  As your mouse location or keyboard cursor change, the context switches and content is updated.

image

 

It’s handy while learning your way around but will probably be turned off in short order to free up screen real estate.

 

Object Inspector

The contents of this window changed based on the currently selected item.  If an entity is selected in the Scene View, the properties of all the components that make up the entity are shown, like below:

image

 

While selecting an asset will show the corresponding editor, like this one for ttf font files:

image

 

Note in this case all of the values are grayed out because I selected one of the built in non-editable assets.  Note the font preview at the top of the window… neat.

 

Finally there is the menu and toolbar across the top:

image

 

This tool bar enables you to load the source in Visual Studio ( the C# icon ), compile + run, compile + debug, or preview in the editor.

 

All told, a streamlined and somewhat minimal but highly configurable editing environment.  I never once experienced a crash or lock up in my time with Duality, so at least for me, stability and performance seem pretty solid.

 

Creating a Game

 

So that’s the editor covered, let’s take a look at using it to actually create a game.  You may have guessed at this point that Duality uses a component based design.  The entities that make up your scene are in turn composed of components that provide that functionality.  The top level entity is called a Game Object and you can create one in the Scene View by right clicking and selecting New->GameObject.

 

image

 

The other options simply create a pre-populated GameObject for you.  Your newly created entity will now be available (and re-nameable) in the Scene View:

image

 

Now let’s right click our game object and add some components to it.  We want to be able to position our object in the world, so let’s first add a transform component.  Simply select New->Transform.

image

 

Let’s make this a sprite, right click again, then select new->Graphics->SpriteRenderer.

image

 

Your entity should now look like:

image

 

Plus if you look over at the editor window, you will see a sprite now appears using the default sprite:

image

 

While in the object inspector you can now edit the two components attached to our object:

image

 

You can also edit the translation, rotation and scale of the sprite in the editor view using one of the cleanest 2D widgets I’ve yet experienced:

movewidget

 

Now let’s add our own sprite, simply drag and drop from Explorer to the Project view, like so:

DragDrop

 

Now if you select the newly created pixmap, you will see it’s settings in the Inspector window:

image

 

Notice like fonts there is a preview of the asset file.  Now we can update our SpriteRenderer’s SharedMaterial property by dragging our new asset over, like so:

ChangeTexture

You will notice that Duality automatically created two new assets, a Material and Texture definition.  You can go a great deal deeper if you wish, for example changing the draw technique that is used to renderer the material to screen, which in turn you can drill down and define your own vertex and fragment shaders, etc.  The details are nicely hidden away from you, but if you want to drop down into the technical details you easily can.  That is beyond what we are going to cover today however.

 

Now we have created a sprite game object that can be positioned in the scene, now let’s go ahead and make it do something.  Let’s add a physics RigidBody component to it by selecting New->Physics->RigidBody:

image

 

As you can see in Inspector, once the rigid body is added, there are a number of values you can configure in the component:

image

 

In this case however we are going to stick to the defaults.  You can also edit the physics bounding shape if desired.  With the game object selected, in the editor view switch to RigidBody Editor, and you can now define a new rigid body shape.

rigidBody

 

Notice will editing the rigid body, the Inspector window has yet a different set of options available:

image

 

Now, lets go ahead and preview our handy work.  If you want to see a more accurate result, switch to Game View, then click the play icon:

image

 

And you should see:

Running

 

So we’ve got a physics enabled sprite being drawn with almost zero effort, pretty cool.

 

The Coding Experience

 

So, that’s the editor down.  Let’s take a look now at what the coding experience is like.  Click the C# icon to load your project in Visual Studio:

image

 

Your starting project is extremely straight forward:

image

 

Your “game” itself is actually implemented as a plugin, that is what the class CorePlugin.cs is.  The contents are incredibly sparse:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

using Duality;

namespace Duality_
{
  /// <summary>
  /// Defines a Duality core plugin.
  /// </summary>
  public class Duality_CorePlugin : CorePlugin
  {
    // Override methods here for global logic
  }
}

 

This is where the global logic and variables of your application reside.  The majority of game logic however will be in the form of components.  A default component is created, YourCustomComponentType.cs, which contains the following code:

using System;
using System.Collections.Generic;
using System.Linq;

using Duality;

namespace Duality_
{
  public class YourCustomComponentType : Component
  {
    
  }
}

 

That's about it, not a lot of boilerplate code required.  Do a compile for your project in Visual Studio.  Now if you go back to editor and add a component to a GameObject you will already see this type is available through the powers of reflection:

image

 

Now let’s add our own new Component, this one for adding WASD controls to our entity.  Simply create a new class called WASDControl.cs with the following code:

using System;
using System.Collections.Generic;
using System.Linq;

using Duality;
using Duality.Components;

namespace Duality_
{
    [RequiredComponent(typeof(Transform))]
    public class WASDControl : Component, ICmpUpdatable, ICmpInitializable
    {
        Vector2 position;

        public void OnInit(Component.InitContext context)
        {
            position = new Vector2(0, 0);
        }
        
        public void OnUpdate()
        {
            var transformComponent = this.GameObj.GetComponent<Transform>();
            position.X = 0; position.Y = 0;

            if (DualityApp.Keyboard.KeyReleased(Duality.Input.Key.W))
                position.Y -= 10f;
            if (DualityApp.Keyboard.KeyReleased(Duality.Input.Key.A))
                position.X -= 10f;
            if (DualityApp.Keyboard.KeyReleased(Duality.Input.Key.S))
                position.Y += 10f;
            if (DualityApp.Keyboard.KeyReleased(Duality.Input.Key.D))
                position.X += 10f;

            transformComponent.MoveBy(position);
        }

        public void OnShutdown(Component.ShutdownContext context)
        {
        }
    }
}

 

This example illustrates a couple of things.  First if your component requires the existence of a certain component, you can define that using the RequiredComponent attribute.  Next you can see I inherited from two additional interfaces, ICmpUpdatable and ICmpInitializable.  The first class tells Duality that your game implements Update() and should be called each frame.  The second indicates you have initialization or cleanup code and thus implement OnInit() and OnShutdown().

 

Otherwise the code is quite simple.  Your component has access to it’s parent game object in the form of GameObj and can access child components using GetComponent().  The component also has access to the engine itself through the DualityApp class, which is used in this example to poll the keyboard state.  This component can now be added in the editor to any game object that has a transform component making for easy code reuse.

 

Given the amount of space already used, I can’t go into extreme detail about what Duality can and can’t do from a programming point of view, but you can get a pretty good idea from looking at the class reference documentation.  The video version also has a bit more in depth on the coding experience if you are interested.

 

Documentation and Community

 

The primary documentation for Duality is the wiki available here.  It’s a collection of tutorials covering most of what you need to get started.  Perhaps most important piece of documentation is the reference material that is included with the engine, however I could not find an online version.  The reference material is fairly comprehensive and while a bit light in places, for the most part has what you need well documented.

Another aspect of Duality is the samples.  These can be downloaded directly within the editor via File->Manage Packages:

image

The code for these projects is also available on Github here.

The community is small but active.   The primary source of help is going to be the forum.  Fortunately it seems like the vast majority of questions receive and answer and the author seems quite active.  Of course the source is available as well.

 

Summary

 

I have to say, I love being surprised by engines and Duality certainly surprised me.  It is a very focused 2D only engine and the requirement for Windows for a development machine.  This is of course going to turn many off.  For the rest though, Duality represents a great, free, open source C# 2D engine.  It’s polished, well documented, well supported and well designed.  There's not much more you can ask for in an engine.

 

The Video

 

Programming


25. October 2015

 

In this Closer Look At we are going to be taking a closer look at the Otter2D game engine.  The Closer Look At series is a combination of an introduction, overview and getting started tutorial that is designed to help you quickly decide if a game engine/framework/library is right for you.  Otter2D is an open sourceotterlogo C# based open source game engine built over top of the SFML framework.  Otter2D provides essentially all of the functionality of SFML as well as higher level game engine features like animations, collisions, sessions and components.

 

As always there is an HD video version of this guide available here.

 

Doing what I do for a living I generally am surprised by a game engine or tool.  If I haven’t used it personally I have at least heard of it.  Otter on the other hand took me completely by surprise and for the most part it’s been a fun (and quick!) journey.  There isn’t a ton to Otter2D, it’s a code only framework built over a framework I am already familiar with.  If you have prior SFML experience, Otter2D will come quickly to you.  Due to the composition of Otter2D, this closer look is going to lean much more toward the code/tutorial side.  Let’s jump in.

 

Getting Started

 

Otter2D is available as a zip file (direct download link) or you can build from current source on Bitbucket.  The code is distributed under this license, excerpted below:

Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

In case you are wondering, there are no conditions after the colon.  So basically it’s a license that lets you do pretty much whatever you want so long as you keep the license intact.

Getting set up is easy but could be better.  Unfortunately Otter2D is not configured to be used as an external library which is a bit of an odd choice.  Instead you add the Otter2D project to your solution and link to it as a dependency in your project, like so:

image

Full instructions on getting started Visual Studio are available here.

 

Your First Application

 

Now that you’ve got Otter downloaded and configured, let’s create our first application.

using Otter;

namespace OtterScratchPad
{
    class Program
    {
        static void Main(string[] args)
        {
            Game game = new Game();
            game.Color = Color.White;

            Scene scene = new Scene();

            Entity entity1 = new Entity();
            entity1.AddGraphic(Image.CreateCircle(90,Color.Red));
            scene.Add(entity1);

            game.Start(scene);
        }
    }
}

 

When you run this example you get:

image

 

Otter2D code is very similar to a traditional Entity Component System (ECS) in it’s approach.  Game is the heart of your application, while scene represents your game world.  The scene itself is composed of entities, which in turn contain defined components like Graphic we used above, or actual components, which we will see later.  A more common approach to the above solution is to derive your game objects from Entity instead, like so:

 

using Otter;

namespace OtterScratchPad
{
    class Player : Entity
    {
        public Player(float x, float y) : base(x, y)
        {
            this.AddGraphic(Image.CreateCircle(120, Color.Red));
        }
    }


    class Program
    {
        static void Main(string[] args)
        {
            Game game = new Game();
            game.Color = Color.White;

            Scene scene = new Scene();

            Entity entity1 = new Player(0,0);
            scene.Add(entity1);

            game.Start(scene);
        }
    }
}

 

Those two examples are functionally equivalent.  As you can see in the second example when we pass coordinates to our Player Entity the origin by default is the top left corner, both of the screen as well as the sprite.  We will look at changing this shortly.  Congratulations however, you just created your first successful Otter2D application.  Easy eh?  Let’s move on and add some sophistication.

 

Input and Image Loading

 

In our next example, instead of creating a graphic procedurally, we are instead going to load a sprite.  For the source images, I am using the freely available sprites announced here.  Specifically I am using this sprite of a B17 bomber. 

 1

Obviously you can use whatever image you wish, so long as the file format is supported.  Keep in mind, Otter2D is built over SFML so it has the same graphics support as SFML which means your sprite can be in bmp, hdr, gif, jpg, png, pic, psd, tga formats.  Additionally in this example we are going to look at handling keyboard input to move our image left and right in response to key presses.  Alright, on to the code:

using Otter;

namespace OtterScratchPad
{
    class PlayerImage : Entity
    {
        public PlayerImage(float x, float y) : base(x, y)
        {
            this.AddGraphic(new Image("1.png"));
        }
        public override void Update()
        {
            if (Input.KeyDown(Key.Right))
            {
                this.X++;
            }
            if (Input.KeyDown(Key.Left))
            {
                this.X--;
            }

            base.Update();
        }
    }


    class Program
    {
        static void Main(string[] args)
        {
            Game game = new Game();
            game.Color = Color.White;

            Scene scene = new Scene();

            Entity entity1 = new PlayerImage(0,0);
            scene.Add(entity1);

            game.Start(scene);
        }
    }
}

 

And when you run it:

example1

 

Note when you launch an Otter2D application, it doesn’t have focus and thus wont receive keyboard events.  This seems to be a bug in the underlying SFML libraries.  I spent a few minutes trying to fix it and sadly couldn’t.  Shouldn’t be a big deal as a production game wont use a console window to construct the main window, so this shouldn’t occur.  As you can see from this example, loading sprites and polling input are both trivial exercises, so let’s move on to animations.

 

Sprite Animations

 

In this example I’ve taken the three different frames of the B17 bomber and created a single 3x1 768x256 using ImageMagick.  The end result was:

ss

 

Not very exciting an animation, but each frame the propeller has turned slightly.  Let’s look at the process in Otter2D of using an animated sprite from a single sheet.  In this example we also show how to move the sprites origin or pivot point to it’s middle.

using Otter;

namespace OtterScratchPad
{
    class PlayerSpriteMap : Entity
    {
        enum Animations { Idle };
        Spritemap<Animations> spriteMap = new Spritemap<Animations>("ss.png", 256, 256);

        public PlayerSpriteMap(float x, float y) : base(x, y)
        {
            this.AddGraphic(spriteMap);
            spriteMap.CenterOrigin();
            spriteMap.Add(Animations.Idle, new int[] { 0, 1, 2 }, new float[] { 9.0f, 4.0f, 10.0f });
            spriteMap.Play(Animations.Idle);
        }
        public override void Update()
        {

            if (Input.KeyDown(Key.Right))
            {
                this.X += 300f * this.Game.RealDeltaTime / 1000;
            }
            if (Input.KeyDown(Key.Left))
            {
                this.X -= 300f * this.Game.RealDeltaTime / 1000;
            }

            base.Update();
        }

    }


    class Program
    {
        static void Main(string[] args)
        {
            Game game = new Game();
            game.Color = Color.White;

            Scene scene = new Scene();

            Entity entity1 = new PlayerSpriteMap(game.HalfWidth,game.HalfHeight);
            scene.Add(entity1);

            game.Start(scene);
        }
    }
}

 

Run it and:

 

example2

 

You may have to squint to see it, but that is certainly an animated sprite.  Instead of using Image we instead use a SpriteMap which takes the individual sprite dimensions as well as the spritesheet file name in it’s constructor.  The entity is then centered with a call to CenterOrigin().  Animations is simply a user defined enum that is used as the key within the sprite map.  When the map is added we pass in an array of ints or strings representing the frames offset within the source image as well as the duration for each frame of animation.

 

Collisions

 

Next we will modify the earlier example so we now have two airplane sprites that can collide with each other.  In addition to adding two sprites to the world, the example has also been changed so you can create both a player and non-player sprite, so only one responds to keyboard input.  Additionally instead of simply moving via X++, we change it so we move at a fixed frame rate depending on the elapsed time since the last frame.

using Otter;

namespace OtterScratchPad
{
    class PlayerSpriteMapWithCollisions : Entity
    {
        enum Animations { Idle };
        Spritemap<Animations> spriteMap = new Spritemap<Animations>("ss.png", 256, 256);

        enum ColliderTypes { Planes };
        bool isPlayer;
        public PlayerSpriteMapWithCollisions(float x, float y, bool player) : base(x, y)
        {
            isPlayer = player;
            this.AddGraphic(spriteMap);
            spriteMap.CenterOrigin();
            spriteMap.Add(Animations.Idle, new int[] { 0, 1, 2 }, new float[] { 9.0f, 4.0f, 10.0f });
            spriteMap.Play(Animations.Idle);

            this.AddCollider(new BoxCollider(256, 256, ColliderTypes.Planes));
            this.Collider.CenterOrigin();
        }

        public override void Update()
        {
            if (isPlayer)
            {
                if (Input.KeyDown(Key.Right))
                {
                    this.X += 100f * this.Game.RealDeltaTime / 1000;
                }
                if (Input.KeyDown(Key.Left))
                {
                    this.X -= 100f * this.Game.RealDeltaTime / 1000;
                }

                // Check for collisions
                if (this.Collider.Overlap(X, Y, ColliderTypes.Planes))
                    this.X = 0f;
            }
            base.Update();
        }

    }


    class Program
    {
        static void Main(string[] args)
        {
            Game game = new Game();
            game.Color = Color.White;

            Scene scene = new Scene();

            Entity entity1 = new PlayerSpriteMapWithCollisions(0,game.HalfHeight,true);
            Entity entity2 = new PlayerSpriteMapWithCollisions(game.Width - 128, game.HalfHeight, false);

            scene.Add(entity1);
            scene.Add(entity2);

            game.Start(scene);
        }
    }
}

 

And run it:

example3

 

You may notice the collision isn’t amazingly accurate.  This is because in this example we used a box collider but there is some dead pixel space between our wing and the end of the image.  If you require increased accuracy you could instead us a pixel collider, but it will have a profound effect on performance.

 

Sound and Music

 

Next lets look at adding audio support to our game.  Let’s start by adding some sound effects to our player:

    class PlayerImageWithSound : Entity
    {
        // 30 cal burst:: http://www.freesound.org/people/Hamp999/sounds/151620/
        Sound sound1 = new Sound("sound1.wav");

        // Bomb drop http://www.freesound.org/people/sunch/sounds/274090/
        Sound sound2 = new Sound("sound2.wav");

        public PlayerImageWithSound(float x, float y) : base(x, y)
        {
            this.AddGraphic(new Image("1.png"));

            //Center within and without
            this.Graphic.CenterOrigin();
        }
        public override void Update()
        {
            if (Input.KeyDown(Key.Num1))
            {
                sound1.Play();
            }
            if (Input.KeyDown(Key.Num2))
            {
                sound2.Play();
            }

            base.Update();
        }
    }

 

When you hit the 1 key a certain sound effect plays, hit the 2 key a different sound effect plays.  There are two important things to note with audio in Otter2D.  Once again, it depends on SFML for the audio code so Otter supports the file formats that SFML supports ( which are too many to list ).  Additionally playing a sound halts earlier versions of that sound, so if you want multiple concurrent plays of the same sound, you need to create multiple instances.

 

Now let’s take a look at a music example.  Instead of extending another Entity, we will be creating our own Scene this time.

using Otter;

namespace OtterScratchPad
{
    class PlayerImageWithSound : Entity
    {
        // 30 cal burst:: http://www.freesound.org/people/Hamp999/sounds/151620/
        Sound sound1 = new Sound("sound1.wav");

        // Bomb drop http://www.freesound.org/people/sunch/sounds/274090/
        Sound sound2 = new Sound("sound2.wav");

        public PlayerImageWithSound(float x, float y) : base(x, y)
        {
            this.AddGraphic(new Image("1.png"));

            //Center within and without
            this.Graphic.CenterOrigin();
        }
        public override void Update()
        {
            if (Input.KeyDown(Key.Num1))
            {
                sound1.Play();
            }
            if (Input.KeyDown(Key.Num2))
            {
                sound2.Play();
            }

            base.Update();
        }
    }

    class SceneWithMusic : Scene
    {
        // Sound file is http://www.freesound.org/people/Diboz/sounds/216071/
        // Play, not looping
        public Music song = new Music("music.ogg", false);

        public SceneWithMusic() : base()
        {
            song.Play();
        }

        public override void Update()
        {
            base.Update();

            if (Input.MouseButtonPressed(MouseButton.Left))
                Music.GlobalVolume -= 0.1f;
            if (Input.MouseButtonPressed(MouseButton.Right))
                Music.GlobalVolume += 0.1f;

            if (Input.KeyPressed(Key.Space))
            {
                // Fast forward 10 seconds on spacebar if 10 seconds remain in play time
                if ((song.Offset + 10000) < song.Duration)
                    song.Offset += 10000;
            }
            if (!song.IsPlaying)
            {
                System.Console.WriteLine("Music stopped");
                Game.Close();
            }
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            Game game = new Game();
            game.Color = Color.White;

            Scene scene = new SceneWithMusic();

            Entity entity1 = new PlayerImageWithSound(0,game.HalfHeight);


            scene.Add(entity1);

            game.Start(scene);
        }
    }
}

In this example there is now music playing when you start your game and you can fast forward the song by pressing the space bar.  Additionally global (all sound effects and music ) volume can be increased and decreased using the left and right mouse button, also illustrating how easy it is to poll the mouse for input as well. 

 

Components

 

I mentioned earlier that Otter2D has component support?  Well we saw a bit of it in action with the addition of Graphic objects to our Entity.  In this case though we are going to drop in slightly more advanced components, as well as create one of our own.

    class CustomComponent : Component
    {
        public override void Update()
        {
            base.Update();
            float alpha = Entity.GetGraphic<Image>().Alpha;
            alpha -= 0.005f;
            if (alpha <= 0.0f)
                alpha = 1.0f;
            Entity.GetGraphic<Image>().Alpha = alpha;
        }
    }
    // A Player Entity with components attached
    class PlayerWithComponents : Entity
    {
        public PlayerWithComponents(float x, float y) : base(x, y)
        {
            this.AddGraphic(new Image("1.png"));

            Axis axis = Axis.CreateWASD();
            BasicMovement movement = new BasicMovement(100, 100, 20);
            movement.Axis = axis;
            AddComponents(
                axis,
                movement,
                new CustomComponent()
                );
            this.Graphic.CenterOrigin();
        }
    }

 

And when you run it:

example4

 

Here we’ve used a set of built in keys, one for applying movement to your entity.  The parameters passed in limit x and y velocity as well as the rate of acceleration.  Then we create another component that maps the WASD keys to an axis, which can be used to drive our movement component.  Finally we create a custom component that changes our alpha over time.

 

Documentation and Community

 

Otter2D’s documentation consists of a collection of examples here and a generated reference manual available here.  It’s not a huge body of work however Otter2D is extremely simple to use so doesn’t really need much more.  Additionally it is built on top of SFML, so that underlying documentation and community are also available.  That said, it is built on the C# bindings of SFML and that community is much smaller than the main SFML community.

 

In terms of community there is a small forum available here.  It’s not extremely active but it is a place to get your questions answered.  There are a handful of tutorials on the web but not a huge amount by any definition of the word.

 

Conclusion

 

Otter2D is a pretty solid 2D game engine built over top of a well established framework.  It was extremely easy to learn and use, the design is clean enough you can intuit most of the process.   On major flaw I never discussed was the support for the Ogmo level editor, which IMHO was a very bad choice.  First off, it simply doesn't work, loaded levels are mangled.  Worse though, Ogmo itself was a frustrating mess to work with… every single change to the map (adding a layer, changing size, tile format, etc. ), completely destroyed everything you had done up to that point.  Adding support for a better editor such as Tiled would be relatively short work, but this was by far the most frustrating part of working with Otter2D.

 

Otherwise it is exactly what it is.  A clean, easy to use, fairly full featured 2D C# game engine.  As it is built over SFML and in C# deploying to platforms such as Android or iOS is most likely going to be painful ( no documentation exists ) and will most certainly require a Xamarin license.  For a 2D desktop title or as a learning game engine however, Otter2D would be a very solid choice.  As odd as it sounds, Otter2D was simply fun to work with, somewhat like Love2D, especially after dealing with much more complex engines or even SFML itself.

 

The Video

Programming


23. October 2015

 

In a past life in which I sat in a cubicle and someone actually gave me a pay check every week I was a huge fan of Xamarin products.  They do very a good job of enabling .NET developers to leverage their skill across many platforms.  In fact, they are the technology that Unity is built on top off.  That said, I became increasingly less of a fan when the checks stopped and expenses came out of my own pocket!

 

There are many people out there that view making money from software as somehow evil.  I am certainly not one of those people.  In that corporate environment, where developers are paid salaries, rent is paid for office space, taxes are paid, etc…  the price of a software tool like Xamarin is trivial to justify.  In the world of indie game development though, this is often simply not the case.

 

Thing is, Xamarin has become a necessary evil for so many C# based game engines ( MonoGame, WaveEngine, Duality, Paradox, etc ) if you want to port to iOS or Android.  Many of these developers will never see a dime from their efforts, while a select few will become massively rich and a certain middle ground will eek out a living doing what they love.  It’s the later two groups that keep companies like Unity and Unreal afloat, and those two groups don’t come into being without the former group.

 

The challenge with Xamarin has always been their license structure has always been pretty awful for amateur developers.  How many people have chosenn not to work in C# simply because their is a price tag attached?  After years of awaiting a newer friendlier license structure (or Microsoft buyout), hope is on the horizon.

 

Today, in response to Xamarin’s recent acquisition of RoboVM, I ended up in this Twitter conversation with Nat Friedman, CEO of Xamarin:

 

First, in regard to the acquisition of RoboVM and how long the free for LibGDX developers offer will be extended:

image

 

Then more on the indie friendly nature of Xamarin, or lack thereof:

image

(Portion excerpted, Twitter message threading is bizarre)

image

image

 

This is news I am certain many C# game developers and tool providers are going to be delighted to hear.  Hopefully something happens fairly soon, as I’ve been waiting about 6 years and counting at this point! ;)

Programming News


GFS On YouTube

See More Tutorials on DevGa.me!

Month List