Subversion Repositories Applications.papyrus

Rev

Rev 1987 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
1463 alexandre_ 1
<?php
2
// +----------------------------------------------------------------------+
3
// | PEAR :: I18Nv2                                                       |
4
// +----------------------------------------------------------------------+
5
// | This source file is subject to version 3.0 of the PHP license,       |
6
// | that is available at http://www.php.net/license/3_0.txt              |
7
// | If you did not receive a copy of the PHP license and are unable      |
8
// | to obtain it through the world-wide-web, please send a note to       |
9
// | license@php.net so we can mail you a copy immediately.               |
10
// +----------------------------------------------------------------------+
11
// | Copyright (c) 2004 Michael Wallner <mike@iworks.at>                  |
12
// +----------------------------------------------------------------------+
13
//
14
// $Id: I18Nv2.php,v 1.1 2007-06-25 09:55:28 alexandre_tb Exp $
15
 
16
/**
17
 * I18Nv2
18
 *
19
 * @package     I18Nv2
20
 * @category    Internationalization
21
 */
22
 
23
define('I18Nv2_WIN', defined('OS_WINDOWS') ? OS_WINDOWS : (strToUpper(substr(PHP_OS, 0,3)) === 'WIN'));
24
 
25
/**
26
 * I18Nv2 - Internationalization v2
27
 *
28
 * @author      Michael Wallner <mike@php.net>
29
 * @version     $Revision: 1.1 $
30
 * @package     I18Nv2
31
 * @access      public
32
 * @static
33
 */
