In Game Currency

Brian Here…

Every time I write that I misspell it as brain here and that’s probably appropriate as this post is all about using your brain to make money from your game. That’s at least part of the whole point right?

You can read the experts blogging about this all over the internet and it boils down to a few basic facts – and when I says facts it’s only true because everyone says it and repeats it:

  1. The free to play games with multiple virtual and real “currencies” in the game economy do best.
  2. Rewarded ads monetise players who do not spend. Apparently that’s most of them.
  3. You need to get players hooked on the game first and then introduce rewards slowly.
  4. You need to build networks with partners who can help promote and support your game and economy.

It’s all about volume and scale. You’re not making a huge amount of cash from every player. It’s small change dollars and cents. So to make any money you have to have heaps and heaps of people who not only download your game but play it regularly. So the game better be good and popular.

The rewards are going to start slowly. So there is no big bang money injection when you release your game. It’s a real slow burn and you need to pick your engagement points so that the game stays enjoyable through all that time.

But how the hell do you do that? You have to test the game with heaps and heaps of people and different target audiences. This is not functional testing. I mean actual player response. You need to know when those frustration points are that mean a player may watch an ad or buy some power-ups to get through some level or reach some achievement. To do that you also need an in-app monitoring system that tracks players progress and provides up to date statistics on what’s happening out there in user land.

You need to be able to squeeze those moments and know which one’s are working and be able to replicate them in other situations in the game. You need to entice players not only with a great game but with achievements and rewards, and special power-ups, and gems and hearts and badges and leader boards and competitions and in game sales campaigns. It’s a huge task.

So these are the metrics and these are the logistics. It’s like organising an empire or a battlefield (hey that would make a good game!). It needs lots of planning and help from as many sides as you can muster.

Every time the player gets rewarded it only seems fair that we get rewarded as well for a job well done.

Fly Birdy! Fly! – 2D Curved Movement in Unity


Xander here…

I’m really pushing to get the flip book style 2D endless runner game we started at the beginning of the year finished.  The game is called Dog Run and as the title suggests is about taking your fun lovin’ pooch for a run – but watch out! There is a bunch of obstacles in your path – it’s a good thing you are such a natural jumper and can run all day.

If you want to do some beta testing of the game subscribe to this blog using the form on the right!

So I wanted to do a nice simple bird flying in the background to add a bit on interest (and also as a distraction for the player).  How hard do you think that would be?  It’s just a little birdy flapping about.  Whole games have been made with less!  It actually too me three days to get this little bird looking right.

In the beginning I started with just a straight fly-by  – a simple transform move that crossed the screen.

Straight


transform.position -= new Vector3(0.1f, 0, 0);

Not that exiting right? But you know – it’s a start.

 

I thought a little more about it and decided it would look better if there was a bit more movement.  I originally envisioned a sort of swooping dive from the top of the screen.

This got me a little closer but it looks really nothing at all like a bird would or could fly. A mechanical bird maybe – but not your darling little currawong.

ZigZag


if (updown)
{
target.position = new Vector3(transform.position.x - 2, transform.position.y - 2, transform.position.z);
updown = false;
}
else
{
target.position = new Vector3(transform.position.x - 2, transform.position.y + 2, transform.position.z);
var desiredRot = new Vector3(0, 0, -30);
updown = true;
}

Not such an elegant piece of code but it did what I wanted it to without a huge fuss.

 

ZigZag with Rotation

I tried to fix it a bit by adding in some rotation towards the direction being flown:


from.rotation = transform.rotation;
to.rotation = Quaternion.Euler(new Vector3(0, 0, 30));
transform.rotation = Quaternion.Lerp(from.rotation, to.rotation, Time.time * lspeed);

I really wasn’t liking where this was going.

Follow the Sine

I had the brainwave to start using a centre point and looping the bird around it with transform.RotateAround();  Which started off looking really good. But all I could do was get the bird to fly in circles – which started to look a little mad!

