Commit 665aeee0 authored by Eirik Alvær's avatar Eirik Alvær
Browse files

Added translation using i18next.js.

parent 29cb8f9b
......@@ -34,13 +34,15 @@
"http://cdnjs.cloudflare.com/ajax/libs/backbone.js/1.0.0/backbone-min.js",
"http://cdnjs.cloudflare.com/ajax/libs/handlebars.js/1.0.0/handlebars.min.js",
"http://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/2.3.2/js/bootstrap.min.js",
"libraries/i18next-1.6.3.js",
// Our own scripts
"js/init.js",
"js/common.js",
"js/model.js",
"js/templates-loader.js",
"js/metadata-maker.js",
"js/controller.js"
);
);
</script>
</body>
......
......@@ -3,10 +3,6 @@ function loadFromRestServer(urlEnding, successFunction) {
robustAjax(url, "json", true, successFunction);
}
function loadSyncFromRestServer(urlEnding) {
return syncAjax(Model.restServerURL + "/" + urlEnding, "json");
}
function getJSON(urlString, successFunction) {
robustAjax(urlString, "json", true, successFunction);
}
......@@ -42,5 +38,10 @@ function robustAjax(urlString, dataType, isAsync, successFunction) {
}
function getTranslation(text) {
return text;
if (text == null) {
return null;
}
else {
return i18n.t(text);
}
}
\ No newline at end of file
i18n.init({
fallbackLng: 'en',
debug: true,
getAsync: false,
resGetPath: 'locales/__ns__.__lng__.json'
});
Handlebars.registerHelper('t', function(i18n_key) {
var result = i18n.t(i18n_key);
return new Handlebars.SafeString(result);
});
\ No newline at end of file
......@@ -31,7 +31,7 @@ function getMetadataHtml(metadataSelection, metadata) {
function getHeadingHtml(metadataSelection, metadata) {
var templateObject = {}
templateObject.heading = metadataSelection.heading;
templateObject.heading = getTranslation(metadataSelection.heading);
return metadataHeadingTemplate(templateObject);
}
......@@ -52,7 +52,7 @@ function getLabel(label, field) {
if (label == "--default--") {
var fields = field.split('.');
var lastField = fields[fields.length-1];
return Model.metadataTranslation[lastField];
return getTranslation("metadataTranslation." + lastField);
}
else {
return getTranslation(label);
......
......@@ -8,7 +8,7 @@ var Model = {
"correlation" : null,
"backRoutes" : [],
"currentAnalysisType" : "", // tabulation / regression / correlation
"currentVariableStore" : "" // rowVariableIds / columnVariableIds /measureVariableId / dependentVariableId / independentVariableIds
"currentVariableStore" : "" // rowVariableIds / columnVariableIds / measureVariableId / dependentVariableId / independentVariableIds
},
"urlObjectSaved" : false,
......@@ -62,8 +62,6 @@ Model.studyMetadataSelection = getSyncJSON("/metadata-selection/study-metadata-s
Model.variableMetadataSelection = getSyncJSON("/metadata-selection/variable-metadata-selection.json");
Model.metadataTranslation = loadSyncFromRestServer("metadata-translation/en").metadataTranslation;
function initNewTabulation() {
Model.urlObject.tabulation = new Tabulation();
Model.urlObject.currentAnalysisType = "tabulation";
......
// i18next, v1.6.3
// Copyright (c)2013 Jan Mühlemann (jamuhl).
// Distributed under MIT license
// http://i18next.com
(function() {
// add indexOf to non ECMA-262 standard compliant browsers
if (!Array.prototype.indexOf) {
Array.prototype.indexOf = function (searchElement /*, fromIndex */ ) {
"use strict";
if (this == null) {
throw new TypeError();
}
var t = Object(this);
var len = t.length >>> 0;
if (len === 0) {
return -1;
}
var n = 0;
if (arguments.length > 0) {
n = Number(arguments[1]);
if (n != n) { // shortcut for verifying if it's NaN
n = 0;
} else if (n != 0 && n != Infinity && n != -Infinity) {
n = (n > 0 || -1) * Math.floor(Math.abs(n));
}
}
if (n >= len) {
return -1;
}
var k = n >= 0 ? n : Math.max(len - Math.abs(n), 0);
for (; k < len; k++) {
if (k in t && t[k] === searchElement) {
return k;
}
}
return -1;
}
}
// add lastIndexOf to non ECMA-262 standard compliant browsers
if (!Array.prototype.lastIndexOf) {
Array.prototype.lastIndexOf = function(searchElement /*, fromIndex*/) {
"use strict";
if (this == null) {
throw new TypeError();
}
var t = Object(this);
var len = t.length >>> 0;
if (len === 0) {
return -1;
}
var n = len;
if (arguments.length > 1) {
n = Number(arguments[1]);
if (n != n) {
n = 0;
} else if (n != 0 && n != (1 / 0) && n != -(1 / 0)) {
n = (n > 0 || -1) * Math.floor(Math.abs(n));
}
}
var k = n >= 0 ? Math.min(n, len - 1) : len - Math.abs(n);
for (; k >= 0; k--) {
if (k in t && t[k] === searchElement) {
return k;
}
}
return -1;
};
}
var root = this
, $ = root.jQuery || root.Zepto
, i18n = {}
, resStore = {}
, currentLng
, replacementCounter = 0
, languages = [];
// Export the i18next object for **CommonJS**.
// If we're not in CommonJS, add `i18n` to the
// global object or to jquery.
if (typeof module !== 'undefined' && module.exports) {
module.exports = i18n;
} else {
if ($) {
$.i18n = $.i18n || i18n;
}
root.i18n = root.i18n || i18n;
}
// defaults
var o = {
lng: undefined,
load: 'all',
preload: [],
lowerCaseLng: false,
returnObjectTrees: false,
fallbackLng: 'dev',
fallbackNS: [],
detectLngQS: 'setLng',
ns: 'translation',
fallbackOnNull: true,
fallbackToDefaultNS: false,
nsseparator: ':',
keyseparator: '.',
selectorAttr: 'data-i18n',
debug: false,
resGetPath: 'locales/__lng__/__ns__.json',
resPostPath: 'locales/add/__lng__/__ns__',
getAsync: true,
postAsync: true,
resStore: undefined,
useLocalStorage: false,
localStorageExpirationTime: 7*24*60*60*1000,
dynamicLoad: false,
sendMissing: false,
sendMissingTo: 'fallback', // current | all
sendType: 'POST',
interpolationPrefix: '__',
interpolationSuffix: '__',
reusePrefix: '$t(',
reuseSuffix: ')',
pluralSuffix: '_plural',
pluralNotFound: ['plural_not_found', Math.random()].join(''),
contextNotFound: ['context_not_found', Math.random()].join(''),
escapeInterpolation: false,
setJqueryExt: true,
defaultValueFromContent: true,
useDataAttrOptions: false,
cookieExpirationTime: undefined,
useCookie: true,
cookieName: 'i18next',
postProcess: undefined,
parseMissingKey: undefined
};
function _extend(target, source) {
if (!source || typeof source === 'function') {
return target;
}
for (var attr in source) { target[attr] = source[attr]; }
return target;
}
function _each(object, callback, args) {
var name, i = 0,
length = object.length,
isObj = length === undefined || typeof object === "function";
if (args) {
if (isObj) {
for (name in object) {
if (callback.apply(object[name], args) === false) {
break;
}
}
} else {
for ( ; i < length; ) {
if (callback.apply(object[i++], args) === false) {
break;
}
}
}
// A special, fast, case for the most common use of each
} else {
if (isObj) {
for (name in object) {
if (callback.call(object[name], name, object[name]) === false) {
break;
}
}
} else {
for ( ; i < length; ) {
if (callback.call(object[i], i, object[i++]) === false) {
break;
}
}
}
}
return object;
}
var _entityMap = {
"&": "&amp;",
"<": "&lt;",
">": "&gt;",
'"': '&quot;',
"'": '&#39;',
"/": '&#x2F;'
};
function _escape(data) {
if (typeof data === 'string') {
return data.replace(/[&<>"'\/]/g, function (s) {
return _entityMap[s];
});
}else{
return data;
}
}
function _ajax(options) {
// v0.5.0 of https://github.com/goloroden/http.js
var getXhr = function (callback) {
// Use the native XHR object if the browser supports it.
if (window.XMLHttpRequest) {
return callback(null, new XMLHttpRequest());
} else if (window.ActiveXObject) {
// In Internet Explorer check for ActiveX versions of the XHR object.
try {
return callback(null, new ActiveXObject("Msxml2.XMLHTTP"));
} catch (e) {
return callback(null, new ActiveXObject("Microsoft.XMLHTTP"));
}
}
// If no XHR support was found, throw an error.
return callback(new Error());
};
var encodeUsingUrlEncoding = function (data) {
if(typeof data === 'string') {
return data;
}
var result = [];
for(var dataItem in data) {
if(data.hasOwnProperty(dataItem)) {
result.push(encodeURIComponent(dataItem) + '=' + encodeURIComponent(data[dataItem]));
}
}
return result.join('&');
};
var utf8 = function (text) {
text = text.replace(/\r\n/g, '\n');
var result = '';
for(var i = 0; i < text.length; i++) {
var c = text.charCodeAt(i);
if(c < 128) {
result += String.fromCharCode(c);
} else if((c > 127) && (c < 2048)) {
result += String.fromCharCode((c >> 6) | 192);
result += String.fromCharCode((c & 63) | 128);
} else {
result += String.fromCharCode((c >> 12) | 224);
result += String.fromCharCode(((c >> 6) & 63) | 128);
result += String.fromCharCode((c & 63) | 128);
}
}
return result;
};
var base64 = function (text) {
var keyStr = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=';
text = utf8(text);
var result = '',
chr1, chr2, chr3,
enc1, enc2, enc3, enc4,
i = 0;
do {
chr1 = text.charCodeAt(i++);
chr2 = text.charCodeAt(i++);
chr3 = text.charCodeAt(i++);
enc1 = chr1 >> 2;
enc2 = ((chr1 & 3) << 4) | (chr2 >> 4);
enc3 = ((chr2 & 15) << 2) | (chr3 >> 6);
enc4 = chr3 & 63;
if(isNaN(chr2)) {
enc3 = enc4 = 64;
} else if(isNaN(chr3)) {
enc4 = 64;
}
result +=
keyStr.charAt(enc1) +
keyStr.charAt(enc2) +
keyStr.charAt(enc3) +
keyStr.charAt(enc4);
chr1 = chr2 = chr3 = '';
enc1 = enc2 = enc3 = enc4 = '';
} while(i < text.length);
return result;
};
var mergeHeaders = function () {
// Use the first header object as base.
var result = arguments[0];
// Iterate through the remaining header objects and add them.
for(var i = 1; i < arguments.length; i++) {
var currentHeaders = arguments[i];
for(var header in currentHeaders) {
if(currentHeaders.hasOwnProperty(header)) {
result[header] = currentHeaders[header];
}
}
}
// Return the merged headers.
return result;
};
var ajax = function (method, url, options, callback) {
// Adjust parameters.
if(typeof options === 'function') {
callback = options;
options = {};
}
// Set default parameter values.
options.cache = options.cache || false;
options.data = options.data || {};
options.headers = options.headers || {};
options.jsonp = options.jsonp || false;
options.async = options.async === undefined ? true : options.async;
// Merge the various header objects.
var headers = mergeHeaders({
'accept': '*/*',
'content-type': 'application/x-www-form-urlencoded;charset=UTF-8'
}, ajax.headers, options.headers);
// Encode the data according to the content-type.
var payload;
if (headers['content-type'] === 'application/json') {
payload = JSON.stringify(options.data);
} else {
payload = encodeUsingUrlEncoding(options.data);
}
// Specially prepare GET requests: Setup the query string, handle caching and make a JSONP call
// if neccessary.
if(method === 'GET') {
// Setup the query string.
var queryString = [];
if(payload) {
queryString.push(payload);
payload = null;
}
// Handle caching.
if(!options.cache) {
queryString.push('_=' + (new Date()).getTime());
}
// If neccessary prepare the query string for a JSONP call.
if(options.jsonp) {
queryString.push('callback=' + options.jsonp);
queryString.push('jsonp=' + options.jsonp);
}
// Merge the query string and attach it to the url.
queryString = queryString.join('&');
if (queryString.length > 1) {
if (url.indexOf('?') > -1) {
url += '&' + queryString;
} else {
url += '?' + queryString;
}
}
// Make a JSONP call if neccessary.
if(options.jsonp) {
var head = document.getElementsByTagName('head')[0];
var script = document.createElement('script');
script.type = 'text/javascript';
script.src = url;
head.appendChild(script);
return;
}
}
// Since we got here, it is no JSONP request, so make a normal XHR request.
getXhr(function (err, xhr) {
if(err) return callback(err);
// Open the request.
xhr.open(method, url, options.async);
// Set the request headers.
for(var header in headers) {
if(headers.hasOwnProperty(header)) {
xhr.setRequestHeader(header, headers[header]);
}
}
// Handle the request events.
xhr.onreadystatechange = function () {
if(xhr.readyState === 4) {
var data = xhr.responseText || '';
// If no callback is given, return.
if(!callback) {
return;
}
// Return an object that provides access to the data as text and JSON.
callback(xhr.status, {
text: function () {
return data;
},
json: function () {
return JSON.parse(data);
}
});
}
};
// Actually send the XHR request.
xhr.send(payload);
});
};
// Define the external interface.
var http = {
authBasic: function (username, password) {
ajax.headers['Authorization'] = 'Basic ' + base64(username + ':' + password);
},
connect: function (url, options, callback) {
return ajax('CONNECT', url, options, callback);
},
del: function (url, options, callback) {
return ajax('DELETE', url, options, callback);
},
get: function (url, options, callback) {
return ajax('GET', url, options, callback);
},
head: function (url, options, callback) {
return ajax('HEAD', url, options, callback);
},
headers: function (headers) {
ajax.headers = headers || {};
},
isAllowed: function (url, verb, callback) {
this.options(url, function (status, data) {
callback(data.text().indexOf(verb) !== -1);
});
},
options: function (url, options, callback) {
return ajax('OPTIONS', url, options, callback);
},
patch: function (url, options, callback) {
return ajax('PATCH', url, options, callback);
},
post: function (url, options, callback) {
return ajax('POST', url, options, callback);
},
put: function (url, options, callback) {
return ajax('PUT', url, options, callback);
},
trace: function (url, options, callback) {
return ajax('TRACE', url, options, callback);
}
};
var methode = options.type ? options.type.toLowerCase() : 'get';
http[methode](options.url, options, function (status, data) {
if (status === 200) {
options.success(data.json(), status, null);
} else {
options.error(data.text(), status, null);
}
});
}
var _cookie = {
create: function(name,value,minutes) {
var expires;
if (minutes) {
var date = new Date();
date.setTime(date.getTime()+(minutes*60*1000));
expires = "; expires="+date.toGMTString();
}
else expires = "";
document.cookie = name+"="+value+expires+"; path=/";
},