WordPress.org

Make WordPress Core

Ticket #26511: switch_to_locale.php

File switch_to_locale.php, 3.7 KB (added by yoavf, 4 years ago)
Line 
1<?php
2
3/**
4 * Switches the translations to the given language.
5 *
6 * @param string $locale The slug of the language: en, fr, ja, etc.
7 * @param   bool $pop    Wether to push or pop the stack of switched languages.
8 * @see restore_current_locale()
9 *
10 * @return bool|string False on failure, language slug on success
11 */
12function switch_to_locale( $locale, $pop = false ) {
13        global $l10n, $wp_locale;
14        static $stack = false,           // Numeric array: The stack of languages we've switched to.  Does not include the original language.
15               $translations = false,    // Associative array: References to the translations.  Keyed by language slug.
16               $filters = false,         // Associative array: Functions used to filter
17               $original_locale = false; // String
18
19        if ( false === $stack ) {
20                $stack = $translations = $filters = array();
21                $original_locale = get_locale();
22        }
23
24        // We're restoring to the previous language via wpcom_restore_current_locale()
25        if ( $pop ) {
26                // The stack is empty, bail
27                if ( !array_pop( $stack ) ) {
28                        return false;
29                }
30
31                // Remove all filters
32                foreach ( $filters as $filter ) {
33                        remove_filter( 'locale', $filter );
34                }
35
36                if ( $locale = end( $stack ) ) {
37                        // Add the required filter back
38                        if ( isset( $filters[$locale] ) ) {
39                                add_filter( 'locale', $filters[$locale] );
40                        }
41                } else {
42                        // There's nothing left in the stack: go back to the original.
43                        $locale = $original_locale;
44                }
45
46                // Hack the correct translations in.
47                foreach ( array_keys( $l10n ) as $textdomain ) {
48                        $l10n[$textdomain] =& $translations[$locale][$textdomain];
49                }
50
51                // Set up date and number formatting globals
52                $wp_locale = new WP_Locale();
53
54                return $locale;
55        }
56
57        $current_locale = get_locale();
58
59        // We don't have a reference to the current translations stored here.  This must be the first time this function was called.
60        // Store it.
61        if ( ! isset( $translations[$current_locale] ) ) {
62                foreach ( array_keys( $l10n ) as $textdomain ) {
63                        $translations[$current_locale][$textdomain] = get_translations_for_domain( $textdomain );
64                }
65        }
66
67        // No change needed.  Still push to the stack so that a future wpcom_restore_current_locale() call won't break anything.
68        if ( $current_locale == $locale ) {
69                $stack[] = $locale;
70                return $locale;
71        }
72
73        // Push to the stack
74        $stack[] = $locale;
75
76        // Remove any filters we have attached
77        foreach ( $filters as $filter ) {
78                remove_filter( 'locale', $filter );
79        }
80
81        // Generate the required filter...
82        if ( ! isset( $filters[$locale] ) ) {
83                $filters[$locale] = function() use( $locale ) {
84                        return $locale;
85                };
86        }
87
88        // ... and add it
89        add_filter( 'locale', $filters[$locale] );
90
91        if ( isset( $translations[$locale] ) ) {
92                // We already have a reference - use it
93                foreach ( array_keys( $l10n ) as $textdomain ) {
94                        $l10n[$textdomain] =& $translations[$locale][$textdomain];
95                }
96        } else {
97                // We don't have a reference to the new translations stored here.  They must not have been generated yet.
98                // Create the translations and store a reference.
99                foreach ( array_keys( $l10n ) as $textdomain ) {
100
101                        unload_textdomain( $textdomain );
102                        if( $textdomain == 'default' ) {
103                                load_default_textdomain();
104                        } else {
105                                //BLOCKER: how do we get the MO file now?
106                                load_textdomain( $textdomain, $mo);
107                                $translations[$locale][$textdomain] = get_translations_for_domain( $textdomain );
108                        }
109                }
110        }
111
112        // Set up date and number formatting globals
113        $wp_locale = new WP_Locale();
114
115        return $locale;
116}
117
118/**
119 * Restores the translation language to the previous language in the stack.
120 * @uses switch_to_locale()
121 *
122 * @return bool|string False on failure, language slug on success.
123 */
124function restore_current_locale() {
125        return switch_to_locale( null, true );
126}