Finally after many attempts I found a method for using a Sine function that looked like it would work really well.  It meant adding a rigidbody to my object and a bit more overhead than I really wanted for a background character but what the heck I’d spent this much time on it – might as well have it look the way I wanted.


public Rigidbody2D rb;

public Transform target;    // A point on the far side of the screen to fly towards
public float speed;             //  I ended up between 2 and 3 in the inspector for this one
public float amplitude;     //  How high (or low) each wave would be - around 8 worked best
public float frequency;     // How many waves would run in the given time (2 to 4 was used)

private float startTime;
private Vector3 direction;
private Vector3 orthogonal;

void Start()
{
startTime = Time.time;
direction = (target.position - transform.position).normalized;    // Which way to head
orthogonal = new Vector3(-direction.z, direction.x, 0);               //  Which wave to catch!
}

void FixedUpdate()
{
float t = Time.time - startTime;
rb.velocity = direction * speed + orthogonal * amplitude * Mathf.Sin(frequency * t);
// The Black Magic
}

This worked a treat and with a bit of tuning was dipping and diving all over the shop!

 

All I needed to do next was to get a little rotation into the picture and we were totally flying!

Sine with Rotation


transform.right = -rb.velocity;

 

Thanks to: http://blog.shamanland.com/2016/03/move-by-sinusoid.html

For helping me understand what I wanted and for not protecting me from the details.

Adventure Castle Legend!

Hey it’s Gene here…

What do you do when it’s dark, wet and cold.?

Spend the afternoon pretending to be a princess exploring a dangerously beautiful castle!

It’s official. I am a legend and king of “The Castle”.

See if you can make it through all ten levels in one sitting.

(Click on image to Play).

HTML5 Retro Gaming at it’s best!   Be patient while it loads  🙂

There’s a new Law in Town!

Hi Harmony here…

Check out this feature character for our new game Endless Elevator.

He’s “The Law Man” and he’s bringing Justice to the small screen.

He’s a chunky little guy and dependably dapper.

Look at that moustache!

He comes complete with accessorised bullet proof vest and fast blasting six gun action.

Bad Guys look out! He’s coming soon.

Unity3D Smooth Moves

Xander here.

For our new game Endless Elevator I’ve been working on finding the best method of moving the character through the scenes.

At it’s most basic our character needs to move left and right across the screen and forwards and backwards on a couple of limited parallel z axis.

The only way he can move up or down is by an escalator or an elevator so we have to take control away from the user in that case and handover to another controller.  Then once we were done moving we can hand control back to the user.

But it was mostly the left-right, forwards-backwards movements I was concerned about for this set of tests.

I wanted a really simple set of controls and didn’t want to hand them over to the Physics Engine with Rigidbodies and Colliders.  But the character movement couldn’t feel stiff or mechanical. We wanted a bit of slack in the movement and bounce

.

I scripted up three different methods of controlling the character with flip switches to move between them during testing so we could decide on the best looking movement.

Method One was the most simple basic Vector move.

Method Two was a damped Vector move using mathf.DampSmooth.

Method Three was to implement the Character Controller and use Object.Move.

I’ll put the script down the bottom of the post. Right now I want to look the actual movement controllers and the Input into those commands.

Let’s start with the Basic Move controller.

We define our speed as a float and get the x and z values from our Vertical and Horizontal Input Axis (WASD or Arrow Keys on the computer).

public float speed = 10f;
var x = Input.GetAxis(“Horizontal”);     // this is a float value between -1 and 1 that tracks left and right input from the left and right controller.  If it’s under 0 we move left. If it’s over 0 we move right. Simple easy to understand and doesn’t factor into the movement at all except to define which way we go.

var z = Input.GetAxis(“Vertical”);  // We do the same for the z value which governs character depth on the screen (forwards and backwards).

