Override a base localizable.strings file - ios

Is there a way to have one base localizable.strings file for multiple targets within a project, and also have a second localizable.string file for each target that will override and append individual values to the base file?
EDIT
I want my app to have two .strings files - Localizable.string and Override.strings. If a string, Title.Welcome, is not found in OverrideLocalizable.strings then I would like the app to search Localizable.strings for Title.Welcome. Essentially, specifying Localizable as the fallback, but using OverrideLocalizable.strings by default.

Here is the solution I found:
NSString *PSILocalizedString(NSString *key, NSString *comment)
{
return NSLocalizedStringWithDefaultValue(key,
#"OverrideLocalizable",
[NSBundle mainBundle],
NSLocalizedString(key, nil),
comment);
}
What this will do is search a file called OverrideLocalizable.strings for the key. If the value for key is not found in OverrideLocalizable.strings, it will search localizable.strings for key. NSLocalizedString(key, nil) by default will search localizable.strings
Pretty simple and elegant solution

For Swift 4 users that come across this issue...
func localizedString(
for key: String, tableName: String = "OverrideLocalizable",
bundle: Bundle = .main, comment: String = ""
) -> String {
let defaultValue = NSLocalizedString(key, comment: comment)
return NSLocalizedString(
key, tableName: tableName, bundle: bundle,
value: defaultValue, comment: comment
)
}

Related

Return a string if localized string not found

I would like to know how could I return a default string value if localized string of key is not found. here is my function to return the localized String.
func localizedStr(key: String) {
return NSLocalizedString(key, comment: "")
}
I would like to return default string e.g. "foo" if the key is not found in localization file.
TL;DR
Use the full
NSLocalizedString(key: "key", value:"English string", comment: "")
If key is not found in your translated file, value is returned
Long version
Don't wrap NSLocalizedString in a function - while there's less code, you're losing valuable information for the localisation process.
you won't be able to use Xcode export an Xliff file for translation - only string literal keys in NSLocalizedString are included
Use a value: parameter with the English (or your base language) string. This is used when no translation is found, and means you don't need to have a base Localizable.strings file.
The comment: appears in the xliff file, and is useful for translators. Use this to give information about the context of the string being translated.
You could give it default value like this, using NSLocalizedString(key, comment: "") would return an Empty String if the Key was not found so checking on it like this should do the trick.
func localizedStr(key: String) {
if NSLocalizedString(key, comment: "") == key {
return "foo"
}
return NSLocalizedString(key, comment: "")

Set default language with localization

Is it possible to use a default language for the localization? for example if a key is not found for one language, than the system will look at it automatically in the English language? If it's not possible to do it automatically, would it be possible to do it manually? look for a key in the current language, if not found then force the system to look at it in the English language? In my current app, when a key is not set, the key name is returned.
Here is a method that do what you want (I didn't find an "official" way to do it).
func localizedString(_ key: String) -> String? {
let localeString = NSLocalizedString(key, comment: "")
// Base can be changed by en or the default language of your choice
if localeString == key,
let path = Bundle.main.path(forResource: "Base", ofType: ".lproj"),
let baseBundle = Bundle(path: path) {
return baseBundle.localizedString(forKey: key, value: nil, table: nil)
}
return nil
}

Localizable strings from JSON runtime on iOS

I have user localizable strings for the strings used in storyboard or source files which are fixed. These are defined in files like Localizable.string (Spanish), Localizable.string (German) etc. But I have a requirement where these strings can keep changing. These strings are received as a response to REST API call. My question is how can I use it.
Current code is let text = NSLocalizedString("Some string", comment: "")
Where NSLocalizedString looks for Localizable.string file. How can I make NSLocalizedString look for localized words from my custom dictionary/Json?
Try this
First you need to copy that files in document directory .
Get Localised Label
let localisedString = self.getLocalizatioString(key: "your key", stringFileName: "test.strings") //
Function
func getLocalizatioString(key : String?, stringFileName : String ) -> String {
let doumentDirectoryPath = NSSearchPathForDirectoriesInDomains(.documentDirectory, .userDomainMask, true)[0] as NSString
let destinationPath = doumentDirectoryPath.appendingPathComponent(stringFileName)
let dict = NSDictionary.init(contentsOfFile: destinationPath)
return (dict?.object(forKey: key!) as? String)!
}
Output
In String file

Unable to use localizable strings

I am trying to follow all instructions I have found in previous questions in term of localizing the application.
I Have succeeded in localizing storybaord when strings were generated. Now I am trying to prepare .strings file in order to use them in my swift files.
what I did:
new -> file -> strings file
Create localization of at least 2 languages on the previously created .strings file
I have put values in (polish)
"HELLO_WORLD" = "Dzień dobry!";
and in (english)
"HELLO_WORLD" = "Hello world!";
I have created string extension as follows:
extension String {
var localized: String {
return NSLocalizedString(self, tableName: nil, bundle: Bundle.main, value: "", comment: "")
}
}
I am trying to show the value like:
`helloworldLabel.text = "HELLO_WORLD".localized
but everything I gets is the same result. In hello world label I see "HELLO_WORLD"
can anyone give me a hint what Am I doing wrong?

iOS Base localization was not used for missing key

Let's say I have this 2 strings files in my project:
Localizable.strings (Base)
"hello_key" = "Hello";
"bye_key" = "Goodbye";
and
Localizable.strings (Chinese Traditional)
"hello_key" = "您好";
And I use the following code to localize the "hello" string
NSLocalizedString("hello_key", comment: "")
It works fine for "hello_key", but if I use "bye_key" in my iPhone with phone language set to Tradition Chinese, I get "bye_key" as the localized string.
In another word, the Base localization was not used. Is it possible to show the Base English "GoodBye" in this case?
Thanks.
This is the case of unsupported phrase, because your did not translate completely for Traditional Chinese.
Apple will not fallback to the base language, but simply return the key. This is just how it behaves. I wrote more about it in my blog.
You have to write a custom NSLocalizedString like this (the example uses en as the fallback language):
public func LS(_ key: String) -> String {
let value = NSLocalizedString(key, comment: "")
if value != key || NSLocale.preferredLanguages.first == "en" {
return value
}
// Fall back to en
guard
let path = Bundle.main.path(forResource: "en", ofType: "lproj"),
let bundle = Bundle(path: path)
else { return value }
return NSLocalizedString(key, bundle: bundle, comment: "")
}

Resources