2

How to localize the NSString with format.

int value = 20;

NSString *str = @"hello";   

textLabel.text = [NSString stringWithFormat:@"%d %@", value, str];

I tried

textLabel.text = [NSString stringWithFormat:NSLocalizedString(@"%d %@", @"%d %@"), value, str];

but didn't work. Any help is appreciated.

Karen
  • 169
  • 1
  • 16
  • as per my understanding, localized strings are pre defined and cannot be changed unless you have a service call that returns the localized strings for a given string. – Teja Nandamuri Jan 10 '18 at 17:22
  • Please read the paragraph *Formatting String Resources* in [Resource Programming Guide](https://developer.apple.com/library/content/documentation/Cocoa/Conceptual/LoadingResources/Strings/Strings.html#//apple_ref/doc/uid/10000051i-CH6-SW1) – vadian Jan 10 '18 at 17:33
  • Are you trying to localise the formatting string, your string (`@"hello"`), or both? Edit your question to make it clear what "didn't work" means. That will help people to help you. – CRD Jan 10 '18 at 17:37
  • I want to convert both text and integer @CRD – Karen Jan 10 '18 at 17:40
  • How do you wish "to convert [the] integer"? Are you wishing that `20 hello` could be localised to, say Spanish, `veinte hola`? You are currently only attempting to localise the *format string*, you are not attempting to localise `str` or `value`. Edit your question and indicate what result you hoped for, what you have in your strings file, etc. and that will help people to help you. – CRD Jan 10 '18 at 18:31
  • Define "didn't work". – rmaddy Jan 10 '18 at 18:38

1 Answers1

5

Your localized string itself must be a format pattern:

"ValueAndStringFMT" = "Value %1$d and string %2$@";

And in your code:

textLabel.text = [NSString 
    stringWithFormat:NSLocalizedString(@"ValueAndStringFMT"),
    value, str
];

Why %1$d and not just %d? So you can change the order. E.g. in some language you may like to have the order swapped:

"ValueAndStringFMT" = "Cadena %2$@ y valor %1$d";

Of course, that is somewhat dangerous as if someone uses more placeholders than your string call offers or uses the wrong types, your app may crash. If you want to be safe, you do a search an replace instead:

"ValueAndStringFMT" = "Value [[VALUE]] and string [[STRING]]";

And in your code:

NSString * string = NSLocalizedString(@"ValueAndStringFMT");
string = [string stringByReplacingOccurrencesOfString:@"[[VALUE]]" 
    withString:@(value).stringValue
];
string = [string stringByReplacingOccurrencesOfString:@"[[STRING]]" 
    withString:str
];
textLabel.text = string;

That way the worst case scenario is that a placeholder is not expanded, meaning the placeholder is visibly printed on screen but at least your app won't crash because someone messed up the localization strings file.

If you need to localize one of the format variables, then you need to do that first in an own step:

NSString * str = NSLocalizedString(@"hello");
Mecki
  • 125,244
  • 33
  • 244
  • 253