if (x < 0) {
transform.position -= new Vector3(speed * Time.deltaTime, 0, 0);  // Move Left the value of speed and normalised for frame rate differences with the deltaTime function.
}
if (x > 0) {
transform.position += new Vector3(speed * Time.deltaTime, 0, 0);  // Right
}
if (z < 0) {
transform.position -= new Vector3(0, 0, speed * Time.deltaTime);  // Towards the camera
}
if (z > 0)
{
transform.position += new Vector3(0, 0, speed * Time.deltaTime);  // Away from the camera
}
Every Update we move our character in the desired direction at a speed of 10.

This is fine. It works. But it looks kind of static.  The character hits full speed straight away and stops on a dime.  It’s not particularly realistic looking (and maybe you want your game to have this look) and not what I really wanted.  But it’s a great comparison to judge the other two methods by.

Let’s look at the Smooth Damp method next.

We use the same kind of input:  eg. x = Input.GetAxis(“Horizontal”);

speed = 1f;  //  This method is much faster so we need to reduce the speed to keep all the methods at roughly the same rate.

We set some variables that control the “bounciness” of the smoothing.

public float forwardVelocity = 0;
public float sidewaysVelocity = 10;

// These Velocity floats hold the value of the velocity between Updates (I only wanted some on the left right movement)

public float movementSmoothing = 0.15f;  // the higher the number the slower it get’s to top speed.

Mathf.SmoothDamp takes the current position and the raw input from the Input keys. That means that those values between -1 and 1 amp up or down over a small amount of time (depending on the direction) . This is is factored together with the current velocity
movementInput.x = Mathf.SmoothDamp(movementInput.x, Input.GetAxisRaw(“Horizontal”), ref forwardVelocity, movementSmoothing);
movementInput.y = Mathf.SmoothDamp(movementInput.y, Input.GetAxisRaw(“Vertical”), ref sidewaysVelocity, movementSmoothing);
transform.position += new Vector3(movementInput.x * speed, 0, movementInput.y * speed);

//transform.position += new Vector3(movementInput.x * speed * Time.deltaTime, 0, movementInput.y* speed * Time.deltaTime);  // I had that last line with the deltaTime in it as well but it looked “moochy” if that’s a word and did the opposite of smoothing the transitions so it ended up looking like this:

movementInput.x = Mathf.SmoothDamp(movementInput.x, Input.GetAxisRaw(“Horizontal”), ref forwardVelocity, movementSmoothing);

Mathf.SmoothDamp
Gradually changes a value towards a desired goal over time.

public static float SmoothDamp(float current, float target, ref float currentVelocity, float smoothTime, float maxSpeed = Mathf.Infinity, float deltaTime = Time.deltaTime);

Input.GetAxisRaw(“Horizontal”) goes straight from -1 on left arrow back to 0 when off and +1 on right arrow – no smoothing.
Input.GetAxis(“Horizontal”); does the same thing but increments gradually over a short time so that it goes from 0 to 1 in a few microseconds.

Sooo using the Raw one and pumping it into the SmoothDamp function does pretty much the same thing. In the Editor I cannot tell the difference between them.

This controller took a bit more playing with but was really looking good.  It picks up speed incrementally when you start moving and there is a controllable amount of exaggerated overshooting when you change direction. If you set the smoothing or velocity too high it gets really bouncy and a little crazy but at low levels it looks cartoony and mimics the  stretch and squash of that genre.

Lastly I looked at the character controller. It’s part of the system so really easy to set up in a simple move script to get a feel for it.

speed = 20f;  // Once again the speed was modified to get a realistic similarity between the three methods.

The character direction comes straight from the input controllers and the cc.Move method handles everything else.

direction = new Vector3((Input.GetAxis(“Vertical”)), 0, (-(Input.GetAxis(“Horizontal”))));
direction1 = transform.TransformDirection(-direction);
cc.Move(direction1 * speed * Time.deltaTime);

Initially this looked really good. But the more I played with it to try and limit the way it was moving the character and the amount of radians it could turn it quickly got way too complicated and I started getting weird movement behaviour.  So if you want a character controller that you can just plug in and go with then this is good. But if you want more control be prepared for a longer haul.

