Tech

Updating Real Time IAP Pricing and Variables with Syncano

Bq7qkl3

Posted by Mark Alexander on 25 April 2016

This week's tech blog is written by guest writer Thomas Webb from the GameMaker community. Today he's going to explain how to use Syncano to change IAP pricing and other variables quickly and easily within your GameMaker game after it has been published.


As an indie game developer attending events like PocketGamer Connects and Develop Brighton, I have noticed this trend. There are lots of services out there for indie developers, and AAA’s enabling them to manage in-game pricing of iAPs, trigger special promotions and even edit in-game functionality – all in real-time at the flick of a switch.

If you’re in the free to play mobile game industry, you will know that analytics is everything. Knowing when to sell to your users, when to offer free rewards, this stuff is priceless and can make the difference between a title with a million DAUs or a title taking $1mil per month in revenue (I am literally just guessing but you get the point).

Why do I need to change in-game pricing?

What’s the point in having products and no method to reflect their price in relation to demand? We all know about the simple pricing psychology tactics, 3.99, 6.99 and 8.99 models where 80% of users are encouraged to purchase the 6.99 price. But in today's world this just doesn’t cut it.

What I want to do is build a game that I can constantly alter, based on geo-location, national holidays and user behaviour. You name it.

How to tackle this problem in GameMaker: Studio

We need real-time access to our game, if users are dropping out after three plays because of an ad, we need to be able to change our game instantly, perhaps to show ads after 6 plays instead and you don’t have a week to wait for Apple or Google to accept your app update, it’s got to happen instantly.

We tackle this by using a real-time cloud service like Syncano. I heard about these guys because my genius of a father uses it for his app to handle data storage and so so much more.

TL DR: You can use this code to load in-game variables and arrays from the cloud and save them onto the device for offline use.

The Code And Inner Workings

To make this work we’re going to create a few scripts that will allow us to have a load file on the Syncano cloud which we will load from each time the device boots up. To keep it up to date, we will save this data to the device for future use when in offline mode.

GameMaker: Studio allows for HTTP request quite nicely along with Asynchronous callbacks. For those that don’t know, an asynchronous event is one that runs outside of the GameMaker step event. It will only trigger once the HTTP request is received on the server and the server sends a callback to the device.

Setting up Syncano

First you need to sign up to Syncano – you can do that here

Once you’re signed up, you need to create an instance – let’s call it gamemaker.

Click on this and then in the left sidebar navigation click on classes. You’re going to create a new class, let’s call it ‘datafile’.

Under the Data Objects column, click the table next to the Zero in your ‘datafile’ class.

This will open up your database effectively. Now Syncano bills users based on datapoints and every time you make a call you use one of these. If you have 50k DAUs and everytime they open your game it’s calling this, you’re going to rack up $$$$$ per month in server costs which may be fine but let’s keep it down by being clever.

We are going to create one object that stores all of our game properties – this way we only need to make one http request per user. We can save this data to the device and even timestamp it so users only download a new datafile once every day, week, it’s up to you.

This is where it gets fun – click on Classes and then hit the three dot menu located on the right hand side of the ‘datafile’ class. It will open a dropdown, click edit class.

This is where we declare all of the variables, strings, integers.

Let’s create a few as an example, ‘ourVarOne’, ‘ourVarTwo’ as integers and ‘gameName’ as a string. You can also create floats (0.000s) and arrays but we will get to that another time.

Now we can click on the table next to the ‘datafile’ class and view our dataobject with ID 1. It will have our variables listed in separate columns and we can click on it to edit these properties. I have put in some data for now.

Right, let’s get this data into GameMaker: Studio! But, before you do this, click on API Keys and create an API key as you'll need it later.

Retrieving The Data From Our GameMaker: Studio Game

I would recommend trying this is in a new project to avoid confusion. First we create a new object called objO. Add a ‘Create’ event and also under Asynchronous, an ‘HTTP’ event.

In our create event we will paste the below code:

