2048 PART 4: ADDING FACEBOOK LOGIN AND SAVING THE PROGRESS

Welcome back to our series of articles demonstrating how to add social and network features to an existing application. If you are reading us for the first time today (we'd like to welcome you by the way!), we recommend that you take a look at our first article.

The next step is similar to the login by e-mail, except that we’ll be adding support for the Facebook SDK. Also, we will give a true meaning to the login, as we will be saving the game in the Cloud, allowing a player to continue it from everywhere by just signing in.

We have two options, we can either link an account to Facebook (allowing to share the gameplay with one’s friends) without using Facebook as a mean of authentication, or convert the account to use Facebook as a credential.

In this case, as we do not have much interest in linking the Facebook credentials with the account, we’ll simply use it as a mean of authentication, just like the e-mail address previously.

ADDING THE FACEBOOK JAVASCRIPT SDK

The first step is to add the Facebook Javascript SDK. Head to the Facebook developer website and follow the instructions. Note that you will need to create an application ID on the Facebook developer portal and configure it to point to the URL where the page will be shown. Everything is documented on the SDK website.

Then, we’ll simply write the code for login through the Facebook Javascript SDK. The interesting part, added to login_ui.js is here:

LoginUi.prototype.doLoginWithFacebook = function() {  
  FB.login(function(response) {
  if (response.authResponse) {
  var token = response.authResponse.accessToken;
  FB.api('/me', function(response) {
  this.doLoginOrRegisterWithNetwork("facebook", response.id, token);
  }.bind(this));
  } else {
  console.log("User cancelled login or did not fully authorize");
  }
  }.bind(this));
};
LoginUi.prototype.doLoginWithFacebook = function() {  
   FB.login(function(response) {
      if (response.authResponse) {
         var token = response.authResponse.accessToken;
         FB.api('/me', function(response) {
            this.doLoginOrRegisterWithNetwork("facebook", response.id, token);
}.bind(this)); } else { console.log("User cancelled login or did not fully authorize"); } }.bind(this)); };

When the login is made properly, we call doLoginOrRegisterWithNetwork, which will convert the anonymous account to a Facebook-identified account. Those two values (response.id and token) are the ones required to convert the account. The rest of the process is largely the same as when converting an account to an e-mail based account, except that the credentials are the Facebook ID and token instead of the mail address and password respectively.

SAVING THE PROGRESS

CloudBuilder offers multiple ways of keeping track of the progress, which might work better on some kind of game or another. You can either use the VFS for a general-purpose key/value storage, the transaction system for delta-based values or matches to store the state of the current game. In our case, as we play alone, the VFS is a good choice.

In order to successfully include network-based (thus asynchronous) save in the current implementation of the 2048, we need to reaffect this responsibility, which was delegated to the localstoragemanager.js, but doesn’t really have anything to do with local storage.

CloudBuilder.prototype.getGameState = function(callback) {  
var vfs = this.clan.withGamer(this.gamerData).gamervfs();  
vfs.get(this.gameStateKey, callback);  
};

Apart from moving that to the cloud_builder.js file, the implementation remains similar (though we do not need to explicitly convert the JSON to text and vice versa, CloudBuilder handles that for us). We just have a callback to notify when the operation completes.

Saving the state is just as simple. We just need to integrate this nicely with the game flow, and the fact that we can sign in and out at any point. In fact, there are three points that need consideration here:

We need to wait for CloudBuilder to be signed in before we can retrieve the game state (thus the game can not directly be restored upon startup).
Save should be done often enough so that when the browser is closed, the player is able to continue his game next time, but not too often to avoid excessive network usage.
The game state should be restored upon signing in.
For the first and third points, we’ll simply move out the automatic game state restoration out from GameManager.setup and do it once signed in. The implementation done in previous articles is already good for that, since we introduced a loginStateChanged event, which can be used exactly for this purpose. This event will then serve the following purposes: refresh the leaderboards, restore the game state and update the UI accordingly.

// COTC Whenever login info change, update the game UI
this.loginUi.loginStateChanged.onEvent(function() {  
var gamerData = this.cloudBuilder.gamerData;  
this.actuator.initialize({gamerName: gamerData.profile.displayName});  
this.restoreGameState();  
this.updateBestScore();  
}.bind(this));

As for saving the game appropriately, it is a slightly different issue. In our case, we simply chose to set a timer that will save the game 5 secondes after any move. Naturally, if a timer has already been set, we won’t add another one. Basically it means that while the player is making moves, the game will be saved around every 5 seconds, and when he has stopped no save will be done at all. Other strategies could be applied, such as saving whenever user activity stops, saving only when the tab closes, etc. yet in our case this one is probably the safest.

This is done simply as shown below, with the didMove method to be called whenever a tile is moved.

GameManager.prototype.didMove = function() {  
this.update();  
if (!this.lastMoveTimer) {  
this.lastMoveTimer = setTimeout(function() {  
this.cloudBuilder.setGameState(this.serialize());  
this.lastMoveTimer = null;  
}.bind(this), 5000);
}
};

That’s it for a nice “cloudified” 2048 game that you can play against your friends. We hope you enjoyed this series of articles. You can play the final game here.

Take the challenge and blast the scores of our 2048-addicted team at Clan of the Cloud!