As with everything this was a greats study into character control methods and one step in the path of looking for a smooth moving character but in the end following a massive redesign of the level system of my game I ended up going with a physics based collider system for the levels and a physics controller.

Not all my time wasted though as I had a better understanding of what I wanted and used elements of both the Smooth Move method and the Basic method in my final Character Control script.

 

This is the final edit of the script I was using if you want to play with it.  Just attach it to a player and add a character controller.  Use the tick boxes on the bools in the editor to switch between methods while playing.

 

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class SmoothMove : MonoBehaviour
{

public bool basicMove;
public bool smoothDampMove;
public bool CCMove;

public Vector2 movementInput = Vector2.zero;
public float forwardVelocity = 0;
public float sidewaysVelocity = 10;

public float movementSmoothing = 0.15f; // the higher the number the slower it get’s to top speed
public float speed;

public CharacterController cc;
public Vector3 direction = Vector3.zero;
public Vector3 direction1; // used for debugging in the editor
float smooth = 50.0f;

// Update is called once per frame
void Update()
{
if (basicMove)
{
speed = 10f;
var x = Input.GetAxis(“Horizontal”);
var z = Input.GetAxis(“Vertical”);

if (x < 0)
{
transform.position -= new Vector3(speed * Time.deltaTime, 0, 0);
}
if (x > 0)
{
transform.position += new Vector3(speed * Time.deltaTime, 0, 0);
}

if (z < 0)
{
transform.position -= new Vector3(0, 0, speed * Time.deltaTime);
}
if (z > 0)
{
transform.position += new Vector3(0, 0, speed * Time.deltaTime);
}
}

if (smoothDampMove)
{
speed = 1f;
movementInput.x = Mathf.SmoothDamp(movementInput.x, Input.GetAxisRaw(“Horizontal”), ref forwardVelocity, movementSmoothing);
movementInput.y = Mathf.SmoothDamp(movementInput.y, Input.GetAxisRaw(“Vertical”), ref sidewaysVelocity, movementSmoothing);
//transform.position += new Vector3(movementInput.x * speed * Time.deltaTime, 0, movementInput.y* speed * Time.deltaTime);
transform.position += new Vector3(movementInput.x * speed, 0, movementInput.y * speed);
}

if (CCMove)
{
speed = 20f;
direction = new Vector3((Input.GetAxis(“Vertical”)), 0, (-(Input.GetAxis(“Horizontal”))));
//direction = new Vector3(0, 0, (-Input.GetAxis(“Horizontal”)));
direction1 = transform.TransformDirection(direction);
//direction1 *= speed;
cc.Move(direction1 * speed * Time.deltaTime);
}
}
}

 

 

Voxellated Procrastination

 

Oh My DOG! Playing with MagicalVoxel is fun! I don’t know what made me open it up. A little bit of frustration with my Dog Run game that’s not really going anywhere that I was happy with. If you feel like doing some beta testing and telling me where I’ve got it all wrong subscribe and I’ll add you into the Alpha Testers group.

You know when you get into that development funk and you can’t seem to get anything to work?

Anyway I was doing some animation research and saw that Magical Voxel had a new upgrade that enabled little animations and that kind of excited me. So I downloaded it and started playing around then BOOM. Inspiration strikes and in a couple of hours I got ten level objects and a new idea for a game and another project building in Unity already.

The voxel editor isn’t that great for porting colored objects into unity cause it creates a new vector for every color and does something a bit funky with the poly count. No problem. I did everything in one color to reduce the number of crazy vectors and imported it into Blender.  Then I added a decimation modifier to lower the poly count and merged a few faces. But then I just started importing models directly into Unity with simple walls and floors and doors and it was awesome.  There was no need to reduce the poly count with such simple meshes. Such a quick workflow!  I could make a doorway or a lift and the actual door or lift box would just fit inside the door frame or lift shaft with no modifications! Awesome. Everything to the same scale.

Import all that into unity and add a dummy character and some basic lighting and here you go…….

Looks great huh?