34
class I18Nv2
35
{
36
    /**
37
     * Set Locale
38
     *
39
     * Example:
40
     * <code>
41
     * I18Nv2::setLocale('en_GB');
42
     * </code>
43
     *
44
     * @static
45
     * @access  public
46
     * @return  mixed   &type.string; used locale or false on failure
47
     * @param   string  $locale     a valid locale like en_US or de_DE
48
     * @param   int     $cat        the locale category - usually LC_ALL
49
     */
50
    function setLocale($locale = null, $cat = LC_ALL)
51
    {
52
        if (!strlen($locale)) {
53
            return setLocale($cat, null);
54
        }
55
 
56
        $locales = I18Nv2::getStaticProperty('locales');
57
 
58
        // get complete standard locale code (en => en_US)
59
        if (isset($locales[$locale])) {
60
            $locale = $locales[$locale];
61
        }
62
 
63
        // get Win32 locale code (en_US => enu)
64
        if (I18Nv2_WIN) {
65
            $windows   = I18Nv2::getStaticProperty('windows');
66
            $setlocale = isset($windows[$locale]) ? $windows[$locale] : $locale;
67
        } else {
68
            $setlocale = $locale;
69
        }
70
 
71
        $syslocale = setLocale($cat, $setlocale);
72
 
73
        // if the locale is not recognized by the system, check if there
74
        // is a fallback locale and try that, otherwise return false
75
        if (!$syslocale) {
76
            $fallbacks = &I18Nv2::getStaticProperty('fallbacks');
77
            if (isset($fallbacks[$locale])) {
78
                // avoid endless recursion with circular fallbacks
79
                $trylocale = $fallbacks[$locale];
80
                unset($fallbacks[$locale]);
81
                if ($retlocale = I18Nv2::setLocale($trylocale, $cat)) {
82
                    $fallbacks[$locale] = $trylocale;
83
                    return $retlocale;
84
                }
85
            }
86
            return false;
87
        }
88
 
89
        $language = substr($locale, 0,2);
90
 
91
        if (I18Nv2_WIN) {
92
            @putEnv('LANG='     . $language);
93
            @putEnv('LANGUAGE=' . $language);
94
        } else {
95
            @putEnv('LANG='     . $locale);
96
            @putEnv('LANGUAGE=' . $locale);
97
        }
98
 
99
        // unshift locale stack
100
        $last = &I18Nv2::getStaticProperty('last');
101
        array_unshift($last,
102
            array(
103
 
104
                1           => $language,
105
                2           => $syslocale,
106
                'locale'    => $locale,
107
                'language'  => $language,
108
                'syslocale' => $syslocale,
109
            )
110
        );
111
 
112
        // fetch locale specific information
113
        $info = &I18Nv2::getStaticProperty('info');
114
        $info = localeConv();
115
 
116
        return $syslocale;
117
    }
118
 
119
    /**
120
     * Get current/prior Locale
121
     *
122
     * @static
123
     * @access  public
124
     * @return  mixed   last locale as string or array
125
     * @param   int     $prior  if 0, the current otherwise n prior to current
126
     * @param   bool    $part   true|all|0=locale|1=language|2=syslocale
127
     */
128
    function lastLocale($prior = 0, $part = 0)
129
    {
130
        $last = I18Nv2::getStaticProperty('last');
131
        if (!isset($last)) {
132
            return I18Nv2::setLocale();
133
        }
134
        if (!isset($last[$prior])) {
135
            return null;
136
        }
137
        if ($part === true || $part == 'all') {
138
            return $last[$prior];
139
        }
140
        return $last[$prior][$part];
141
    }
142
 
143
    /**
144
     * Get several locale specific information
145
     *
146
     * @see     http://www.php.net/localeconv
147
     *
148
     * <code>
149
     * $locale = I18Nv2::setLocale('en_US');
150
     * $dollar = I18Nv2::getInfo('currency_symbol');
151
     * $point  = I18Nv2::getInfo('decimal_point');
152
     * </code>
153
     *
154
     * @static
155
     * @access  public
156
     * @return  mixed
157
     * @param   string  $part
158
     */
159
    function getInfo($part = null)
160
    {
161
        $info = &I18Nv2::getStaticProperty('info');
162
        return isset($part, $info[$part]) ? $info[$part] : $info;
163
    }
164
 
165
    /**
166
     * Create a Locale object
167
     *
168
     * @static
169
     * @access  public
170
     * @return  object  I18Nv2_Locale
171
     * @param   string  $locale     The locale to use.
172
     * @param   bool    $paranoid   Whether to operate in paranoid mode.
173
     */
174
    function &createLocale($locale = null, $paranoid = false)
175
    {
176
        require_once 'I18Nv2/Locale.php';
177
        $obj = &new I18Nv2_Locale($locale, $paranoid);
178
        return $obj;
179
    }
180
 
181
    /**
182
     * Create a Negotiator object
183
     *
184
     * @static
185
     * @access  public
186
     * @return  object  I18Nv2_Negotiator
187
     * @param   string  $defLang        default language
188
     * @param   string  $defEnc         default encoding
189
     * @param   string  $defCtry        default country
190
     */
191
    function &createNegotiator($defLang = 'en', $defEnc = 'iso-8859-1', $defCtry = '')
192
    {
193
        require_once 'I18Nv2/Negotiator.php';
194
        $obj = &new I18Nv2_Negotiator($defLang, $defEnc, $defCtry);
195
        return $obj;
196
    }
197
 
198
    /**
199
     * Automatically transform output between encodings
200
     *
201
     * This method utilizes ob_iconv_handler(), so you should call it at the
202
     * beginning of your script (prior to output).  If any output buffering has
203
     * been started before, the contents will be fetched with ob_get_contents()
204
     * and the buffers will be destroyed by ob_end_clean() if $refetchOB is set
205
     * to true.
206
     *
207
     * <code>
208
     * require_once('I18Nv2.php');
209
     * I18Nv2::autoConv('CP1252');
210
     * print('...'); // some iso-8859-1 stuff gets converted to Windows-1252
211
     * // ...
212
     * </code>
213
     *
214
     * @static
215
     * @access  public
216
     * @return  mixed   Returns &true; on success or
217
     *                  <classname>PEAR_Error</classname> on failure.
218
     * @param   string  $oe             desired output encoding
219
     * @param   string  $ie             internal encoding
220
     * @param   bool    $decodeRequest  whether to decode request variables
221
     *                                  ($_GET and $_POST) from $oe to $ie
222
     * @param   bool    $refetchOB      whether contents of already active
223
     *                                  output buffers should be fetched, the
224
     *                                  output buffer handlers destroyed and
225
     *                                  the fetched data be passed through
226
     *                                  ob_iconvhandler
227
     */
228
    function autoConv($oe = 'UTF-8', $ie = 'ISO-8859-1', $decodeRequest = true, $refetchOB = true)
229
    {
230
        if (!strcasecmp($oe, $ie)) {
231
            return true;
232
        }
233
 
234
        if (!extension_loaded('iconv')) {
235
            require_once 'PEAR.php';
236
            if (!PEAR::loadExtension('iconv')) {
237
                return PEAR::raiseError('Error: ext/iconv is not available');
238
            }
239
        }
240
 
241
        iconv_set_encoding('internal_encoding', $ie);
242
        iconv_set_encoding('output_encoding', $oe);
243
        iconv_set_encoding('input_encoding', $oe);
244
 
245
        $buffer = '';
246
        if ($refetchOB && $level = ob_get_level()) {
247
            while ($level--) {
248
                $buffer .= ob_get_contents();
249
                ob_end_clean();
250
            }
251
        }
252
 
253
        if (!ob_start('ob_iconv_handler')) {
254
            require_once 'PEAR.php';
255
            return PEAR::raiseError('Couldn\'t start output buffering');
256
        }
257
        echo $buffer;
258
 
259
        if ($decodeRequest) {
260
            I18Nv2::recursiveIconv($_GET, $oe, $ie);
261
            I18Nv2::recursiveIconv($_POST, $oe, $ie);
262
        }
263
 
264
        return true;
265
    }
266
 
267
    /**
268
     * Recursive Iconv
269
     *
270
     * @static
271
     * @access  public
272
     * @return  void
273
     * @param   array   $value
274
     * @param   string  $from
275
     * @param   string  $to
276
     */
277
    function recursiveIconv(&$value, $from, $to)
278
    {
279
        foreach ($value as $key => $val) {
280
            if (is_array($val)) {
281
                I18Nv2::recursiveIconv($value[$key], $from, $to);
282
            } else {
283
                $value[$key] = iconv($from, $to .'//TRANSLIT', $val);
284
            }
285
        }
286
    }
287
 
288
    /**
289
     * Traverse locales to languages
290
     *
291
     * Returns en-US, de-DE from en_US and de_DE
292
     *
293
     * @static
294
     * @access  public
295
     * @return  array
296
     * @param   array   $locales
297
     */
298
    function locales2langs($locales)
299
    {
300
        return array_map(array('I18Nv2','l2l'), (array) $locales);
301
    }
302
 
303
    /**
304
     * Traverse languages to locales
305
     *
306
     * Returns en_US, de_DE from en-US and de-DE
307
     *
308
     * @static
309
     * @access  public
310
     * @return  array
311
     * @param   array   $languages
312
     */
313
    function langs2locales($languages)
314
    {
315
        return array_map(array('I18Nv2','l2l'), (array) $languages);
316
    }
317
 
318
    /**
319
     * Locale to language or language to locale
320
     *
321
     * @static
322
     * @access  public
323
     * @return  string
324
     * @param   string  $localeOrLanguage
325
     */
326
    function l2l($localeOrLanguage)
327
    {
328
        return strtr($localeOrLanguage, '-_', '_-');
329
    }
330
 
331
    /**
332
     * Split locale code
333
     *
334
     * Splits locale codes into its language and country part
335
     *
336
     * @static
337
     * @access  public
338
     * @return  array
339
     * @param   string  $locale
340
     */
341
    function splitLocale($locale)
342
    {
343
        @list($l, $c) = preg_split('/[_-]/', $locale, 2, PREG_SPLIT_NO_EMPTY);
344
        return array($l, $c);
345
    }
346
 
347
    /**
348
     * Get language code of locale
349
     *
350
     * @static
351
     * @access  public
352
     * @return  string
353
     * @patram  string  $locale
354
     */
355
    function languageOf($locale)
356
    {
357
        return current($a = I18Nv2::splitLocale($locale));
358
    }
359
 
360
    /**
361
     * Get country code of locale
362
     *
363
     * @static
364
     * @access  public
365
     * @return  string
366
     * @param   string  $locale
367
     */
368
    function countryOf($locale)
369
    {
370
        return end($a = I18Nv2::splitLocale($locale));
371
    }
372
 
373
    /**
374
     * Get access to static property
375
     *
376
     * @static
377
     * @access  public
378
     * @return  mixed   Returns a reference to a static property
379
     * @param   string  $property   the static property
380
     */
381
    function &getStaticProperty($property)
382
    {
383
        static $properties;
384
        return $properties[$property];
385
    }
386
 
387
    /**
388
     * This one gets called automatically
389
     *
390
     * @ignore
391
     * @static
392
     * @internal
393
     * @access  private
394
     * @return  void
395
     */
396
    function _main()
397
    {
398
        // initialize the locale stack
399
        $last = &I18Nv2::getStaticProperty('last');
400
        $last = array();
401
 
402
        // map of "fully qualified locale" codes
403
        $locales = &I18Nv2::getStaticProperty('locales');
404
        $locales = array(
405
            'af' => 'af_ZA',
406
            'de' => 'de_DE',
407
            'en' => 'en_US',
408
            'fr' => 'fr_FR',
409
            'it' => 'it_IT',
410
            'es' => 'es_ES',
411
            'pt' => 'pt_PT',
412
            'sv' => 'sv_SE',
413
            'nb' => 'nb_NO',
414
            'nn' => 'nn_NO',
415
            'no' => 'no_NO',
416
            'fi' => 'fi_FI',
417
            'is' => 'is_IS',
418
            'da' => 'da_DK',
419
            'nl' => 'nl_NL',
420
            'pl' => 'pl_PL',
421
            'sl' => 'sl_SI',
422
            'hu' => 'hu_HU',
423
            'ru' => 'ru_RU',
424
            'cs' => 'cs_CZ',
425
        );
426
 
427
        // define locale fallbacks
428
        $fallbacks = &I18Nv2::getStaticProperty('fallbacks');
429
        $fallbacks = array(
430
            'no_NO' => 'nb_NO',
431
            'nb_NO' => 'no_NO',
432
        );
433
 
434
        // include Win32 locale codes
435
        if (I18Nv2_WIN) {
436
            include_once 'I18Nv2/Locale/Windows.php';
437
        }
438
    }
439
}
440
 
441
I18Nv2::_main();
442
 
443
?>