Merge "Added release notes for 'ContentHandler::runLegacyHooks' removal"
[mediawiki.git] / resources / lib / jquery.i18n / src / jquery.i18n.language.js
blobe596fbc83ebba58fe4337233c667d9c3f94c0e34
1 /*global pluralRuleParser */
2 ( function ( $ ) {
3         'use strict';
5         var language = {
6                 // CLDR plural rules generated using
7                 // libs/CLDRPluralRuleParser/tools/PluralXML2JSON.html
8                 pluralRules: {
9                         ak: {
10                                 one: 'n = 0..1'
11                         },
12                         am: {
13                                 one: 'i = 0 or n = 1'
14                         },
15                         ar: {
16                                 zero: 'n = 0',
17                                 one: 'n = 1',
18                                 two: 'n = 2',
19                                 few: 'n % 100 = 3..10',
20                                 many: 'n % 100 = 11..99'
21                         },
22                         be: {
23                                 one: 'n % 10 = 1 and n % 100 != 11',
24                                 few: 'n % 10 = 2..4 and n % 100 != 12..14',
25                                 many: 'n % 10 = 0 or n % 10 = 5..9 or n % 100 = 11..14'
26                         },
27                         bh: {
28                                 one: 'n = 0..1'
29                         },
30                         bn: {
31                                 one: 'i = 0 or n = 1'
32                         },
33                         br: {
34                                 one: 'n % 10 = 1 and n % 100 != 11,71,91',
35                                 two: 'n % 10 = 2 and n % 100 != 12,72,92',
36                                 few: 'n % 10 = 3..4,9 and n % 100 != 10..19,70..79,90..99',
37                                 many: 'n != 0 and n % 1000000 = 0'
38                         },
39                         bs: {
40                                 one: 'v = 0 and i % 10 = 1 and i % 100 != 11 or f % 10 = 1 and f % 100 != 11',
41                                 few: 'v = 0 and i % 10 = 2..4 and i % 100 != 12..14 or f % 10 = 2..4 and f % 100 != 12..14'
42                         },
43                         cs: {
44                                 one: 'i = 1 and v = 0',
45                                 few: 'i = 2..4 and v = 0',
46                                 many: 'v != 0'
47                         },
48                         cy: {
49                                 zero: 'n = 0',
50                                 one: 'n = 1',
51                                 two: 'n = 2',
52                                 few: 'n = 3',
53                                 many: 'n = 6'
54                         },
55                         da: {
56                                 one: 'n = 1 or t != 0 and i = 0,1'
57                         },
58                         fa: {
59                                 one: 'i = 0 or n = 1'
60                         },
61                         ff: {
62                                 one: 'i = 0,1'
63                         },
64                         fil: {
65                                 one: 'i = 0..1 and v = 0'
66                         },
67                         fr: {
68                                 one: 'i = 0,1'
69                         },
70                         ga: {
71                                 one: 'n = 1',
72                                 two: 'n = 2',
73                                 few: 'n = 3..6',
74                                 many: 'n = 7..10'
75                         },
76                         gd: {
77                                 one: 'n = 1,11',
78                                 two: 'n = 2,12',
79                                 few: 'n = 3..10,13..19'
80                         },
81                         gu: {
82                                 one: 'i = 0 or n = 1'
83                         },
84                         guw: {
85                                 one: 'n = 0..1'
86                         },
87                         gv: {
88                                 one: 'n % 10 = 1',
89                                 two: 'n % 10 = 2',
90                                 few: 'n % 100 = 0,20,40,60'
91                         },
92                         he: {
93                                 one: 'i = 1 and v = 0',
94                                 two: 'i = 2 and v = 0',
95                                 many: 'v = 0 and n != 0..10 and n % 10 = 0'
96                         },
97                         hi: {
98                                 one: 'i = 0 or n = 1'
99                         },
100                         hr: {
101                                 one: 'v = 0 and i % 10 = 1 and i % 100 != 11 or f % 10 = 1 and f % 100 != 11',
102                                 few: 'v = 0 and i % 10 = 2..4 and i % 100 != 12..14 or f % 10 = 2..4 and f % 100 != 12..14'
103                         },
104                         hy: {
105                                 one: 'i = 0,1'
106                         },
107                         is: {
108                                 one: 't = 0 and i % 10 = 1 and i % 100 != 11 or t != 0'
109                         },
110                         iu: {
111                                 one: 'n = 1',
112                                 two: 'n = 2'
113                         },
114                         iw: {
115                                 one: 'i = 1 and v = 0',
116                                 two: 'i = 2 and v = 0',
117                                 many: 'v = 0 and n != 0..10 and n % 10 = 0'
118                         },
119                         kab: {
120                                 one: 'i = 0,1'
121                         },
122                         kn: {
123                                 one: 'i = 0 or n = 1'
124                         },
125                         kw: {
126                                 one: 'n = 1',
127                                 two: 'n = 2'
128                         },
129                         lag: {
130                                 zero: 'n = 0',
131                                 one: 'i = 0,1 and n != 0'
132                         },
133                         ln: {
134                                 one: 'n = 0..1'
135                         },
136                         lt: {
137                                 one: 'n % 10 = 1 and n % 100 != 11..19',
138                                 few: 'n % 10 = 2..9 and n % 100 != 11..19',
139                                 many: 'f != 0'
140                         },
141                         lv: {
142                                 zero: 'n % 10 = 0 or n % 100 = 11..19 or v = 2 and f % 100 = 11..19',
143                                 one: 'n % 10 = 1 and n % 100 != 11 or v = 2 and f % 10 = 1 and f % 100 != 11 or v != 2 and f % 10 = 1'
144                         },
145                         mg: {
146                                 one: 'n = 0..1'
147                         },
148                         mk: {
149                                 one: 'v = 0 and i % 10 = 1 or f % 10 = 1'
150                         },
151                         mo: {
152                                 one: 'i = 1 and v = 0',
153                                 few: 'v != 0 or n = 0 or n != 1 and n % 100 = 1..19'
154                         },
155                         mr: {
156                                 one: 'i = 0 or n = 1'
157                         },
158                         mt: {
159                                 one: 'n = 1',
160                                 few: 'n = 0 or n % 100 = 2..10',
161                                 many: 'n % 100 = 11..19'
162                         },
163                         naq: {
164                                 one: 'n = 1',
165                                 two: 'n = 2'
166                         },
167                         nso: {
168                                 one: 'n = 0..1'
169                         },
170                         pa: {
171                                 one: 'n = 0..1'
172                         },
173                         pl: {
174                                 one: 'i = 1 and v = 0',
175                                 few: 'v = 0 and i % 10 = 2..4 and i % 100 != 12..14',
176                                 many: 'v = 0 and i != 1 and i % 10 = 0..1 or v = 0 and i % 10 = 5..9 or v = 0 and i % 100 = 12..14'
177                         },
178                         pt: {
179                                 one: 'i = 1 and v = 0 or i = 0 and t = 1'
180                         },
181                         // jscs:disable requireCamelCaseOrUpperCaseIdentifiers
182                         pt_PT: {
183                                 one: 'n = 1 and v = 0'
184                         },
185                         // jscs:enable requireCamelCaseOrUpperCaseIdentifiers
186                         ro: {
187                                 one: 'i = 1 and v = 0',
188                                 few: 'v != 0 or n = 0 or n != 1 and n % 100 = 1..19'
189                         },
190                         ru: {
191                                 one: 'v = 0 and i % 10 = 1 and i % 100 != 11',
192                                 many: 'v = 0 and i % 10 = 0 or v = 0 and i % 10 = 5..9 or v = 0 and i % 100 = 11..14'
193                         },
194                         se: {
195                                 one: 'n = 1',
196                                 two: 'n = 2'
197                         },
198                         sh: {
199                                 one: 'v = 0 and i % 10 = 1 and i % 100 != 11 or f % 10 = 1 and f % 100 != 11',
200                                 few: 'v = 0 and i % 10 = 2..4 and i % 100 != 12..14 or f % 10 = 2..4 and f % 100 != 12..14'
201                         },
202                         shi: {
203                                 one: 'i = 0 or n = 1',
204                                 few: 'n = 2..10'
205                         },
206                         si: {
207                                 one: 'n = 0,1 or i = 0 and f = 1'
208                         },
209                         sk: {
210                                 one: 'i = 1 and v = 0',
211                                 few: 'i = 2..4 and v = 0',
212                                 many: 'v != 0'
213                         },
214                         sl: {
215                                 one: 'v = 0 and i % 100 = 1',
216                                 two: 'v = 0 and i % 100 = 2',
217                                 few: 'v = 0 and i % 100 = 3..4 or v != 0'
218                         },
219                         sma: {
220                                 one: 'n = 1',
221                                 two: 'n = 2'
222                         },
223                         smi: {
224                                 one: 'n = 1',
225                                 two: 'n = 2'
226                         },
227                         smj: {
228                                 one: 'n = 1',
229                                 two: 'n = 2'
230                         },
231                         smn: {
232                                 one: 'n = 1',
233                                 two: 'n = 2'
234                         },
235                         sms: {
236                                 one: 'n = 1',
237                                 two: 'n = 2'
238                         },
239                         sr: {
240                                 one: 'v = 0 and i % 10 = 1 and i % 100 != 11 or f % 10 = 1 and f % 100 != 11',
241                                 few: 'v = 0 and i % 10 = 2..4 and i % 100 != 12..14 or f % 10 = 2..4 and f % 100 != 12..14'
242                         },
243                         ti: {
244                                 one: 'n = 0..1'
245                         },
246                         tl: {
247                                 one: 'i = 0..1 and v = 0'
248                         },
249                         tzm: {
250                                 one: 'n = 0..1 or n = 11..99'
251                         },
252                         uk: {
253                                 one: 'v = 0 and i % 10 = 1 and i % 100 != 11',
254                                 few: 'v = 0 and i % 10 = 2..4 and i % 100 != 12..14',
255                                 many: 'v = 0 and i % 10 = 0 or v = 0 and i % 10 = 5..9 or v = 0 and i % 100 = 11..14'
256                         },
257                         wa: {
258                                 one: 'n = 0..1'
259                         },
260                         zu: {
261                                 one: 'i = 0 or n = 1'
262                         }
263                 },
265                 /**
266                  * Plural form transformations, needed for some languages.
267                  *
268                  * @param count
269                  *            integer Non-localized quantifier
270                  * @param forms
271                  *            array List of plural forms
272                  * @return string Correct form for quantifier in this language
273                  */
274                 convertPlural: function ( count, forms ) {
275                         var pluralRules,
276                                 pluralFormIndex,
277                                 index,
278                                 explicitPluralPattern = new RegExp( '\\d+=', 'i' ),
279                                 formCount,
280                                 form;
282                         if ( !forms || forms.length === 0 ) {
283                                 return '';
284                         }
286                         // Handle for Explicit 0= & 1= values
287                         for ( index = 0; index < forms.length; index++ ) {
288                                 form = forms[index];
289                                 if ( explicitPluralPattern.test( form ) ) {
290                                         formCount = parseInt( form.substring( 0, form.indexOf( '=' ) ), 10 );
291                                         if ( formCount === count ) {
292                                                 return ( form.substr( form.indexOf( '=' ) + 1 ) );
293                                         }
294                                         forms[index] = undefined;
295                                 }
296                         }
298                         forms = $.map( forms, function ( form ) {
299                                 if ( form !== undefined ) {
300                                         return form;
301                                 }
302                         } );
304                         pluralRules = this.pluralRules[$.i18n().locale];
306                         if ( !pluralRules ) {
307                                 // default fallback.
308                                 return ( count === 1 ) ? forms[0] : forms[1];
309                         }
311                         pluralFormIndex = this.getPluralForm( count, pluralRules );
312                         pluralFormIndex = Math.min( pluralFormIndex, forms.length - 1 );
314                         return forms[pluralFormIndex];
315                 },
317                 /**
318                  * For the number, get the plural for index
319                  *
320                  * @param number
321                  * @param pluralRules
322                  * @return plural form index
323                  */
324                 getPluralForm: function ( number, pluralRules ) {
325                         var i,
326                                 pluralForms = [ 'zero', 'one', 'two', 'few', 'many', 'other' ],
327                                 pluralFormIndex = 0;
329                         for ( i = 0; i < pluralForms.length; i++ ) {
330                                 if ( pluralRules[pluralForms[i]] ) {
331                                         if ( pluralRuleParser( pluralRules[pluralForms[i]], number ) ) {
332                                                 return pluralFormIndex;
333                                         }
335                                         pluralFormIndex++;
336                                 }
337                         }
339                         return pluralFormIndex;
340                 },
342                 /**
343                  * Converts a number using digitTransformTable.
344                  *
345                  * @param {number} num Value to be converted
346                  * @param {boolean} integer Convert the return value to an integer
347                  */
348                 convertNumber: function ( num, integer ) {
349                         var tmp, item, i,
350                                 transformTable, numberString, convertedNumber;
352                         // Set the target Transform table:
353                         transformTable = this.digitTransformTable( $.i18n().locale );
354                         numberString = String( num );
355                         convertedNumber = '';
357                         if ( !transformTable ) {
358                                 return num;
359                         }
361                         // Check if the restore to Latin number flag is set:
362                         if ( integer ) {
363                                 if ( parseFloat( num, 10 ) === num ) {
364                                         return num;
365                                 }
367                                 tmp = [];
369                                 for ( item in transformTable ) {
370                                         tmp[transformTable[item]] = item;
371                                 }
373                                 transformTable = tmp;
374                         }
376                         for ( i = 0; i < numberString.length; i++ ) {
377                                 if ( transformTable[numberString[i]] ) {
378                                         convertedNumber += transformTable[numberString[i]];
379                                 } else {
380                                         convertedNumber += numberString[i];
381                                 }
382                         }
384                         return integer ? parseFloat( convertedNumber, 10 ) : convertedNumber;
385                 },
387                 /**
388                  * Grammatical transformations, needed for inflected languages.
389                  * Invoked by putting {{grammar:form|word}} in a message.
390                  * Override this method for languages that need special grammar rules
391                  * applied dynamically.
392                  *
393                  * @param word {String}
394                  * @param form {String}
395                  * @return {String}
396                  */
397                 convertGrammar: function ( word, form ) { /*jshint unused: false */
398                         return word;
399                 },
401                 /**
402                  * Provides an alternative text depending on specified gender. Usage
403                  * {{gender:[gender|user object]|masculine|feminine|neutral}}. If second
404                  * or third parameter are not specified, masculine is used.
405                  *
406                  * These details may be overriden per language.
407                  *
408                  * @param gender
409                  *      string male, female, or anything else for neutral.
410                  * @param forms
411                  *      array List of gender forms
412                  *
413                  * @return string
414                  */
415                 gender: function ( gender, forms ) {
416                         if ( !forms || forms.length === 0 ) {
417                                 return '';
418                         }
420                         while ( forms.length < 2 ) {
421                                 forms.push( forms[forms.length - 1] );
422                         }
424                         if ( gender === 'male' ) {
425                                 return forms[0];
426                         }
428                         if ( gender === 'female' ) {
429                                 return forms[1];
430                         }
432                         return ( forms.length === 3 ) ? forms[2] : forms[0];
433                 },
435                 /**
436                  * Get the digit transform table for the given language
437                  * See http://cldr.unicode.org/translation/numbering-systems
438                  * @param language
439                  * @returns {Array|boolean} List of digits in the passed language or false
440                  * representation, or boolean false if there is no information.
441                  */
442                 digitTransformTable: function ( language ) {
443                         var tables = {
444                                 ar: '٠١٢٣٤٥٦٧٨٩',
445                                 fa: '۰۱۲۳۴۵۶۷۸۹',
446                                 ml: '൦൧൨൩൪൫൬൭൮൯',
447                                 kn: '೦೧೨೩೪೫೬೭೮೯',
448                                 lo: '໐໑໒໓໔໕໖໗໘໙',
449                                 or: '୦୧୨୩୪୫୬୭୮୯',
450                                 kh: '០១២៣៤៥៦៧៨៩',
451                                 pa: '੦੧੨੩੪੫੬੭੮੯',
452                                 gu: '૦૧૨૩૪૫૬૭૮૯',
453                                 hi: '०१२३४५६७८९',
454                                 my: '၀၁၂၃၄၅၆၇၈၉',
455                                 ta: '௦௧௨௩௪௫௬௭௮௯',
456                                 te: '౦౧౨౩౪౫౬౭౮౯',
457                                 th: '๐๑๒๓๔๕๖๗๘๙', // FIXME use iso 639 codes
458                                 bo: '༠༡༢༣༤༥༦༧༨༩' // FIXME use iso 639 codes
459                         };
461                         if ( !tables[language] ) {
462                                 return false;
463                         }
465                         return tables[language].split( '' );
466                 }
467         };
469         $.extend( $.i18n.languages, {
470                 'default': language
471         } );
472 }( jQuery ) );