How to force NSLocalizedString to use a specific l

2018-12-31 01:34发布

On iPhone NSLocalizedString returns the string in the language of the iPhone. Is it possible to force NSLocalizedString to use a specific language to have the app in a different language than the device ?

25条回答
美炸的是我
2楼-- · 2018-12-31 02:09

You could build a sub-bundle with the set of localized strings that you want to do this with, and then use NSLocalizedStringFromTableInBundle() to load them. (I'm assuming that this is content separate from the normal UI localization you might be doing on the app.)

查看更多
高级女魔头
3楼-- · 2018-12-31 02:11

NSLocalizedString() (and variants thereof) access the "AppleLanguages" key in NSUserDefaults to determine what the user's settings for preferred languages are. This returns an array of language codes, with the first one being the one set by the user for their phone, and the subsequent ones used as fallbacks if a resource is not available in the preferred language. (on the desktop, the user can specify multiple languages with a custom ordering in System Preferences)

You can override the global setting for your own application if you wish by using the setObject:forKey: method to set your own language list. This will take precedence over the globally set value and be returned to any code in your application that is performing localization. The code for this would look something like:

[[NSUserDefaults standardUserDefaults] setObject:[NSArray arrayWithObjects:@"de", @"en", @"fr", nil] forKey:@"AppleLanguages"];
[[NSUserDefaults standardUserDefaults] synchronize]; //to make the change immediate

This would make German the preferred language for your application, with English and French as fallbacks. You would want to call this sometime early in your application's startup. You can read more about language/locale preferences here: Internationalization Programming Topics: Getting the Current Language and Locale

查看更多
回忆,回不去的记忆
4楼-- · 2018-12-31 02:11

for my case i have two localized file , ja and en

and i would like to force it to en if the preferred language in the system neither en or ja

i'm going to edit the main.m file

i 'll check whether the first preferred is en or ja , if not then i 'll change the second preferred language to en.

int main(int argc, char *argv[])
{

    [[NSUserDefaults standardUserDefaults] removeObjectForKey:@"AppleLanguages"];
    [[NSUserDefaults standardUserDefaults] synchronize];

    NSString *lang = [[NSLocale preferredLanguages] objectAtIndex:0];

    if (![lang isEqualToString:@"en"]  &&  ![lang isEqualToString:@"ja"]){

        NSMutableArray *array = [[NSMutableArray alloc] initWithArray:[NSLocale preferredLanguages]];
        [array replaceObjectAtIndex:1 withObject:@"en"];

        [[NSUserDefaults standardUserDefaults] setObject:array forKey:@"AppleLanguages"];
        [[NSUserDefaults standardUserDefaults] synchronize];


    }

    @autoreleasepool {
        return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class]));


    }


}
查看更多
素衣白纱
5楼-- · 2018-12-31 02:13

Here is a decent solution for this problem, and it does not require application restart.

https://github.com/cmaftuleac/BundleLocalization

This implementation works by tweaking inside NSBundle. The idea is that you override the method localizedStringForKey on the instance of NSBundle object, and then call this method on a different bundle with a different language. Simple and elegant fully compatible with all types of resources.

查看更多
只靠听说
6楼-- · 2018-12-31 02:14

Swift 3 solution:

let languages = ["bs", "zh-Hant", "en", "fi", "ko", "lv", "ms", "pl", "pt-BR", "ru", "sr-Latn", "sk", "es", "tr"]
UserDefaults.standard.set([languages[0]], forKey: "AppleLanguages")

Gave some examples of language codes that can be used. Hope this helps

查看更多
荒废的爱情
7楼-- · 2018-12-31 02:16

I wanted to add support for a language that isn't officially supported by iOS (not listed in Language section under system settings). By following the Apple's Internationalization Tutorial and few hints here by Brian Webster and geon, I came up with this piece of code (put it in main.m):

int main(int argc, char * argv[]) {
    @autoreleasepool {
        // Grab regional settings locale, for Slovenian this is either sl_SI or en_SI
        NSLocale *locale = [NSLocale currentLocale];
        NSString *ll = [locale localeIdentifier]; // sl_SI

        // Grab the first part of language identifier
        NSArray *comp = [ll componentsSeparatedByString:@"_"];
        NSString *ll1 = @"en";
        if (comp.count > 0) {
            ll1 = comp[0]; // sl, en, ...
        }
        // Check if we already saved language (user can manually change it inside app for example)
        if (![[NSUserDefaults standardUserDefaults] objectForKey:@"SelectedLanguage"]) {
            //   Slovenian (Slovenia),            Slovenia
            if ([ll isEqualToString:@"sl_SI"] || [ll isEqualToString:@"en_SI"]) {
                ll1 = @"sl-SI"; // This is the part of localized path for Slovenian language that Xcode generates
            }
            // Add more unsupported languages here...

            [[NSUserDefaults standardUserDefaults] setObject:ll1 forKey:@"SelectedLanguage"]; // Save language
        }
        else {
            // Restore language as we have previously saved it
            ll1 = [[NSUserDefaults standardUserDefaults] objectForKey:@"SelectedLanguage"];
        }
        // Overwrite NSLocalizedString and StoryBoard language preference
        [[NSUserDefaults standardUserDefaults] setObject:[NSArray arrayWithObjects:ll1, @"en", @"fr", nil] forKey:@"AppleLanguages"];
        // Make sure settings are stored to disk
        [[NSUserDefaults standardUserDefaults] synchronize];

        return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class]));
    }
}

This works well for both Storyboard and NSLocalizedString code. The code assumes that user will have an option to manually change language inside app later on.

Of course, don't forget to add proper Storyboard translations and Localizable.strings translations (see link to Apple page above for how to do that).

查看更多
登录 后发表回答