How to deal with different Region’s number formats in Swift
When building a simple Calculator App as my first App, I came across an issue that was never a concern when I started to code the App: numbers, most surely have different presentation formats, based on the user’s phone Region Settings!!!
That can impact not only the UI/UX of course, but also the way you write your code. You don’t want to have a String that cannot be converted to a Double and therefore cannot be used in the calculation. There might be some other ways to solve this, but the one that I found the easiest is by using the NumberFormatter Type. Swift make it simple and deal with all the transformations for you!
So how to do it? We’ll use a simple example in Playgrounds.
- First we declare a variable with the NumberFormatter Type:
var number = NumberFormatter()
2. Then using some of the properties of that Class, we can format it as we please:
- first let’s use the user’s current Region to set the general format of our variable.
number.locale = .current
- it can have a lot of Styles, like currency, ordinal or percentage. For the example let’s keep it with decimal:
number.numberStyle = .decimal
- setting it to true, we are accepting the format the current region has for the thousands separator. Alternatively we could use the commented line, setting the group separator ourselves:
number.usesGroupingSeparator = true
//number.groupingSeparator = “ “
3. Then let’s deal with the user’s input from the UI. That value comes for instance from a Text Field, is of type String, and we place it into a variable:
var userInput= “12000.02”
Just a String, with no spaces, and with a dot as the decimal separator.
4. The “tricky” part here is that we need to convert the String to a NSNumber in order to use the string() method of the NumberFormatter type. For that and to remove the complication everytime we need to use this, let’s make it as a function:
5. If we pass our User’s input through the function, we have the correctly formatted and useful result as a String, ready to be presented in the UI:
var result = formatResultForRegion(basedOn: userInput)
print(result)
In my case it will print 12 000,02 because I’m Portuguese and that’s how we divide the thousands (with a space), and decimals (with a comma).
6. Let’s just change some of the properties of our NumberFormatter variable and see what we would get:
number.locale = Locale(identifier: “pt_BR”)
number.numberStyle = .currency
As you can see we can also force the region to be whichever we want to. Just set it to the region you want. You can find the guide for the correct identifiers here.
Based on those changes if you call the function again the result will be:
$R 12.000,02
We changed the region to Brazil and the style to currency!
And that’s it! To know more about the NumberFormatter Type, its properties and methods, go here.