don't save old value for host selector
[qcg-portal.git] / filex / static / filex / humanize / humanize-duration.js
1 // HumanizeDuration.js - http://git.io/j0HgmQ
2
3 (function() {
4
5   var UNITS = {
6     year: 31557600000,
7     month: 2629800000,
8     week: 604800000,
9     day: 86400000,
10     hour: 3600000,
11     minute: 60000,
12     second: 1000,
13     millisecond: 1
14   };
15
16   var languages = {
17     ca: {
18       year: function(c) { return "any" + ((c !== 1) ? "s" : ""); },
19       month: function(c) { return "mes" + ((c !== 1) ? "os" : ""); },
20       week: function(c) { return "setman" + ((c !== 1) ? "es" : "a"); },
21       day: function(c) { return "di" + ((c !== 1) ? "es" : "a"); },
22       hour: function(c) { return "hor" + ((c !== 1) ? "es" : "a"); },
23       minute: function(c) { return "minut" + ((c !== 1) ? "s" : ""); },
24       second: function(c) { return "segon" + ((c !== 1) ? "s" : ""); },
25       millisecond: function(c) { return "milisegon" + ((c !== 1) ? "s" : "" ); }
26     },
27     da: {
28       year: "år",
29       month: function(c) { return "måned" + ((c !== 1) ? "er" : ""); },
30       week: function(c) { return "uge" + ((c !== 1) ? "r" : ""); },
31       day: function(c) { return "dag" + ((c !== 1) ? "e" : ""); },
32       hour: function(c) { return "time" + ((c !== 1) ? "r" : ""); },
33       minute: function(c) { return "minut" + ((c !== 1) ? "ter" : ""); },
34       second: function(c) { return "sekund" + ((c !== 1) ? "er" : ""); },
35       millisecond: function(c) { return "millisekund" + ((c !== 1) ? "er" : ""); }
36     },
37     de: {
38       year: function(c) { return "jahr" + ((c !== 1) ? "e" : ""); },
39       month: function(c) { return "monat" + ((c !== 1) ? "e" : ""); },
40       week: function(c) { return "woche" + ((c !== 1) ? "n" : ""); },
41       day: function(c) { return "tag" + ((c !== 1) ? "e" : ""); },
42       hour: function(c) { return "stunde" + ((c !== 1) ? "n" : ""); },
43       minute: function(c) { return "minute" + ((c !== 1) ? "n" : ""); },
44       second: function(c) { return "sekunde" + ((c !== 1) ? "n" : ""); },
45       millisecond: function(c) { return "millisekunde" + ((c !== 1) ? "n" : ""); }
46     },
47     en: {
48       year: function(c) { return "year" + ((c !== 1) ? "s" : ""); },
49       month: function(c) { return "month" + ((c !== 1) ? "s" : ""); },
50       week: function(c) { return "week" + ((c !== 1) ? "s" : ""); },
51       day: function(c) { return "day" + ((c !== 1) ? "s" : ""); },
52       hour: function(c) { return "hour" + ((c !== 1) ? "s" : ""); },
53       minute: function(c) { return "minute" + ((c !== 1) ? "s" : ""); },
54       second: function(c) { return "second" + ((c !== 1) ? "s" : ""); },
55       millisecond: function(c) { return "millisecond" + ((c !== 1) ? "s" : ""); }
56     },
57     nl: {
58       year: "jaar",
59       month: function(c) { return (c === 1) ? "maand" : "maanden"; },
60       week: function(c) { return (c === 1) ? "week" : "weken"; },
61       day: function(c) { return (c === 1) ? "dag" : "dagen"; },
62       hour: "uur",
63       minute: function(c) { return (c === 1) ? "minuut" : "minuten"; },
64       second: function(c) { return (c === 1) ? "seconde" : "seconden"; },
65       millisecond: function(c) { return (c === 1) ? "milliseconde" : "milliseconden"; }
66     },
67     es: {
68       year: function(c) { return "año" + ((c !== 1) ? "s" : ""); },
69       month: function(c) { return "mes" + ((c !== 1) ? "es" : ""); },
70       week: function(c) { return "semana" + ((c !== 1) ? "s" : ""); },
71       day: function(c) { return "día" + ((c !== 1) ? "s" : ""); },
72       hour: function(c) { return "hora" + ((c !== 1) ? "s" : ""); },
73       minute: function(c) { return "minuto" + ((c !== 1) ? "s" : ""); },
74       second: function(c) { return "segundo" + ((c !== 1) ? "s" : ""); },
75       millisecond: function(c) { return "milisegundo" + ((c !== 1) ? "s" : "" ); }
76     },
77     fr: {
78       year: function(c) { return "an" + ((c !== 1) ? "s" : ""); },
79       month: "mois",
80       week: function(c) { return "semaine" + ((c !== 1) ? "s" : ""); },
81       day: function(c) { return "jour" + ((c !== 1) ? "s" : ""); },
82       hour: function(c) { return "heure" + ((c !== 1) ? "s" : ""); },
83       minute: function(c) { return "minute" + ((c !== 1) ? "s" : ""); },
84       second: function(c) { return "seconde" + ((c !== 1) ? "s" : ""); },
85       millisecond: function(c) { return "milliseconde" + ((c !== 1) ? "s" : ""); }
86     },
87     hu: {
88       year: "év",
89       month: "hónap",
90       week: "hét",
91       day: "nap",
92       hour: "óra",
93       minute: "perc",
94       second: "másodperc",
95       millisecond: "ezredmásodperc"
96     },
97     ja: {
98       year: "年",
99       month: "月",
100       week: "週",
101       day: "日",
102       hour: "時間",
103       minute: "分",
104       second: "秒",
105       millisecond: "ミリ秒"
106     },
107     ko: {
108       year: "년",
109       month: "개월",
110       week: "주일",
111       day: "일",
112       hour: "시간",
113       minute: "분",
114       second: "초",
115       millisecond: "밀리 초"
116     },
117     nob: {
118       year: "år",
119       month: function(c) { return "måned" + ((c !== 1) ? "er" : ""); },
120       week: function(c) { return "uke" + ((c !== 1) ? "r" : ""); },
121       day: function(c) { return "dag" + ((c !== 1) ? "er" : ""); },
122       hour: function(c) { return "time" + ((c !== 1) ? "r" : ""); },
123       minute: function(c) { return "minutt" + ((c !== 1) ? "er" : ""); },
124       second: function(c) { return "sekund" + ((c !== 1) ? "er" : ""); },
125       millisecond: function(c) { return "millisekund" + ((c !== 1) ? "er" : ""); }
126     },
127     pl: {
128       year: function(c) { return ["rok", "roku", "lata", "lat"][getPolishForm(c)]; },
129       month: function(c) { return ["miesiąc", "miesiąca", "miesiące", "miesięcy"][getPolishForm(c)]; },
130       week: function(c) { return ["tydzień", "tygodnia", "tygodnie", "tygodni"][getPolishForm(c)]; },
131       day: function(c) { return ["dzień", "dnia", "dni", "dni"][getPolishForm(c)]; },
132       hour: function(c) { return ["godzina", "godziny", "godziny", "godzin"][getPolishForm(c)]; },
133       minute: function(c) { return ["minuta", "minuty", "minuty", "minut"][getPolishForm(c)]; },
134       second: function(c) { return ["sekunda", "sekundy", "sekundy", "sekund"][getPolishForm(c)]; },
135       millisecond: function(c) { return ["milisekunda", "milisekundy", "milisekundy", "milisekund"][getPolishForm(c)]; }
136     },
137     pt: {
138       year: function(c) { return "ano" + ((c !== 1) ? "s" : ""); },
139       month: function(c) { return (c !== 1) ? "meses" : "mês"; },
140       week: function(c) { return "semana" + ((c !== 1) ? "s" : ""); },
141       day: function(c) { return "dia" + ((c !== 1) ? "s" : ""); },
142       hour: function(c) { return "hora" + ((c !== 1) ? "s" : ""); },
143       minute: function(c) { return "minuto" + ((c !== 1) ? "s" : ""); },
144       second: function(c) { return "segundo" + ((c !== 1) ? "s" : ""); },
145       millisecond: function(c) { return "milissegundo" + ((c !== 1) ? "s" : ""); }
146     },
147     ru: {
148       year: function(c) { return ["лет", "год", "года"][getRussianForm(c)]; },
149       month: function(c) { return ["месяцев", "месяц", "месяца"][getRussianForm(c)]; },
150       week: function(c) { return ["недель", "неделя", "недели"][getRussianForm(c)]; },
151       day: function(c) { return ["дней", "день", "дня"][getRussianForm(c)]; },
152       hour: function(c) { return ["часов", "час", "часа"][getRussianForm(c)]; },
153       minute: function(c) { return ["минут", "минута", "минуты"][getRussianForm(c)]; },
154       second: function(c) { return ["секунд", "секунда", "секунды"][getRussianForm(c)]; },
155       millisecond: function(c) { return ["миллисекунд", "миллисекунда", "миллисекунды"][getRussianForm(c)]; }
156     },
157     sv: {
158       year: "år",
159       month: function(c) { return "månad" + ((c !== 1) ? "er" : ""); },
160       week: function(c) { return "veck" + ((c !== 1) ? "or" : "a"); },
161       day: function(c) { return "dag" + ((c !== 1) ? "ar" : ""); },
162       hour: function(c) { return "timm" + ((c !== 1) ? "ar" : "e"); },
163       minute: function(c) { return "minut" + ((c !== 1) ? "er" : ""); },
164       second: function(c) { return "sekund" + ((c !== 1) ? "er" : ""); },
165       millisecond: function(c) { return "millisekund" + ((c !== 1) ? "er" : ""); }
166     },
167     tr: {
168       year: "yıl",
169       month: "ay",
170       week: "hafta",
171       day: "gün",
172       hour: "saat",
173       minute: "dakika",
174       second: "saniye",
175       millisecond: "milisaniye"
176     },
177     "zh-CN": {
178       year: "年",
179       month: "个月",
180       week: "周",
181       day: "天",
182       hour: "小时",
183       minute: "分钟",
184       second: "秒",
185       millisecond: "毫秒"
186     },
187     "zh-TW": {
188       year: "年",
189       month: "個月",
190       week: "周",
191       day: "天",
192       hour: "小時",
193       minute: "分鐘",
194       second: "秒",
195       millisecond: "毫秒"
196     }
197   };
198
199   // You can create a humanizer, which returns a function with defaults
200   // parameters.
201   function humanizer(passedOptions) {
202
203     var result = function humanizer(ms, humanizerOptions) {
204       var options = extend({}, result, humanizerOptions || {});
205       return doHumanization(ms, options);
206     };
207
208     return extend(result, {
209       language: "en",
210       delimiter: ", ",
211       spacer: " ",
212       units: ["year", "month", "week", "day", "hour", "minute", "second"],
213       languages: {},
214       halfUnit: true,
215       round: false
216     }, passedOptions);
217
218   }
219
220   // The main function is just a wrapper around a default humanizer.
221   var defaultHumanizer = humanizer({});
222   function humanizeDuration() {
223     return defaultHumanizer.apply(defaultHumanizer, arguments);
224   }
225
226   // doHumanization does the bulk of the work.
227   function doHumanization(ms, options) {
228
229     // Make sure we have a positive number.
230     // Has the nice sideffect of turning Number objects into primitives.
231     ms = Math.abs(ms);
232
233     if (ms === 0) {
234       return "0";
235     }
236
237     var dictionary = options.languages[options.language] || languages[options.language];
238     if (!dictionary) {
239       throw new Error("No language " + dictionary + ".");
240     }
241
242     var result = [];
243
244     // Start at the top and keep removing units, bit by bit.
245     var unitName, unitMS, unitCount, mightBeHalfUnit;
246     for (var i = 0, len = options.units.length; i < len; i ++) {
247
248       unitName = options.units[i];
249       if (unitName[unitName.length - 1] === "s") { // strip plurals
250         unitName = unitName.substring(0, unitName.length - 1);
251       }
252       unitMS = UNITS[unitName];
253
254       // If it's a half-unit interval, we're done.
255       if (result.length === 0 && options.halfUnit) {
256         mightBeHalfUnit = (ms / unitMS) * 2;
257         if (mightBeHalfUnit === Math.floor(mightBeHalfUnit)) {
258           return render(mightBeHalfUnit / 2, unitName, dictionary, options.spacer);
259         }
260       }
261
262       // What's the number of full units we can fit?
263       if ((i + 1) === len) {
264         unitCount = ms / unitMS;
265         if (options.round) {
266           unitCount = Math.round(unitCount);
267         }
268       } else {
269         unitCount = Math.floor(ms / unitMS);
270       }
271
272       // Add the string.
273       if (unitCount) {
274         result.push(render(unitCount, unitName, dictionary, options.spacer));
275       }
276
277       // Remove what we just figured out.
278       ms -= unitCount * unitMS;
279
280     }
281
282     return result.join(options.delimiter);
283
284   }
285
286   function render(count, type, dictionary, spacer) {
287     var dictionaryValue = dictionary[type];
288     var word;
289     if (typeof dictionaryValue === "function") {
290       word = dictionaryValue(count);
291     } else {
292       word = dictionaryValue;
293     }
294     return count + spacer + word;
295   }
296
297   function extend(destination) {
298     var source;
299     for (var i = 1; i < arguments.length; i ++) {
300       source = arguments[i];
301       for (var prop in source) {
302         destination[prop] = source[prop];
303       }
304     }
305     return destination;
306   }
307
308   // Internal helper function for Polish language.
309   function getPolishForm(c) {
310     if (c === 1) {
311       return 0;
312     } else if (Math.floor(c) !== c) {
313       return 1;
314     } else if (2 <= c % 10 && c % 10 <= 4 && !(10 < c % 100 && c % 100 < 20)) {
315       return 2;
316     } else {
317       return 3;
318     }
319   }
320
321   // Internal helper function for Russian language.
322   function getRussianForm(c) {
323     if (Math.floor(c) !== c) {
324       return 2;
325     } else if (c === 0 || (c >= 5 && c <= 20) || (c % 10 >= 5 && c % 10 <= 9) || (c % 10 === 0)) {
326       return 0;
327     } else if (c === 1 || c % 10 === 1) {
328       return 1;
329     } else if (c > 1) {
330       return 2;
331     } else {
332       return 0;
333     }
334   }
335
336   humanizeDuration.humanizer = humanizer;
337   if (typeof define === "function" && define.amd) {
338     define(function() {
339       return humanizeDuration;
340     });
341   } else if (typeof module !== "undefined" && module.exports) {
342     module.exports = humanizeDuration;
343   } else {
344     this.humanizeDuration = humanizeDuration;
345   }
346
347 })();