What’s wrong with currency character display in iOS?

Decrease of application perfomance due to fonts and symbols specific combinations is not well-studied problem. This article is closes issue partially

What’s wrong with currency character display in iOS?

What’s wrong with currency character display in iOS?

What’s wrong with currency character display in iOS?, photo 1

In June 2016 the ILE DE BEAUTE app that we developed was released in the App Store. The customer specified that we had to use the Carisma font for the app. Carisma is not a system font of the iOS platform, as you can see for yourself here. While working on the app, we noticed that currency characters ranging from U+20B6 (symbol for livre tournois) to U+20BE (symbol for Georgian lari) that are displayed in any non-system font cause performance drops. The russian ruble symbol is in this range as well.

Check out the difference:

currency-character-display-in-iOS.gif#as

Captain Obvious says hi!

The screen on the right scrolls slower. It can be seen by CPU`s overloading.

Let’s discuss this issue.

To determine which specific situations cause lag and performance drops, we’ll split the string representation with the currency symbol into separate parts:

  1. The following entities can contain the text: UILabel, UITextView and UITextField
  2. In these entities either the standard NSString or attributed NSAttributedString can be used
  3. There are three ways to get the ruble character for the string:
    1. using HTML:
    2. using unicode:
    3. using number formatter:

HTML

NSString *htmlString = @«<p>500 ₽</p> «; self.string = [[NSAttributedString alloc] initWithData:[htmlString dataUsingEncoding:NSUnicodeStringEncoding] options:@{ NSDocumentTypeDocumentAttribute: NSHTMLTextDocumentType } documentAttributes:nil error:nil];

unicode

self.string = [[NSAttributedString alloc] initWithString: @«500 \u20BD»];

number formatter

NSNumberFormatter * numberFormatter = [[NSNumberFormatter alloc] init]; [numberFormatter setNumberStyle:NSNumberFormatterCurrencyStyle]; [numberFormatter setCurrencyCode:@«RUB»]; [numberFormatter setMaximumFractionDigits:0]; self.string = [[NSAttributedString alloc] initWithString:[numberFormatter stringFromNumber:@500]];

Following combinations cause a drop in performance:

  1. UILabel, string type: attributed; methods used to get the character: 2 or 3
  2. UITextView, string type: any; methods used to get the character: any
  3. UITextField, string type: any; methods used to get the character: any

The idea of the experiment was to measure CPU load when scrolling the list with the elements containing the ruble character. The average load for the default state was lower than 10%, but if there was a performance drop, CPU load would go up to 30–80%, which is visible on the GIF’s.

symbols.png#asset:7364

The symbols highlighted on this image are the ones that cause this issue.

To get the app to function properly, you have to avoid the combinations I described above or use other fonts for currency symbols, like San Francisco or fonts from the Helvetica Neue family. However, these are minimal requirements. The actual reason for the increase in CPU load remains a mystery.

Skills
Staying optimistic about rendering optimization

Reflections about the future, in which websites load quickly and run smoothly, and how to approach it

Skills
December 27, 2016
Features of multi window mode on Android tablets

Issues that can arise when implementing multi window mode on tablet versions of apps

Skills
December 23, 2016