Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Added ability to share game board with scores on twitter and facebook. #8

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
53 changes: 39 additions & 14 deletions Gruntfile.js
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ module.exports = function (grunt) {
watch: {
bower: {
files: ['bower.json'],
tasks: ['bowerInstall']
tasks: ['wiredep']
},
js: {
files: ['<%= yeoman.app %>/scripts/{,*/}*.js'],
Expand Down Expand Up @@ -119,8 +119,8 @@ module.exports = function (grunt) {
dest: '<%= yeoman.dist %>/scripts/templates.js',
options: {
cwd: '<%= yeoman.app %>',
url: function(url) {
return url.replace('app/', '');
url: function(url) {
return url.replace('app/', '');
},
usemin: 'scripts/templates.js',
htmlmin: '<%= htmlmin.app %>'
Expand Down Expand Up @@ -174,14 +174,31 @@ module.exports = function (grunt) {
},

// Automatically inject Bower components into the app
bowerInstall: {
app: {
src: ['<%= yeoman.app %>/index.html'],
ignorePath: '<%= yeoman.app %>/'
},
sass: {
src: ['<%= yeoman.app %>/styles/{,*/}*.{scss,sass}'],
ignorePath: '<%= yeoman.app %>/bower_components/'
// bowerInstall: {
// app: {
// src: ['<%= yeoman.app %>/index.html'],
// ignorePath: '<%= yeoman.app %>/'
// },
// sass: {
// src: ['<%= yeoman.app %>/styles/{,*/}*.{scss,sass}'],
// ignorePath: '<%= yeoman.app %>/bower_components/'
// }
// },
wiredep: {
task: {
// Point to the files that should be updated when
// you run `grunt wiredep`
src: [
'<%= yeoman.app %>/index.html', // .html support...
'<%= yeoman.app %>/styles/main.scss' // .scss & .sass support...
],

options: {
// See wiredep's configuration documentation for the options
// you may pass:

// https://github.com/taptapship/wiredep#configuration
}
}
},
// Renames files for browser caching purposes
Expand Down Expand Up @@ -285,7 +302,7 @@ module.exports = function (grunt) {
}]
}
},

// Replace Google CDN references
cdnify: {
dist: {
Expand Down Expand Up @@ -366,6 +383,9 @@ module.exports = function (grunt) {
// },

// Test settings
/**
* The Karma configurations.
*/
karma: {
unit: {
configFile: 'karma.conf.js',
Expand All @@ -382,7 +402,8 @@ module.exports = function (grunt) {

grunt.task.run([
'clean:server',
'bowerInstall',
// 'bowerInstall',
'wiredep',
'concurrent:server',
'autoprefixer',
'connect:livereload',
Expand All @@ -405,7 +426,7 @@ module.exports = function (grunt) {

grunt.registerTask('build', [
'clean:dist',
'bowerInstall',
'wiredep',
'useminPrepare',
'concurrent:dist',
'autoprefixer',
Expand All @@ -427,3 +448,7 @@ module.exports = function (grunt) {
'build'
]);
};




51 changes: 34 additions & 17 deletions app/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,13 @@
<title>2048</title>
<meta name="description" content="">
<meta name="viewport" content="width=device-width">
<!-- use base tag to remove # (hashtag) from the URL -->
<base href="/">
<!-- Place favicon.ico and apple-touch-icon.png in the root directory -->
<!-- build:css({.tmp,app}) styles/main.css -->
<link rel="stylesheet" href="styles/main.css">
<!-- endbuild -->
<link href='http://fonts.googleapis.com/css?family=Open+Sans:400,700' rel='stylesheet' type='text/css'>

</head>
<body ng-app="twentyfourtyeightApp">
<!--[if lt IE 7]>
Expand All @@ -39,30 +40,46 @@
<script src="bower_components/json3/lib/json3.min.js"></script>
<![endif]-->

<!-- build:js scripts/vendor.js -->
<!-- build:js -->
<!-- bower:js -->
<script src="bower_components/jquery/dist/jquery.js"></script>
<script src="bower_components/angular/angular.js"></script>
<script src="bower_components/bootstrap-sass-official/vendor/assets/javascripts/bootstrap.js"></script>
<script src="bower_components/angular-route/angular-route.js"></script>
<script src="bower_components/json3/lib/json3.min.js"></script>
<script src="bower_components/es5-shim/es5-shim.js"></script>
<script src="bower_components/jquery/dist/jquery.js"></script>
<script src="bower_components/bootstrap-sass-official/vendor/assets/javascripts/bootstrap/affix.js"></script>
<script src="bower_components/bootstrap-sass-official/vendor/assets/javascripts/bootstrap/alert.js"></script>
<script src="bower_components/bootstrap-sass-official/vendor/assets/javascripts/bootstrap/button.js"></script>
<script src="bower_components/bootstrap-sass-official/vendor/assets/javascripts/bootstrap/carousel.js"></script>
<script src="bower_components/bootstrap-sass-official/vendor/assets/javascripts/bootstrap/collapse.js"></script>
<script src="bower_components/bootstrap-sass-official/vendor/assets/javascripts/bootstrap/dropdown.js"></script>
<script src="bower_components/bootstrap-sass-official/vendor/assets/javascripts/bootstrap/tab.js"></script>
<script src="bower_components/bootstrap-sass-official/vendor/assets/javascripts/bootstrap/transition.js"></script>
<script src="bower_components/bootstrap-sass-official/vendor/assets/javascripts/bootstrap/scrollspy.js"></script>
<script src="bower_components/bootstrap-sass-official/vendor/assets/javascripts/bootstrap/modal.js"></script>
<script src="bower_components/bootstrap-sass-official/vendor/assets/javascripts/bootstrap/tooltip.js"></script>
<script src="bower_components/bootstrap-sass-official/vendor/assets/javascripts/bootstrap/popover.js"></script>
<script src="bower_components/angular-cookies/angular-cookies.js"></script>
<script src="bower_components/angular-animate/angular-animate.js"></script>
<script src="bower_components/angular-ui-router/release/angular-ui-router.js"></script>
<!-- endbower -->
<!-- endbuild -->

<!-- build:js({.tmp,app}) scripts/scripts.js -->
<script src="scripts/app.js"></script>
<script src="scripts/grid/grid.js"></script>
<script src="scripts/grid/grid_directive.js"></script>
<script src="scripts/grid/tile_directive.js"></script>
<script src="scripts/keyboard/keyboard.js"></script>
<script src="scripts/game/game.js"></script>
<!-- endbuild -->
<!-- LZ-String Compress and Encode (Vendor) -->
<!-- https://github.com/pieroxy/lz-string/ -->
<script src="vendors/lz-string/lz-string.js"></script>


<!-- build:js scripts/templates.js -->
<!-- bower:js -->
<!-- endbower -->
<!-- endbuild -->
<!-- build:js({.tmp,app}) scripts/scripts.js -->
<script src="scripts/app.js"></script>
<script src="scripts/grid/grid.js"></script>
<script src="scripts/grid/grid_directive.js"></script>
<script src="scripts/grid/tile_directive.js"></script>
<script src="scripts/keyboard/keyboard.js"></script>
<script src="scripts/social/social.js"></script>
<script src="scripts/social/twitter/twitter_directive.js"></script>
<script src="scripts/social/facebook/facebook_directive.js"></script>
<script src="scripts/game/game.js"></script>
<!-- endbuild -->

</body>
</html>
54 changes: 44 additions & 10 deletions app/scripts/app.js
Original file line number Diff line number Diff line change
@@ -1,26 +1,60 @@
'use strict';

angular
.module('twentyfourtyeightApp', ['Game', 'Grid', 'Keyboard', 'ngAnimate', 'ngCookies'])
.module('twentyfourtyeightApp', ['Game', 'Grid', 'Keyboard', 'Social', 'ngAnimate', 'ngCookies', 'ui.router'])
.config(function(GridServiceProvider) {
GridServiceProvider.setSize(4);
})
.controller('GameController', function(GameManager, KeyboardService) {
.config(function($stateProvider, $urlRouterProvider, $locationProvider) {
$stateProvider.state( 'app', {
url: '/?board',
controller: 'GameController'
});

this.game = GameManager;
// For any unmatched url,
$urlRouterProvider.otherwise('/');
// use the HTML5 History API so we can remove # (hashtag) from the URL
$locationProvider.html5Mode(true).hashPrefix('!');
})
.controller('GameController', function(GameManager, KeyboardService, $stateParams, $location) {
var vm = this;

vm.game = GameManager;

this.newGame = function() {
// Internal function. It will not be exposed in Controller API
var init = function() {
KeyboardService.init();
this.game.newGame();
this.startGame();
// if board parameter is not empty
if ($stateParams.board && $stateParams.board.length > 0) {
vm.restoreGame();
} else {
vm.newGame();
}
vm.startGame();
};

this.startGame = function() {
var self = this;
vm.newGame = function() {
vm.game.newGame();
};

vm.startGame = function() {
KeyboardService.on(function(key) {
self.game.move(key);
vm.game.move(key).then(function() {});
});
};

this.newGame();
vm.restoreGame = function() {
vm.game.restoreGame($stateParams.board);
};

vm.generateShareableLink = function() {
var url = $location.protocol() + '://' + $location.host() + ':' + $location.port();
return url + '/?board=' + vm.game.encodeGame();
};

vm.getShareableText = function() {
return 'My ' + vm.game.currentScore + ' scores at';
};

init();
});
65 changes: 63 additions & 2 deletions app/scripts/game/game.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
'use strict';

angular.module('Game', ['Grid', 'ngCookies'])
.service('GameManager', function($q, $timeout, GridService, $cookieStore) {
angular.module('Game', ['Grid', 'ngCookies', 'LZString'])
.service('GameManager', function($q, $timeout, GridService, $cookieStore, LZString) {

this.getHighScore = function() {
return parseInt($cookieStore.get('highScore')) || 0;
Expand All @@ -18,6 +18,8 @@ angular.module('Game', ['Grid', 'ngCookies'])
this.win = false;
this.currentScore = 0;
this.highScore = this.getHighScore();
//
this.encrypted = null;
};
this.reinit();

Expand All @@ -27,6 +29,64 @@ angular.module('Game', ['Grid', 'ngCookies'])
this.reinit();
};

// Restore the game board with the data sent by the user via URL
this.restoreGame = function(gameEncrypted) {
GridService.buildEmptyGameBoard();
if (gameEncrypted) {
// decode the data
var game = this.decodeGame(gameEncrypted);

if (game) {
GridService.restoreGameBoard(game.tiles);
this.updateScore(game.currentScore);
return true;
}
}
// Couldn't restore, start in initial state
GridService.buildStartingPosition();
return false;
};

this.encodeGame = function() {
// minify tiles object
var tiles = this.tiles.map(function(tile) {
return tile ? tile.value : null;
});
var game = [this.currentScore, tiles];
// encode game data
var encryptedGame = LZString.compressToEncodedURIComponent(JSON.stringify(game));
return encryptedGame;
};

this.decodeGame = function(encryptedGame) {
var decompressed = LZString.decompressFromEncodedURIComponent(encryptedGame);
if (decompressed) {
var temp = JSON.parse(decompressed);
if (this.validateDecodedGame(temp)) {
var game = {
currentScore: temp[0],
tiles: temp[1]
};
return game;
}
}
return null;
};

this.validateDecodedGame = function(game) {
if (game.length === 2 && game[1].length === 16) {
// Check if its in the right structure
for (var i = 0, l = game[1].length; i < l; i++) {
var item = game[1][i];
if (Array.isArray(item)) {
return false;
}
}
return true;
}
return false;
};

/*
* The game loop
*
Expand Down Expand Up @@ -117,6 +177,7 @@ angular.module('Game', ['Grid', 'ngCookies'])

this.updateScore = function(newScore) {
this.currentScore = newScore;

if(this.currentScore > this.getHighScore()) {
this.highScore = newScore;
$cookieStore.put('highScore', newScore);
Expand Down
21 changes: 18 additions & 3 deletions app/scripts/grid/grid.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ angular.module('Grid', [])
// http://stackoverflow.com/questions/105034/how-to-create-a-guid-uuid-in-javascript
var d = new Date().getTime();
var uuid = 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, function(c) {
var r = (d + Math.random()*16)%16 | 0;
var r = (d + Math.random()*16) %16 | 0;
d = Math.floor(d/16);
return (c === 'x' ? r : (r&0x7|0x8)).toString(16);
});
Expand Down Expand Up @@ -91,10 +91,11 @@ angular.module('Grid', [])
this.getSize = function() {
return service.size;
};
// Build game board

// Build empty game board
this.buildEmptyGameBoard = function() {
var self = this;

// Initialize our grid
for (var x = 0; x < service.size * service.size; x++) {
this.grid[x] = null;
Expand All @@ -105,6 +106,20 @@ angular.module('Grid', [])
});
};

// Restore game board from array of values
this.restoreGameBoard = function(tilesValues) {
var self = this,
i = 0;
this.forEach(function(x,y) {
var value = tilesValues[i];
if (value) {
var tile = self.newTile({x:x,y:y}, value);
self.insertTile(tile);
}
i++;
});
};

/*
* Prepare for traversal
*/
Expand Down
1 change: 1 addition & 0 deletions app/scripts/social/facebook/facebook_directive.html
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
<img class="facebook-share" src="https://simplesharebuttons.com/images/somacro/facebook.png" alt="Facebook" title="Share on Facebook" />
Loading