initial checkin
This commit is contained in:
2
app/js/config.js
Normal file
2
app/js/config.js
Normal file
@@ -0,0 +1,2 @@
|
||||
var sw = {};
|
||||
sw.apiPrefix = './';
|
2
app/js/config.prod.js
Normal file
2
app/js/config.prod.js
Normal file
@@ -0,0 +1,2 @@
|
||||
var sw = {};
|
||||
sw.apiPrefix = '/';
|
1777
app/js/ejs.js
Normal file
1777
app/js/ejs.js
Normal file
File diff suppressed because it is too large
Load Diff
123
app/js/index.js
Normal file
123
app/js/index.js
Normal file
@@ -0,0 +1,123 @@
|
||||
if (typeof(sw) == 'undefined') {
|
||||
var sw = {};
|
||||
sw.apiPrefix = '/';
|
||||
}
|
||||
|
||||
|
||||
(function($) {
|
||||
|
||||
|
||||
//helper functions
|
||||
var pulse = function pulse(elem, duration, easing, props_to, props_from, until) {
|
||||
elem.animate(props_to, duration, easing, function() {
|
||||
if (until() == false) {
|
||||
pulse(elem, duration, easing, props_from, props_to, until);
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
var shuffle = function(obj) {
|
||||
return obj.sort( function() { return 0.5 - Math.random(); } );
|
||||
};
|
||||
var getKey = function(obj) {
|
||||
var word = [];
|
||||
for(var k in obj) word.push(k);
|
||||
return word[0];
|
||||
};
|
||||
|
||||
var selectWordsForGame = function() {
|
||||
//select a random word from the list
|
||||
var words = sw.words[Math.round(Math.random() * sw.words.length)];
|
||||
|
||||
var word = getKey(words);
|
||||
var similar = words[word];
|
||||
//i really should include _
|
||||
var filtered = [];
|
||||
for(var i=0; i<similar.length; i++) {
|
||||
if(similar[i] != word) {
|
||||
filtered.push(similar[i]);
|
||||
}
|
||||
}
|
||||
filtered = shuffle(filtered);
|
||||
filtered = filtered.slice(0, 3);
|
||||
filtered.push(word);
|
||||
filtered = shuffle(filtered);
|
||||
|
||||
sw.currentWord = word;
|
||||
return {word: word, similar: filtered};
|
||||
};
|
||||
|
||||
var startGame = function() {
|
||||
$("#main").empty().html('views/index.ejs', selectWordsForGame());
|
||||
};
|
||||
|
||||
//start app
|
||||
var w = $.ajax({
|
||||
url: sw.apiPrefix + "words.json",
|
||||
dataType: 'json'
|
||||
});
|
||||
|
||||
|
||||
w.done(function(words) {
|
||||
var start = $('.start');
|
||||
start.removeClass('disabled');
|
||||
start.html(' Start ');
|
||||
start.animate({
|
||||
opacity : 1
|
||||
}, 1000, 'linear');
|
||||
|
||||
sw.words = words.words;
|
||||
});
|
||||
|
||||
//events
|
||||
$(document).on('click', '.start', function() {
|
||||
startGame();
|
||||
});
|
||||
|
||||
$(document).on('click', '.word-button', function(ev, el) {
|
||||
el = $(ev.currentTarget);
|
||||
if(sw.currentWord == el.html()) {
|
||||
el.addClass('btn-success');
|
||||
} else {
|
||||
el.addClass('btn-danger');
|
||||
}
|
||||
|
||||
setTimeout(function() {
|
||||
$('.word-button[data-word="' + sw.currentWord + '"]').addClass('btn-success');
|
||||
|
||||
setTimeout(function() {
|
||||
startGame();
|
||||
}, 1000);
|
||||
}, 1000);
|
||||
});
|
||||
|
||||
|
||||
//globals
|
||||
sw.words = [];
|
||||
sw.currentWord;
|
||||
})(jQuery);
|
||||
|
||||
|
||||
|
||||
//utils
|
||||
(function() {
|
||||
window.Utils = {};
|
||||
|
||||
Utils.ellipsis = function(text, maxLength){
|
||||
if(typeof maxLength === 'undefined'){
|
||||
maxLength = 9000; //a large number
|
||||
}
|
||||
|
||||
if (text.length <= maxLength)
|
||||
return text;
|
||||
|
||||
var xMaxFit = maxLength - 1;
|
||||
var xTruncateAt = text.lastIndexOf(' ', xMaxFit);
|
||||
if (xTruncateAt == -1 || xTruncateAt < maxLength / 2)
|
||||
xTruncateAt = xMaxFit;
|
||||
|
||||
return text.substr(0, xTruncateAt) + "…";
|
||||
};
|
||||
|
||||
})();
|
||||
|
9597
app/js/jquery-1.9.1.js
vendored
Normal file
9597
app/js/jquery-1.9.1.js
vendored
Normal file
File diff suppressed because it is too large
Load Diff
1400
app/js/moment.js
Normal file
1400
app/js/moment.js
Normal file
File diff suppressed because it is too large
Load Diff
202
app/js/routie.js
Normal file
202
app/js/routie.js
Normal file
@@ -0,0 +1,202 @@
|
||||
/*!
|
||||
* routie - a tiny hash router
|
||||
* v0.3.0
|
||||
* https://github.com/jgallen23/routie
|
||||
* copyright JGA 2012
|
||||
* MIT License
|
||||
*/
|
||||
|
||||
(function(w) {
|
||||
|
||||
var routes = [];
|
||||
var map = {};
|
||||
|
||||
var Route = function(path, name) {
|
||||
this.name = name;
|
||||
this.path = path;
|
||||
this.keys = [];
|
||||
this.fns = [];
|
||||
this.params = {};
|
||||
this.regex = pathToRegexp(this.path, this.keys, false, false);
|
||||
|
||||
};
|
||||
|
||||
Route.prototype.addHandler = function(fn) {
|
||||
this.fns.push(fn);
|
||||
|
||||
//check against current hash
|
||||
var hash = getHash();
|
||||
checkRoute(hash, this);
|
||||
};
|
||||
|
||||
Route.prototype.removeHandler = function(fn) {
|
||||
for (var i = 0, c = this.fns.length; i < c; i++) {
|
||||
var f = this.fns[i];
|
||||
if (fn == f) {
|
||||
this.fns.splice(i, 1);
|
||||
return;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
Route.prototype.run = function(params) {
|
||||
for (var i = 0, c = this.fns.length; i < c; i++) {
|
||||
this.fns[i].apply(this, params);
|
||||
}
|
||||
};
|
||||
|
||||
Route.prototype.match = function(path, params){
|
||||
var m = this.regex.exec(path);
|
||||
|
||||
if (!m) return false;
|
||||
|
||||
|
||||
for (var i = 1, len = m.length; i < len; ++i) {
|
||||
var key = this.keys[i - 1];
|
||||
|
||||
var val = ('string' == typeof m[i]) ? decodeURIComponent(m[i]) : m[i];
|
||||
|
||||
if (key) {
|
||||
this.params[key.name] = val;
|
||||
}
|
||||
params.push(val);
|
||||
}
|
||||
|
||||
return true;
|
||||
};
|
||||
|
||||
Route.prototype.toURL = function(params) {
|
||||
var path = this.path;
|
||||
for (var param in params) {
|
||||
path = path.replace('/:'+param, '/'+params[param]);
|
||||
}
|
||||
path = path.replace(/\/:.*\?/g, '/').replace(/\?/g, '');
|
||||
if (path.indexOf(':') != -1) {
|
||||
throw new Error('missing parameters for url: '+path);
|
||||
}
|
||||
return path;
|
||||
};
|
||||
|
||||
var pathToRegexp = function(path, keys, sensitive, strict) {
|
||||
if (path instanceof RegExp) return path;
|
||||
if (path instanceof Array) path = '(' + path.join('|') + ')';
|
||||
path = path
|
||||
.concat(strict ? '' : '/?')
|
||||
.replace(/\/\(/g, '(?:/')
|
||||
.replace(/\+/g, '__plus__')
|
||||
.replace(/(\/)?(\.)?:(\w+)(?:(\(.*?\)))?(\?)?/g, function(_, slash, format, key, capture, optional){
|
||||
keys.push({ name: key, optional: !! optional });
|
||||
slash = slash || '';
|
||||
return '' + (optional ? '' : slash) + '(?:' + (optional ? slash : '') + (format || '') + (capture || (format && '([^/.]+?)' || '([^/]+?)')) + ')' + (optional || '');
|
||||
})
|
||||
.replace(/([\/.])/g, '\\$1')
|
||||
.replace(/__plus__/g, '(.+)')
|
||||
.replace(/\*/g, '(.*)');
|
||||
return new RegExp('^' + path + '$', sensitive ? '' : 'i');
|
||||
};
|
||||
|
||||
var addHandler = function(path, fn) {
|
||||
var s = path.split(' ');
|
||||
var name = (s.length == 2) ? s[0] : null;
|
||||
path = (s.length == 2) ? s[1] : s[0];
|
||||
|
||||
if (!map[path]) {
|
||||
map[path] = new Route(path, name);
|
||||
routes.push(map[path]);
|
||||
}
|
||||
map[path].addHandler(fn);
|
||||
};
|
||||
|
||||
var routie = function(path, fn) {
|
||||
if (typeof fn == 'function') {
|
||||
addHandler(path, fn);
|
||||
} else if (typeof path == 'object') {
|
||||
for (var p in path) {
|
||||
addHandler(p, path[p]);
|
||||
}
|
||||
} else if (typeof fn === 'undefined') {
|
||||
routie.navigate(path);
|
||||
}
|
||||
};
|
||||
|
||||
routie.lookup = function(name, obj) {
|
||||
for (var i = 0, c = routes.length; i < c; i++) {
|
||||
var route = routes[i];
|
||||
if (route.name == name) {
|
||||
return route.toURL(obj);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
routie.remove = function(path, fn) {
|
||||
var route = map[path];
|
||||
if (!route)
|
||||
return;
|
||||
route.removeHandler(fn);
|
||||
};
|
||||
|
||||
routie.removeAll = function() {
|
||||
map = {};
|
||||
routes = [];
|
||||
};
|
||||
|
||||
routie.navigate = function(path, options) {
|
||||
options = options || {};
|
||||
var silent = options.silent || false;
|
||||
|
||||
if (silent) {
|
||||
removeListener();
|
||||
}
|
||||
setTimeout(function() {
|
||||
window.location.hash = path;
|
||||
|
||||
if (silent) {
|
||||
setTimeout(function() {
|
||||
addListener();
|
||||
}, 1);
|
||||
}
|
||||
|
||||
}, 1);
|
||||
};
|
||||
|
||||
var getHash = function() {
|
||||
return window.location.hash.substring(1);
|
||||
};
|
||||
|
||||
var checkRoute = function(hash, route) {
|
||||
var params = [];
|
||||
if (route.match(hash, params)) {
|
||||
route.run(params);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
};
|
||||
|
||||
var hashChanged = routie.reload = function() {
|
||||
var hash = getHash();
|
||||
for (var i = 0, c = routes.length; i < c; i++) {
|
||||
var route = routes[i];
|
||||
if (checkRoute(hash, route))
|
||||
return;
|
||||
}
|
||||
};
|
||||
|
||||
var addListener = function() {
|
||||
if (w.addEventListener) {
|
||||
w.addEventListener('hashchange', hashChanged);
|
||||
} else {
|
||||
w.attachEvent('onhashchange', hashChanged);
|
||||
}
|
||||
};
|
||||
|
||||
var removeListener = function() {
|
||||
if (w.removeEventListener) {
|
||||
w.removeEventListener('hashchange', hashChanged);
|
||||
} else {
|
||||
w.detachEvent('onhashchange', hashChanged);
|
||||
}
|
||||
};
|
||||
addListener();
|
||||
|
||||
w.routie = routie;
|
||||
})(window);
|
200
app/js/view.js
Normal file
200
app/js/view.js
Normal file
@@ -0,0 +1,200 @@
|
||||
EJS.Helpers.prototype.date_tag = function(name, value , html_options) {
|
||||
if(! (value instanceof Date))
|
||||
value = new Date()
|
||||
|
||||
var month_names = ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"];
|
||||
var years = [], months = [], days =[];
|
||||
var year = value.getFullYear();
|
||||
var month = value.getMonth();
|
||||
var day = value.getDate();
|
||||
for(var y = year - 15; y < year+15 ; y++)
|
||||
{
|
||||
years.push({value: y, text: y})
|
||||
}
|
||||
for(var m = 0; m < 12; m++)
|
||||
{
|
||||
months.push({value: (m), text: month_names[m]})
|
||||
}
|
||||
for(var d = 0; d < 31; d++)
|
||||
{
|
||||
days.push({value: (d+1), text: (d+1)})
|
||||
}
|
||||
var year_select = this.select_tag(name+'[year]', year, years, {id: name+'[year]'} )
|
||||
var month_select = this.select_tag(name+'[month]', month, months, {id: name+'[month]'})
|
||||
var day_select = this.select_tag(name+'[day]', day, days, {id: name+'[day]'})
|
||||
|
||||
return year_select+month_select+day_select;
|
||||
}
|
||||
|
||||
EJS.Helpers.prototype.form_tag = function(action, html_options) {
|
||||
|
||||
|
||||
html_options = html_options || {};
|
||||
html_options.action = action
|
||||
if(html_options.multipart == true) {
|
||||
html_options.method = 'post';
|
||||
html_options.enctype = 'multipart/form-data';
|
||||
}
|
||||
|
||||
return this.start_tag_for('form', html_options)
|
||||
}
|
||||
|
||||
EJS.Helpers.prototype.form_tag_end = function() { return this.tag_end('form'); }
|
||||
|
||||
EJS.Helpers.prototype.hidden_field_tag = function(name, value, html_options) {
|
||||
return this.input_field_tag(name, value, 'hidden', html_options);
|
||||
}
|
||||
|
||||
EJS.Helpers.prototype.input_field_tag = function(name, value , inputType, html_options) {
|
||||
|
||||
html_options = html_options || {};
|
||||
html_options.id = html_options.id || name;
|
||||
html_options.value = value || '';
|
||||
html_options.type = inputType || 'text';
|
||||
html_options.name = name;
|
||||
|
||||
return this.single_tag_for('input', html_options)
|
||||
}
|
||||
|
||||
EJS.Helpers.prototype.is_current_page = function(url) {
|
||||
return (window.location.href == url || window.location.pathname == url ? true : false);
|
||||
}
|
||||
|
||||
EJS.Helpers.prototype.link_to = function(name, url, html_options) {
|
||||
if(!name) var name = 'null';
|
||||
if(!html_options) var html_options = {}
|
||||
|
||||
if(html_options.confirm){
|
||||
html_options.onclick =
|
||||
" var ret_confirm = confirm(\""+html_options.confirm+"\"); if(!ret_confirm){ return false;} "
|
||||
html_options.confirm = null;
|
||||
}
|
||||
html_options.href=url
|
||||
return this.start_tag_for('a', html_options)+name+ this.tag_end('a');
|
||||
}
|
||||
|
||||
EJS.Helpers.prototype.submit_link_to = function(name, url, html_options){
|
||||
if(!name) var name = 'null';
|
||||
if(!html_options) var html_options = {}
|
||||
html_options.onclick = html_options.onclick || '' ;
|
||||
|
||||
if(html_options.confirm){
|
||||
html_options.onclick =
|
||||
" var ret_confirm = confirm(\""+html_options.confirm+"\"); if(!ret_confirm){ return false;} "
|
||||
html_options.confirm = null;
|
||||
}
|
||||
|
||||
html_options.value = name;
|
||||
html_options.type = 'submit'
|
||||
html_options.onclick=html_options.onclick+
|
||||
(url ? this.url_for(url) : '')+'return false;';
|
||||
//html_options.href='#'+(options ? Routes.url_for(options) : '')
|
||||
return this.start_tag_for('input', html_options)
|
||||
}
|
||||
|
||||
EJS.Helpers.prototype.link_to_if = function(condition, name, url, html_options, post, block) {
|
||||
return this.link_to_unless((condition == false), name, url, html_options, post, block);
|
||||
}
|
||||
|
||||
EJS.Helpers.prototype.link_to_unless = function(condition, name, url, html_options, block) {
|
||||
html_options = html_options || {};
|
||||
if(condition) {
|
||||
if(block && typeof block == 'function') {
|
||||
return block(name, url, html_options, block);
|
||||
} else {
|
||||
return name;
|
||||
}
|
||||
} else
|
||||
return this.link_to(name, url, html_options);
|
||||
}
|
||||
|
||||
EJS.Helpers.prototype.link_to_unless_current = function(name, url, html_options, block) {
|
||||
html_options = html_options || {};
|
||||
return this.link_to_unless(this.is_current_page(url), name, url, html_options, block)
|
||||
}
|
||||
|
||||
|
||||
EJS.Helpers.prototype.password_field_tag = function(name, value, html_options) { return this.input_field_tag(name, value, 'password', html_options); }
|
||||
|
||||
EJS.Helpers.prototype.select_tag = function(name, value, choices, html_options) {
|
||||
html_options = html_options || {};
|
||||
html_options.id = html_options.id || name;
|
||||
html_options.value = value;
|
||||
html_options.name = name;
|
||||
|
||||
var txt = ''
|
||||
txt += this.start_tag_for('select', html_options)
|
||||
|
||||
for(var i = 0; i < choices.length; i++)
|
||||
{
|
||||
var choice = choices[i];
|
||||
var optionOptions = {value: choice.value}
|
||||
if(choice.value == value)
|
||||
optionOptions.selected ='selected'
|
||||
txt += this.start_tag_for('option', optionOptions )+choice.text+this.tag_end('option')
|
||||
}
|
||||
txt += this.tag_end('select');
|
||||
return txt;
|
||||
}
|
||||
|
||||
EJS.Helpers.prototype.single_tag_for = function(tag, html_options) { return this.tag(tag, html_options, '/>');}
|
||||
|
||||
EJS.Helpers.prototype.start_tag_for = function(tag, html_options) { return this.tag(tag, html_options); }
|
||||
|
||||
EJS.Helpers.prototype.submit_tag = function(name, html_options) {
|
||||
html_options = html_options || {};
|
||||
//html_options.name = html_options.id || 'commit';
|
||||
html_options.type = html_options.type || 'submit';
|
||||
html_options.value = name || 'Submit';
|
||||
return this.single_tag_for('input', html_options);
|
||||
}
|
||||
|
||||
EJS.Helpers.prototype.tag = function(tag, html_options, end) {
|
||||
if(!end) var end = '>'
|
||||
var txt = ' '
|
||||
for(var attr in html_options) {
|
||||
if(html_options[attr] != null)
|
||||
var value = html_options[attr].toString();
|
||||
else
|
||||
var value=''
|
||||
if(attr == "Class") // special case because "class" is a reserved word in IE
|
||||
attr = "class";
|
||||
if( value.indexOf("'") != -1 )
|
||||
txt += attr+'=\"'+value+'\" '
|
||||
else
|
||||
txt += attr+"='"+value+"' "
|
||||
}
|
||||
return '<'+tag+txt+end;
|
||||
}
|
||||
|
||||
EJS.Helpers.prototype.tag_end = function(tag) { return '</'+tag+'>'; }
|
||||
|
||||
EJS.Helpers.prototype.text_area_tag = function(name, value, html_options) {
|
||||
html_options = html_options || {};
|
||||
html_options.id = html_options.id || name;
|
||||
html_options.name = html_options.name || name;
|
||||
value = value || ''
|
||||
if(html_options.size) {
|
||||
html_options.cols = html_options.size.split('x')[0]
|
||||
html_options.rows = html_options.size.split('x')[1];
|
||||
delete html_options.size
|
||||
}
|
||||
|
||||
html_options.cols = html_options.cols || 50;
|
||||
html_options.rows = html_options.rows || 4;
|
||||
|
||||
return this.start_tag_for('textarea', html_options)+value+this.tag_end('textarea')
|
||||
}
|
||||
EJS.Helpers.prototype.text_tag = EJS.Helpers.prototype.text_area_tag
|
||||
|
||||
EJS.Helpers.prototype.text_field_tag = function(name, value, html_options) { return this.input_field_tag(name, value, 'text', html_options); }
|
||||
|
||||
EJS.Helpers.prototype.url_for = function(url) {
|
||||
return 'window.location="'+url+'";'
|
||||
}
|
||||
EJS.Helpers.prototype.img_tag = function(image_location, alt, options){
|
||||
options = options || {};
|
||||
options.src = image_location
|
||||
options.alt = alt
|
||||
return this.single_tag_for('img', options)
|
||||
}
|
Reference in New Issue
Block a user