5
\$\begingroup\$

I am building a Tic Tac Toe game with AngularJS and making it online playable with AngularFire. The Tic Tac Toe logic is all there so this question concerns Angularfire a little bit more. I want to be able to match a user with an opponent as well as delete inactive games.

I have done my homework and at this point I want to get the smell out of my code. Since I am handling asynchronous requests, I built a factory that returns a promise.

app.factory("GameCreator", ["$q","$firebase",function($q, $firebase){
    var deferred = $q.defer();
    var ref = new Firebase("https://myfirebase.firebaseio.com/");
    $firebase(ref).$on("loaded",function(value){
        var games = $firebase(ref);
        var IDs = games.$getIndex();
        var initGame = function(n){
            games.$add({
                //the board's state and turns, shared by all users
                board:[['','',''],['','',''],['','','']],
                xTurn:true,
                turns:0,
                playerone:{piece:'x', ready:false,won:false},
                playertwo:{piece:'o',ready:false,won:false},
                //helpers to sync and assign player
                xIsAvailable:false,
                oIsAvailable:true
            });
            //my opponent did something.  His/her actions need to appear on my screen.
            games.$on("change",function(){  
                deferred.resolve( games.$child(games.$getIndex()[n]) );
            });
        };
        var n = IDs.length;
        //if no games, then build a game
        if(n == 0){
            initGame(n);
        }
        //else, determine placement in new vs existing game
        else{
            //if last - 1 has a spot, put me in that game, else create me a new game
            var checkThisGame = games.$child(IDs[n-1]);
            checkThisGame.$on('loaded',function(){
                if(checkThisGame.oIsAvailable == true){
                    checkThisGame.oIsAvailable = false;
                    checkThisGame.$save();
                    deferred.resolve(checkThisGame);
                }
                else{
                    initGame(n);
                }
            });
        }
    return deferred.promise;    
    });
}])

In my controller, I then use the resolved promise to fulfill my objectives:

app.controller ('BoardCtrl', function($scope,$timeout,GameCreator,$window) {
    GameCreator.then(function(returnedData){
        returnedData.$on('loaded',function(){
            $scope.game = returnedData;
            var piece;
            if(returnedData.oIsAvailable == true) {
                piece = 'x';
            }
            else {
                piece = 'o';
            }
            $scope.myPiece = {
                val:piece
            };
            $window.onbeforeunload = function (event) {
                //delete this game from the firebase I/O
                returnedData.$remove();
                return null;
            }
            //the rest of the tic tac toe game logic follows here,
            //with all proper calls to $scope.game.$save()
        });
    });
);

Since I do not completely know what I am doing, I will ask: did I do this right? Is there some refactoring that could be done? It works as expected but I thought I would ask for a review.

\$\endgroup\$
1
\$\begingroup\$

I am not an angular expert, but this

var piece;
if(returnedData.oIsAvailable == true) {
    piece = 'x';
}
else {
    piece = 'o';
}
$scope.myPiece = {
    val:piece
};

could be

$scope.myPiece = {
    val: returnedData.oIsAvailable ? 'x' : 'o'
};

Also

  • I know the firebase API calls the object returned by new Firebase a (root) reference. It still irks me since my brain keeps thinking what is ref?? I would probably go against the grain and call it db, but that could be because I am simply not familiar enough with the API
  • if(checkThisGame.oIsAvailable == true){ should be if(checkThisGame.oIsAvailable){ or if(checkThisGame.oIsAvailable === true){
  • the game is well documented
  • JsHint.com finds a number of small things, you should use the site
\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.