UNPKG

webmaker-i18n

Version:

Webmaker Localization Components for node.js and the browser

168 lines (146 loc) 5.14 kB
(function(global, ignoreRequireJS, factory) { // AMD. Register as an anonymous module. Also deal with the case // that we've been told to force localized on the global (e.g., // in cases where require.js might exist in a page and we want to // ignore it and use the global instead). if (typeof define === 'function' && define.amd && !ignoreRequireJS) { define(factory); } // Expose a global instead else { global.Localized = factory(); } }(this, this.__LOCALIZED_IGNORE_REQUIREJS, function() { var _strings, _readyCallbacks = [], _requestedStrings = false; function fireReadyCallbacks() { // Fire all ready callbacks we have queued up. while(_readyCallbacks.length) { (_readyCallbacks.pop())(); } } function ready(data) { function domReady() { // If the DOM isn't ready yet, repeat when it is if ( document.readyState !== "complete" ) { document.onreadystatechange = domReady; return; } document.onreadystatechange = null; _strings = data; fireReadyCallbacks(); } domReady(); } // Get the current lang from the document's HTML element, which the // server set when the page was first rendered. This saves us having // to pass extra locale info around on the URL. function getCurrentLang() { var html = document.querySelector( "html" ); return html && html.lang ? html.lang : "en-US"; } return { /** * gets the localized string for a given key */ get: function(key) { if ( !_strings ) { console.error( "[webmaker-i18n] Error: string catalog not found." ); return ""; } return ( _strings[ key ] || "" ); }, /** * Convert the given language name into Moment.js supported Language name * * lang: 'en-US' return: 'en' * lang: 'en-CA' return: 'en-ca' * lang: 'th-TH' return: 'th' **/ langToMomentJSLang: function(lang) { /* The list of moment.js supported languages * Extracted from http://momentjs.com/downloads/moment-with-langs.js */ var momentLangMap = ['en', 'ar-ma', 'ar', 'bg', 'br', 'bs', 'ca', 'cs', 'cv', 'cy', 'da', 'de', 'el', 'en-au', 'en-ca', 'en-gb', 'eo', 'es', 'et', 'eu', 'fa', 'fi', 'fo', 'fr-ca', 'fr', 'gl', 'he', 'hi', 'hr', 'hu', 'id', 'is', 'it', 'ja', 'ka', 'ko', "lt", 'lv', 'ml', 'mr', 'ms-my', 'nb', 'ne', 'nl', 'nn', 'pl', 'pt-br', 'pt', 'ro', 'ru', 'sk', 'sl', 'sq', 'sv', 'th', 'tl-ph', 'tr', 'tzm-la', 'tzm', 'uk', 'uz', 'vn', 'zh-cn', 'zh-tw']; lang = lang.toLowerCase(); var newLang = lang.substr(0,2); if (momentLangMap.indexOf(lang) !== -1) { return lang; } else if (momentLangMap.indexOf(newLang) !== -1) { return newLang; } return 'en'; }, /** * gets the current lang used for the given page, or en-US by default. */ getCurrentLang: getCurrentLang, /** * initializes the strings locally (i.e., downloads if not already downloaded) and * queues a callback to be fired when the DOM + strings are ready. It is safe to * call ready() multiple times. For cache busting, pass noCache=true on the options arg. */ ready: function(options, callback) { var _callback; // Allow calling ready with or without options. if (typeof options === 'function') { _callback = options; options = {}; } else { _callback = callback || function(){}; } var noCache = !!options.noCache, url = options.url || '/strings'; // If given an absolute url (starting in http), we don't process it. // Otherwise we fix it up to include the current lang from <html lang="..."> if (url.indexOf( 'http' ) !== 0) { url = url.replace(/^\/?/, '/').replace(/\/?$/, '/'); url = url + getCurrentLang(); } // Add cache busting if requested. url = url + (noCache ? '?bust=' + Date.now() : ''); if (!_requestedStrings) { _requestedStrings = true; _readyCallbacks.push(_callback); var xhr = new XMLHttpRequest(); xhr.open('GET', url, true); xhr.onreadystatechange = function(){ if (this.readyState !== 4) { return; } if (xhr.status !== 200) { console.error("Localized Error: HTTP error " + xhr.status); return; } try { ready(JSON.parse(this.responseText)); } catch (err) { console.error("Localized Error: " + err); } }; xhr.send(null); } if (this.isReady()) { fireReadyCallbacks(); } }, /** * returns true if the localized strings have been loaded and can be used. */ isReady: function() { return !!_strings; } }; }));