// This is the name of your instance in Syncano | CHANGE TO YOUR INSTANCE ID
instanceid = "gamemaker";
//This is the name of your class in Syncano | CHANGE TO YOUR CLASS NAME
class = "datafile";
// This is your API Key from Syncano| CHANGE TO YOUR API KEY
apikey = "PASTE IN YOUR API KEY";
// This is the Data Object ID - If you only have one data object, the ID will be 1 for e.g.| CHANGE TO YOUR DATA OBJECT ID
objectid = "1"
// This creates the HTTP request with the ID syncGet, we will check this in the Async Event DO NOT EDIT THIS
global.syncGet = http_get("https://api.syncano.io//v1.1/instances/" + instanceid + "/classes/" + class + "/objects/" + objectid + "/?api_key=" + apikey);
//Run to show the full string in debug console 
show_debug_message("https://api.syncano.io//v1.1/instances/" + instanceid + "/classes/" + class + "/objects/" + objectid + "/?api_key=" + apikey)

What this will do is make a HTTP request with the ID of global.syncGet (I use a global incase you put the async event in a different room, it can take a while to come back if you’re on a really slow connection.

This calls your Syncano instance and will return a JSON encoded string. Now GameMaker doesn’t understand JSON, but it can decode it into a DS_Map.. GREAT SUCCESS!

So we paste this code below into the HTTP async event – this will only trigger once we get a callback from Syncano.

First it checks that the HTTP callback matches the original one we sent out – this is helpful if you have multiple HTTP requests firing and don’t want your code to be triggered by the wrong callback.

// Check that this Async Event matches the HTTP request ID syncGet
if async_load[? "id"] == global.syncGet
    {
    // Check the HTTP request ID matches the ASYNC Event 
    // Store the JSON callback string from Syncano in a varible
    var json = async_load[? "result"]
    // To check you're getting the right JSON back you can print it to the screen.
    //show_message(json);
    //Decode the JSON from the HTTP request into a DS Map called var map
    var map = json_decode(json);
    //if it doesn't load map
    if map = -1 {show_debug_message("failed to get URL")}
    // DEFINE YOUR CLASSES
    /// REPLICATE THIS TO GRAB ANY FLOAT,INTEGER,STRING and store it in a ds_map
    ourVarOne = syncanoVar(map,"ourVarOne");
    // For example - this would check for a class called test2 and fill ourVariable2 with whatever is in it.
    ourVarTwo = syncanoVar(map,"ourVarTwo");
    // Get a string
    gameName = syncanoVar(map,"gameName");
    // destroy the map to avoid leaks 
    ds_map_destroy(map);
    }

There we have it. If you set everything up right you should have your three variables full of real-time data. Just log into Syncano and change the numbers, it should update instantly in your app.

I would load these variables in the create event, and if they are grabbed in the Async event, write them to the device. This way if you have no internet connection, your device will load the most recent datafile downloaded.

Applications

Here are a few ideas I have used this for.

Running various game code versions – say you have three different methods of gameplay you want to test. Create a variable, either 1,2 or 3, put in a switch statement and boom. You can select which version you want to run in you Data Object on Syncano and it will update in game.

Geo-Located pricing - let’s say you have three iAPs. 10, 100 and 1000 coins. You can’t change the iAP price easily, but you could make it 20, 200 or 2000 coins.

  1. Create a new dataobject for each of your regions, their object ID will be 1,2,3,4,5, etc. Create three variables, purchase1,purchase2,purchase3.
  2. You can grab regionCode on your device using a HTTP request to http://ip-api.com/json
  3. Decode the JSON, load it into a DS map the same way as done above.
  4. Now you can make some code that will change the ‘objectid’ we use in our HTTP request from Syncano depending on what the region code is, ‘if regionCode = GB {objectid = 3} for example.

Personally I store 20 variables that effect the game play, how often ads show in game, pricing, rewards, I even have code that will allow me to turn a variable to true and initiate a special offer.

Feel free to drop me any questions to the social media links below and have fun making your game even more dynamic with updatable, online storage using Syncanos real-time cloud.


Thomas Webb Director Reventador Games.

Thomas started programming 2 years ago with GameMaker Studio with zero previous knowledge. Now developing indie games for mobile devices @ReventadorGames.

Back to Top